Fix drag-handoff bugs: gate FX re-resolve on outside-panel, cache unresolvable OS-drag verdict, block double FX-add retry

This commit is contained in:
2026-07-30 00:09:00 -04:00
parent 0800760833
commit 875d5b4632
9 changed files with 110 additions and 75 deletions
+1 -2
View File
@@ -50,8 +50,7 @@ PathList assemblePathList(const std::vector<ResolvedSample>& resolved) {
OsHandoff decideOsHandoff(const std::vector<std::string>& paths) {
OsHandoff out;
out.startOsDrag = !paths.empty();
out.releaseInternalDrag = out.startOsDrag;
out.handOffToOs = !paths.empty();
return out;
}
+8 -6
View File
@@ -71,13 +71,15 @@ PathList assemblePathList(const std::vector<ResolvedSample>& resolved);
// --- OS hand-off ordering -----------------------------------------------------
// The two side effects the shell performs when a drag crosses out of REAPER. They are ONE
// decision, not two: winding the internal drag down (release capture, clear drag state) for a
// hand-off that then cannot happen consumes the gesture — the user sees a drag that silently
// did nothing and drags again. Never release without starting.
// Whether an empty/unresolvable payload should hand off to the OS at all. This decides ONLY
// the empty-payload third of the failure space — an unresolvable payload must leave the
// internal drag live rather than winding it down (release capture, clear drag state) for a
// hand-off that then never happens, which reads to the user as "the drag did nothing, try
// again". A resolved-but-OS-not-ready hand-off (OLE unavailable, HDROP build failure) is a
// separate, shell-side readiness gate (drag_out_win::canInitiateDragOut) checked BEFORE the
// shell tears down internal drag state — this struct does not model that path.
struct OsHandoff {
bool startOsDrag = false; // hand `paths` to the OS drag initiator
bool releaseInternalDrag = false; // first wind down mouse capture + panel drag state
bool handOffToOs = false; // true: wind down internal drag state, then start the OS drag
};
// Decides the hand-off from the assembled path list. Empty (everything stale/unresolvable)