saebekassebil / teoria

Javascript taught Music Theory
http://saebekassebil.github.io/teoria
MIT License
1.32k stars 114 forks source link

Implement TeoriaNote#scaleDegree method #13

Closed saebekassebil closed 12 years ago

saebekassebil commented 12 years ago

In response to the feature request in Issue #12 I came up with this method which is a mixture of the proposed TeoriaNote#isScaleDegree and TeoriaNote#getScaleDegree.

The new method TeoriaNote#scaleDegree(scale) returns the scale degree of a note, given a scale. Its syntax is much like the other methods of the framework:

var scale = teoria.scale('eb4', 'major');
teoria.note('eb4').scaleDegree(scale); // Returns 1 as it is the proper degree number
teoria.note('f2').scaleDegree(scale); // Returns 2
teoria.note('g3').scaleDegree(scale); // Returns 3
teoria.note('g4').scaleDegree(scale); // Returns also 3
teoria.note('g5').scaleDegree(scale); // Returns also 3
teoria.note('a4').scaleDegree(scale); // Returns 0 as it is not listed in the scale
teoria.note('b5').scaleDegree(scale); // Returns 0
teoria.note('d#4').scaleDegree(scale); // Returns 0 as well.

The "clever" thing here is that notes that aren't in the scale will return 0, and in JavaScript 0 evaluates to false in a Boolean context, so that this method can be used just as a isScaleDegree method would be, e.g.:

if (note.scaleDegree(randomScale)) {
  // ...
}

// or for the more pedantic of us
if (!!note.scaleDegree(randomScale)) {
  // ...
}

// or for the *really* pedantic of us
if (note.scaleDegree(randomScale) !== 0) {
  // ...
}

I'm not quite sure however if this should be exploited, and I'd like a little feedback on this, and to hear if there's any objections against this.

@LukeHorvat, @GregJ - You guys have been active lately, any thoughts about this?

gregjopa commented 12 years ago

+1. I like this approach alot. It combines two methods into one and takes advantage of falsyness in javascript.

lukehorvat commented 12 years ago

Looks good. I like the dual-functionality. As long as it's documented in the readme, I don't think there should be any problems.

Thanks.