| 1112 | } |
| 1113 | |
| 1114 | static findHammerPullDestination(note: Note): Note | null { |
| 1115 | // For Hammer-Pull destinations we have 2 potential candidates |
| 1116 | // 1. A note on the same string |
| 1117 | // 2. A note on a different string, but with a left-hand-tapping applied |
| 1118 | |
| 1119 | // for the second case we have a special logic to search for notes: |
| 1120 | // 1. We first search on lower strings, then on higher strings |
| 1121 | // 2. If we find a note with a left-hand-tap applied it becomes the target |
| 1122 | // 3. If we find a note without a left-hand-tap we stop searching in this direction |
| 1123 | |
| 1124 | let nextBeat: Beat | null = note.beat.nextBeat; |
| 1125 | // keep searching in same bar |
| 1126 | while (nextBeat && nextBeat.voice.bar.index <= note.beat.voice.bar.index + Note._maxOffsetForSameLineSearch) { |
| 1127 | // 1. same string first |
| 1128 | let noteOnString: Note | null = nextBeat.getNoteOnString(note.string); |
| 1129 | if (noteOnString) { |
| 1130 | return noteOnString; |
| 1131 | } |
| 1132 | |
| 1133 | // 2. search toward lower strings |
| 1134 | for (let str = note.string; str > 0; str--) { |
| 1135 | noteOnString = nextBeat.getNoteOnString(str); |
| 1136 | if (noteOnString) { |
| 1137 | if (noteOnString.isLeftHandTapped) { |
| 1138 | return noteOnString; |
| 1139 | } |
| 1140 | break; |
| 1141 | } |
| 1142 | } |
| 1143 | |
| 1144 | // 3. search toward higher strings |
| 1145 | for (let str = note.string; str <= note.beat.voice.bar.staff.tuning.length; str++) { |
| 1146 | noteOnString = nextBeat.getNoteOnString(str); |
| 1147 | if (noteOnString) { |
| 1148 | if (noteOnString.isLeftHandTapped) { |
| 1149 | return noteOnString; |
| 1150 | } |
| 1151 | break; |
| 1152 | } |
| 1153 | } |
| 1154 | |
| 1155 | // nothing found, search on next beat |
| 1156 | nextBeat = nextBeat.nextBeat; |
| 1157 | } |
| 1158 | return null; |
| 1159 | } |
| 1160 | |
| 1161 | public static findTieOrigin(note: Note): Note | null { |
| 1162 | let previousBeat: Beat | null = note.beat.previousBeat; |