diff --git a/app/static/js/app.jsx b/app/static/js/app.jsx index d5b2355..087273f 100644 --- a/app/static/js/app.jsx +++ b/app/static/js/app.jsx @@ -14925,6 +14925,24 @@ const App = () => { const [selectionCleared, setSelectionCleared] = useState(false); // LOOP_EDITOR_2.md §4.2 + // Detect MAIN/SECTION play vừa DỪNG (hết notes/projectEnd/stop): nếu đang ở + // PIANO ROLL tab (không play tab) → playhead về 0 — user: main play hết → + // không còn midi note → piano roll phải về đầu (không giữ local cuối). + const prevIsPlayingRef = useRef(false); + useEffect(() => { + const wasPlaying = prevIsPlayingRef.current; + prevIsPlayingRef.current = isPlaying; + if (wasPlaying && !isPlaying) { + const _tabId = activeTabRef.current; + if (_tabId && _tabId.startsWith('midi_')) { + const _prSt = subTabsRef.current.find(s => s.id === _tabId); + if (_prSt && !_prSt.isPlaying) { + setSubTabs(prev => prev.map(s => s.id === _tabId ? { ...s, currentTime: 0 } : s)); + } + } + } + }, [isPlaying]); + const midiVuActivityRef = useRef({}); const triggerMidiVuActivity = (trackId, velocity) => { if (!trackId) return; diff --git a/app/static/js/app.precompiled.js b/app/static/js/app.precompiled.js index 68c04b5..7c445f6 100644 --- a/app/static/js/app.precompiled.js +++ b/app/static/js/app.precompiled.js @@ -717,7 +717,10 @@ if(activeTab==='main'&&prevSub.parent_tab_id&&prevSub.parent_tab_id.startsWith(' // roll — mainResumeRef vừa set bởi handleEditMidiInTab — clear nhầm ở // đây làm resume chết → quay lại main/section bị CÂM). mainResumeRef.current=null;}}},[activeTab]);const[selectionCleared,setSelectionCleared]=useState(false);// LOOP_EDITOR_2.md §4.2 -const midiVuActivityRef=useRef({});const triggerMidiVuActivity=(trackId,velocity)=>{if(!trackId)return;const velFactor=typeof velocity==='number'?velocity>1?velocity/127:velocity:0.8;const peak=Math.min(1.0,Math.max(0.15,velFactor));midiVuActivityRef.current[trackId]=peak;};window.triggerMidiVuActivity=triggerMidiVuActivity;// ── Temp Edit Tab (LOOP_EDITOR_2.md §1.2 Sub Tab) ── +// Detect MAIN/SECTION play vừa DỪNG (hết notes/projectEnd/stop): nếu đang ở +// PIANO ROLL tab (không play tab) → playhead về 0 — user: main play hết → +// không còn midi note → piano roll phải về đầu (không giữ local cuối). +const prevIsPlayingRef=useRef(false);useEffect(()=>{const wasPlaying=prevIsPlayingRef.current;prevIsPlayingRef.current=isPlaying;if(wasPlaying&&!isPlaying){const _tabId=activeTabRef.current;if(_tabId&&_tabId.startsWith('midi_')){const _prSt=subTabsRef.current.find(s=>s.id===_tabId);if(_prSt&&!_prSt.isPlaying){setSubTabs(prev=>prev.map(s=>s.id===_tabId?{...s,currentTime:0}:s));}}}},[isPlaying]);const midiVuActivityRef=useRef({});const triggerMidiVuActivity=(trackId,velocity)=>{if(!trackId)return;const velFactor=typeof velocity==='number'?velocity>1?velocity/127:velocity:0.8;const peak=Math.min(1.0,Math.max(0.15,velFactor));midiVuActivityRef.current[trackId]=peak;};window.triggerMidiVuActivity=triggerMidiVuActivity;// ── Temp Edit Tab (LOOP_EDITOR_2.md §1.2 Sub Tab) ── const[tempTabActive,setTempTabActive]=useState(false);const[tempTabBuffer,setTempTabBuffer]=useState(null);const[tempTabTrackId,setTempTabTrackId]=useState(null);const[tempTabOrigStart,setTempTabOrigStart]=useState(0);const[tempTabOrigEnd,setTempTabOrigEnd]=useState(0);const tempTabCanvasRef=useRef(null);// Effect parameters for temp tab const[tempTabEffects,setTempTabEffects]=useState({reverse:false,gainDb:0,fadeInMs:0,fadeOutMs:0});// ── Auth / User State ── const[currentUser,setCurrentUser]=useState(null);const[authModalOpen,setAuthModalOpen]=useState(false);const[authMode,setAuthMode]=useState('login');// 'login' | 'register' | 'force_change' diff --git a/app/templates/index.html b/app/templates/index.html index 9a1cc99..c9d5ce3 100644 --- a/app/templates/index.html +++ b/app/templates/index.html @@ -24,7 +24,7 @@ - +