Add motif/stem_note display and offset note hierarchy

- parseAstLog: abort on depth jump >1 or missing slot (depth>0)
- buildStemNote: full clause tree (notes/pauses/stacks), editable fields
- buildClause: replaces buildCluster; filters nested clause.chain silently
- buildMotif: builds from voice.motif; sets isStatic
- buildOffset: uses buildStemNote; drops old clusters/chains arrays
- buildVoice: motifs are now objects, not label strings
- PaneSubObjects: static motifs before offsets; motif/offset→stem_note drill-down
- PaneFO: motif + stem_note FO cases; unknownProps display helper
- PaneCP: motif + stem_note shortView cases
- test-parser.mjs: 21 new synthetic tests for motif/clause/stack/guards
This commit is contained in:
c0dev0id
2026-06-27 16:14:56 +02:00
parent 3cd66f1e10
commit b887341df4
5 changed files with 233 additions and 66 deletions

View File

@@ -51,12 +51,32 @@ export const PaneSubObjects = {
}
if (node.type === 'bar') {
return Object.entries(node.voices).map(([name, v]) => ({
kind: 'voice', node: v, label: name, hasChildren: v.offsets.length > 0,
kind: 'voice', node: v, label: name,
hasChildren: v.offsets.length > 0 || v.motifs.some(m => m.isStatic),
}));
}
if (node.type === 'voice') {
return node.offsets.map((o, idx) => ({
kind: 'offset', node: o, label: `tick ${o.tick ?? idx}`, hasChildren: false,
return [
...node.motifs
.filter(m => m.isStatic)
.map(m => ({ kind: 'motif', node: m, label: m.label, hasChildren: m.stemNotes.length > 0 })),
...node.offsets.map((o, idx) => ({
kind: 'offset', node: o, label: `tick ${o.tick ?? idx}`, hasChildren: o.stemNotes.length > 0,
})),
];
}
if (node.type === 'motif') {
return node.stemNotes.map(sn => ({
kind: 'stem_note', node: sn,
label: `pitch ${sn.pitch}${sn.clauses.length ? ` (${sn.clauses.length} clause${sn.clauses.length > 1 ? 's' : ''})` : ''}`,
hasChildren: false,
}));
}
if (node.type === 'offset') {
return node.stemNotes.map(sn => ({
kind: 'stem_note', node: sn,
label: `pitch ${sn.pitch}${sn.clauses.length ? ` (${sn.clauses.length} clause${sn.clauses.length > 1 ? 's' : ''})` : ''}`,
hasChildren: false,
}));
}
return [];