when exporting KGProject to ABC Notation Music Sheet, we need to export all the tracks including the track contains user selected region, but we should skip the track with no region or no note.

This commit is contained in:
Xiaohan-Tian
2025-08-12 18:56:55 -07:00
parent 5e5a68e1d7
commit 4fc2d773fd
+31 -57
View File
@@ -4,9 +4,6 @@ import { KGMidiTrack } from '../../core/track/KGMidiTrack';
import { KGMidiRegion } from '../../core/region/KGMidiRegion';
import { convertRegionToABCNotation } from '../../util/abcNotationUtil';
import { KEY_SIGNATURE_MAP } from '../../constants/coreConstants';
import { useProjectStore } from '../../stores/projectStore';
import { KGRegion } from '../../core/region/KGRegion';
import { KGCore } from '../../core/KGCore';
/**
* Tool for reading music content from the project
@@ -104,65 +101,43 @@ export class ReadMusicTool extends BaseTool {
}
/**
* Get KGCore instance
* Find tracks that should be skipped because they have no musical content
* (no regions or regions with no notes)
*/
private getKGCore(): KGCore {
return KGCore.instance();
}
/**
* Find the track that contains the active piano roll region or first selected region
*/
private findTrackToSkip(tracks: KGMidiTrack[]): KGMidiTrack | null {
private findTracksToSkip(tracks: KGMidiTrack[]): KGMidiTrack[] {
try {
const store = useProjectStore.getState();
const core = this.getKGCore();
const tracksToSkip: KGMidiTrack[] = [];
// First check for active piano roll region
if (store.activeRegionId) {
const activeRegion = this.findRegionById(store.activeRegionId, tracks);
if (activeRegion) {
const track = this.findTrackByRegion(activeRegion, tracks);
return track;
for (const track of tracks) {
const regions = track.getRegions();
// Skip tracks with no regions
if (regions.length === 0) {
tracksToSkip.push(track);
continue;
}
// Check if all regions in this track are empty (have no notes)
const hasAnyNotes = regions.some(region => {
if (region.getCurrentType() === 'KGMidiRegion') {
return (region as KGMidiRegion).getNotes().length > 0;
}
return false;
});
// Skip tracks where no regions have notes
if (!hasAnyNotes) {
tracksToSkip.push(track);
}
}
// Then check for selected regions
const selectedItems = core.getSelectedItems();
const selectedRegion = selectedItems.find((item: unknown) => item instanceof KGRegion) as KGRegion;
if (selectedRegion) {
const track = this.findTrackByRegion(selectedRegion, tracks);
return track;
}
return null;
return tracksToSkip;
} catch (error) {
console.error('Error finding track to skip:', error);
return null;
console.error('Error finding tracks to skip:', error);
return [];
}
}
/**
* Find a region by ID across all tracks
*/
private findRegionById(regionId: string, tracks: KGMidiTrack[]): KGRegion | null {
for (const track of tracks) {
const regions = track.getRegions();
const region = regions.find(r => r.getId() === regionId);
if (region) {
return region;
}
}
return null;
}
/**
* Find track that contains the given region
*/
private findTrackByRegion(region: KGRegion, tracks: KGMidiTrack[]): KGMidiTrack | null {
return tracks.find(track => track.getRegions().includes(region)) || null;
}
/**
* Generate ABC notation for all tracks
@@ -174,9 +149,8 @@ export class ReadMusicTool extends BaseTool {
return 'No MIDI tracks found in the project.';
}
// Find the track to skip (unless it's the first track)
const trackToSkip = this.findTrackToSkip(midiTracks);
const firstTrack = midiTracks[0]; // The melody track
// Find tracks to skip (tracks with no content)
const tracksToSkip = this.findTracksToSkip(midiTracks);
// Get project settings for proper notation
const project = this.getCurrentProject();
@@ -187,8 +161,8 @@ export class ReadMusicTool extends BaseTool {
let output = `All Tracks (beats ${startBeat}-${endBeat || 'end'}):\n\n`;
midiTracks.forEach((track, index) => {
// Skip this track if it's the track to skip AND it's not the first track (melody)
if (trackToSkip && track === trackToSkip && track !== firstTrack) {
// Skip tracks that have no musical content
if (tracksToSkip.includes(track)) {
return; // Skip this track
}
const trackNumber = index + 1;