Prove the render bounds at the boundary they cross, and name a short render whose count is exactly a millisecond-floored window
No truncation exists on our side of that boundary, so the read-back is the only evidence available for whether REAPER kept the window — and it fires on every tail mode, where only None was ever judged.
This commit is contained in:
@@ -34,6 +34,7 @@
|
||||
#include "core/capture/wav_codec.h" // hashWavContent / collapseToMono — the one WAV/RIFF owner
|
||||
#include "core/util/file_bytes.h"
|
||||
#include "core/capture/render_settings.h"
|
||||
#include "core/capture/render_window.h" // describeBoundsDrift — the read-back's verdict
|
||||
#include "shell/capture/render_bounds_gate.h" // the exact-bounds verdict on the landed render
|
||||
|
||||
#define REAPERAPI_MINIMAL
|
||||
@@ -424,6 +425,12 @@ CaptureResult OfflineRenderBackend::capture(const CaptureRequest& request) {
|
||||
GetSetProjectInfo(proj, "RENDER_STARTPOS", request.startSeconds, true);
|
||||
GetSetProjectInfo(proj, "RENDER_ENDPOS", request.endSeconds, true);
|
||||
|
||||
// The requested window crosses out of this process HERE and nowhere else, so the
|
||||
// read-back is the only evidence available on this side of that boundary for
|
||||
// whether REAPER kept it. Reported below, once the project rate is known.
|
||||
const double storedStart = GetSetProjectInfo(proj, "RENDER_STARTPOS", 0.0, false);
|
||||
const double storedEnd = GetSetProjectInfo(proj, "RENDER_ENDPOS", 0.0, false);
|
||||
|
||||
// TAILFLAG/TAILMS/NORMALIZE/TRIMEND from the pure mapping: None -> exact
|
||||
// bounds + disable-all normalize; Auto -> 8s tail + surgical trim-end
|
||||
// normalize + -72 dB TRIMEND; Manual -> clamped fixed tail + disable-all, no
|
||||
@@ -453,6 +460,18 @@ CaptureResult OfflineRenderBackend::capture(const CaptureRequest& request) {
|
||||
GetSetProjectInfo(proj, "RENDER_SRATE",
|
||||
static_cast<double>(effectiveSampleRate), true);
|
||||
}
|
||||
|
||||
// Silent unless a bound came back changed. Fires on EVERY tail mode on purpose:
|
||||
// only None is judged against its window after the render, so this is the sole
|
||||
// signal an Auto/Manual capture was shortened before it ever started.
|
||||
{
|
||||
const std::string drift =
|
||||
describeBoundsDrift(request.startSeconds, request.endSeconds,
|
||||
storedStart, storedEnd, effectiveSampleRate);
|
||||
if (!drift.empty())
|
||||
ShowConsoleMsg(("ReaSampler capture: " + drift + "\n").c_str());
|
||||
}
|
||||
|
||||
GetSetProjectInfo(proj, "RENDER_CHANNELS",
|
||||
static_cast<double>(request.channelCount), true);
|
||||
|
||||
|
||||
@@ -99,6 +99,17 @@ BoundsVerdict checkRenderedBounds(const std::string& renderedPath,
|
||||
const long long actualFrames = static_cast<long long>(layout.frameCount());
|
||||
if (renderHonoredBounds(expectedFrames, actualFrames)) return v;
|
||||
|
||||
// Says whether this shortfall has the one shape two live short renders already
|
||||
// matched to the frame, so every refusal from here on adds to (or breaks) that
|
||||
// evidence instead of needing the arithmetic done by hand. A count coincidence
|
||||
// only — it does not establish how the render resolved anything.
|
||||
const std::string msNote =
|
||||
actualFrames == msFlooredEndFrameCount(request.startSeconds,
|
||||
request.endSeconds, rate)
|
||||
? " Those are exactly the frames this window holds with its end floored to"
|
||||
" the millisecond -- a match on the count, not a measured cause."
|
||||
: std::string();
|
||||
|
||||
v.refused = true;
|
||||
v.message = "Render produced " + std::to_string(actualFrames) +
|
||||
" frames but the requested range is " + std::to_string(expectedFrames) +
|
||||
@@ -108,7 +119,7 @@ BoundsVerdict checkRenderedBounds(const std::string& renderedPath,
|
||||
std::to_string(request.endSeconds) + "s) -> frame indices [" +
|
||||
std::to_string(std::llround(request.startSeconds * rate)) + ", " +
|
||||
std::to_string(std::llround(request.endSeconds * rate)) + ")." +
|
||||
retainRefusedRender(renderedPath, projectDir);
|
||||
msNote + retainRefusedRender(renderedPath, projectDir);
|
||||
return v;
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user