fix: minor updated the region lasso selection behavior
This commit is contained in:
@@ -94,6 +94,7 @@ const MainContent: React.FC<MainContentProps> = ({
|
||||
|
||||
// Refs to track pending updates for verification
|
||||
const pendingUpdates = useRef<Map<string, { trackId: string, regionId: string, startBeat: number, length: number }>>(new Map());
|
||||
const preventEmptyMainContentDeselectRef = useRef(false);
|
||||
|
||||
// Refs for auto-scroll during playback
|
||||
const mainContentRef = useRef<HTMLDivElement | null>(null);
|
||||
@@ -632,9 +633,18 @@ const MainContent: React.FC<MainContentProps> = ({
|
||||
return;
|
||||
}
|
||||
|
||||
if (preventEmptyMainContentDeselectRef.current) {
|
||||
preventEmptyMainContentDeselectRef.current = false;
|
||||
return;
|
||||
}
|
||||
|
||||
handleRegionLassoSelection([], { shiftKey: false });
|
||||
};
|
||||
|
||||
const handleRegionLassoCommit = () => {
|
||||
preventEmptyMainContentDeselectRef.current = true;
|
||||
};
|
||||
|
||||
// Handle region single click: selection only (no piano roll opening)
|
||||
const handleRegionClick = (regionId: string, options: RegionClickOptions = { shiftKey: false }) => {
|
||||
if (DEBUG_MODE.MAIN_CONTENT) {
|
||||
@@ -990,6 +1000,7 @@ const MainContent: React.FC<MainContentProps> = ({
|
||||
onRegionUpdated={handleRegionUpdated}
|
||||
onRegionClick={handleRegionClick}
|
||||
onRegionLassoSelection={handleRegionLassoSelection}
|
||||
onRegionLassoCommit={handleRegionLassoCommit}
|
||||
onOpenPianoRoll={handleOpenPianoRoll}
|
||||
onOpenSpectrogram={handleOpenSpectrogram}
|
||||
showHybridButtonForAudio={showHybridButtonForAudio}
|
||||
|
||||
@@ -119,6 +119,17 @@ describe('TrackGridPanel lasso selection', () => {
|
||||
expect(onRegionLassoSelection).toHaveBeenCalledWith(['region-b', 'region-a'], { shiftKey: false });
|
||||
});
|
||||
|
||||
it('uses the closest intersected region as primary when release is outside all regions', () => {
|
||||
const { container, onRegionLassoSelection } = renderPanel();
|
||||
const firstTrackGrid = container.querySelector('[data-test-id="track-grid-1"]') as HTMLDivElement;
|
||||
|
||||
fireEvent.mouseDown(firstTrackGrid, { clientX: 10, clientY: 10, button: 0 });
|
||||
fireEvent.mouseMove(document, { clientX: 150, clientY: 170 });
|
||||
fireEvent.mouseUp(document, { clientX: 150, clientY: 170 });
|
||||
|
||||
expect(onRegionLassoSelection).toHaveBeenCalledWith(['region-a', 'region-b'], { shiftKey: false });
|
||||
});
|
||||
|
||||
it('clears selection on a plain empty-space click', () => {
|
||||
const { container, onRegionLassoSelection } = renderPanel();
|
||||
const firstTrackGrid = container.querySelector('[data-test-id="track-grid-1"]') as HTMLDivElement;
|
||||
|
||||
@@ -32,6 +32,7 @@ interface TrackGridPanelProps {
|
||||
onRegionUpdated?: (regionId: string, updates: Partial<RegionUI>, expectedModelUpdates?: { startBeat: number, length: number }) => void;
|
||||
onRegionClick?: (regionId: string, options: RegionClickOptions) => void;
|
||||
onRegionLassoSelection?: (regionIds: string[], options: RegionClickOptions) => void;
|
||||
onRegionLassoCommit?: () => void;
|
||||
onOpenPianoRoll?: (regionId: string) => void;
|
||||
onOpenSpectrogram?: (regionId: string) => void;
|
||||
showHybridButtonForAudio?: boolean;
|
||||
@@ -53,6 +54,7 @@ const TrackGridPanel: React.FC<TrackGridPanelProps> = ({
|
||||
onRegionUpdated,
|
||||
onRegionClick,
|
||||
onRegionLassoSelection,
|
||||
onRegionLassoCommit,
|
||||
onOpenPianoRoll,
|
||||
onOpenSpectrogram,
|
||||
showHybridButtonForAudio,
|
||||
@@ -160,12 +162,36 @@ const TrackGridPanel: React.FC<TrackGridPanelProps> = ({
|
||||
});
|
||||
|
||||
const intersectedRegionIds = intersectedRegions.map(region => region.id);
|
||||
if (releaseRegionIndex > -1) {
|
||||
const [releaseRegionId] = intersectedRegionIds.splice(releaseRegionIndex, 1);
|
||||
intersectedRegionIds.push(releaseRegionId);
|
||||
if (intersectedRegionIds.length > 0) {
|
||||
const primaryRegionIndex = releaseRegionIndex > -1
|
||||
? releaseRegionIndex
|
||||
: intersectedRegions.reduce((closestIndex, region, index, allRegions) => {
|
||||
const regionLeft = (region.barNumber - 1) * barWidth;
|
||||
const regionRight = regionLeft + (region.length * barWidth);
|
||||
const regionTop = region.trackIndex * 120;
|
||||
const regionBottom = regionTop + 120;
|
||||
const regionCenterX = (regionLeft + regionRight) / 2;
|
||||
const regionCenterY = (regionTop + regionBottom) / 2;
|
||||
const regionDistance = Math.hypot(releasePointX - regionCenterX, releasePointY - regionCenterY);
|
||||
|
||||
const closestRegion = allRegions[closestIndex];
|
||||
const closestLeft = (closestRegion.barNumber - 1) * barWidth;
|
||||
const closestRight = closestLeft + (closestRegion.length * barWidth);
|
||||
const closestTop = closestRegion.trackIndex * 120;
|
||||
const closestBottom = closestTop + 120;
|
||||
const closestCenterX = (closestLeft + closestRight) / 2;
|
||||
const closestCenterY = (closestTop + closestBottom) / 2;
|
||||
const closestDistance = Math.hypot(releasePointX - closestCenterX, releasePointY - closestCenterY);
|
||||
|
||||
return regionDistance < closestDistance ? index : closestIndex;
|
||||
}, 0);
|
||||
|
||||
const [primaryRegionId] = intersectedRegionIds.splice(primaryRegionIndex, 1);
|
||||
intersectedRegionIds.push(primaryRegionId);
|
||||
}
|
||||
|
||||
onRegionLassoSelection?.(intersectedRegionIds, { shiftKey: isLassoShiftPressedRef.current });
|
||||
onRegionLassoCommit?.();
|
||||
}
|
||||
|
||||
isLassoSelectingRef.current = false;
|
||||
|
||||
Reference in New Issue
Block a user