renderer: nuke lastFrameDamage and rework finalDamage

this fucking SUCKED
This commit is contained in:
Vaxry 2024-02-23 01:02:32 +00:00
parent c1ef361e02
commit 8c3613632a
6 changed files with 34 additions and 31 deletions

View File

@ -107,8 +107,6 @@ class CMonitor {
CMonitor* pMirrorOf = nullptr;
std::vector<CMonitor*> mirrors;
CRegion lastFrameDamage; // stores last frame damage
// for tearing
CWindow* solitaryClient = nullptr;

View File

@ -431,16 +431,19 @@ void CScreencopyProtocolManager::sendFrameDamage(SScreencopyFrame* frame) {
if (!frame->withDamage)
return;
for (auto& RECT : frame->pMonitor->lastFrameDamage.getRects()) {
// TODO:
// add a damage ring for this.
if (frame->buffer->width < 1 || frame->buffer->height < 1 || frame->buffer->width - RECT.x1 < 1 || frame->buffer->height - RECT.y1 < 1) {
Debug::log(ERR, "[sc] Failed to send damage");
break;
}
// for (auto& RECT : frame->pMonitor->lastFrameDamage.getRects()) {
zwlr_screencopy_frame_v1_send_damage(frame->resource, std::clamp(RECT.x1, 0, frame->buffer->width), std::clamp(RECT.y1, 0, frame->buffer->height),
std::clamp(RECT.x2 - RECT.x1, 0, frame->buffer->width - RECT.x1), std::clamp(RECT.y2 - RECT.y1, 0, frame->buffer->height - RECT.y1));
}
// if (frame->buffer->width < 1 || frame->buffer->height < 1 || frame->buffer->width - RECT.x1 < 1 || frame->buffer->height - RECT.y1 < 1) {
// Debug::log(ERR, "[sc] Failed to send damage");
// break;
// }
// zwlr_screencopy_frame_v1_send_damage(frame->resource, std::clamp(RECT.x1, 0, frame->buffer->width), std::clamp(RECT.y1, 0, frame->buffer->height),
// std::clamp(RECT.x2 - RECT.x1, 0, frame->buffer->width - RECT.x1), std::clamp(RECT.y2 - RECT.y1, 0, frame->buffer->height - RECT.y1));
// }
}
bool CScreencopyProtocolManager::copyFrameShm(SScreencopyFrame* frame, timespec* now) {
@ -531,8 +534,6 @@ bool CScreencopyProtocolManager::copyFrameDmabuf(SScreencopyFrame* frame) {
g_pHyprOpenGL->renderTexture(sourceTex, &monbox, 1);
g_pHyprOpenGL->setMonitorTransformEnabled(true);
frame->pMonitor->lastFrameDamage = fakeDamage;
g_pHyprRenderer->endRender();
wlr_texture_destroy(sourceTex);

View File

@ -452,10 +452,6 @@ bool CToplevelExportProtocolManager::copyFrameDmabuf(SScreencopyFrame* frame, ti
if (frame->overlayCursor)
g_pHyprRenderer->renderSoftwareCursors(PMONITOR, fakeDamage, g_pInputManager->getMouseCoordsInternal() - frame->pWindow->m_vRealPosition.vec());
// introspection uses this as final damage.
// TODO: dont. This fucking sucks.
PMONITOR->lastFrameDamage = fakeDamage;
g_pHyprRenderer->endRender();
return true;
}

View File

@ -186,7 +186,7 @@ bool CHyprOpenGLImpl::passRequiresIntrospection(CMonitor* pMonitor) {
return false;
}
void CHyprOpenGLImpl::begin(CMonitor* pMonitor, CRegion* pDamage, CFramebuffer* fb) {
void CHyprOpenGLImpl::begin(CMonitor* pMonitor, const CRegion& damage_, CFramebuffer* fb, std::optional<CRegion> finalDamage) {
m_RenderData.pMonitor = pMonitor;
#ifndef GLES2
@ -238,7 +238,8 @@ void CHyprOpenGLImpl::begin(CMonitor* pMonitor, CRegion* pDamage, CFramebuffer*
if (m_RenderData.pCurrentMonData->monitorMirrorFB.isAllocated() && m_RenderData.pMonitor->mirrors.empty())
m_RenderData.pCurrentMonData->monitorMirrorFB.release();
m_RenderData.damage.set(*pDamage);
m_RenderData.damage.set(damage_);
m_RenderData.finalDamage.set(finalDamage.value_or(damage_));
m_bFakeFrame = fb;
@ -284,7 +285,7 @@ void CHyprOpenGLImpl::end() {
// end the render, copy the data to the WLR framebuffer
if (m_bOffloadedFramebuffer) {
m_RenderData.damage = m_RenderData.pMonitor->lastFrameDamage;
m_RenderData.damage = m_RenderData.finalDamage;
m_RenderData.outFB->bind();
@ -342,6 +343,11 @@ void CHyprOpenGLImpl::end() {
RASSERT(false, "glGetError at Opengl::end() returned GL_CONTEXT_LOST. Cannot continue until proper GPU reset handling is implemented.");
}
void CHyprOpenGLImpl::setDamage(const CRegion& damage_, std::optional<CRegion> finalDamage) {
m_RenderData.damage.set(damage_);
m_RenderData.finalDamage.set(finalDamage.value_or(damage_));
}
void CHyprOpenGLImpl::initShaders() {
GLuint prog = createProgram(QUADVERTSRC, QUADFRAGSRC);
m_RenderData.pCurrentMonData->m_shQUAD.program = prog;

View File

@ -101,6 +101,7 @@ struct SCurrentRenderData {
CFramebuffer* outFB = nullptr; // out to render to (if offloaded, etc)
CRegion damage;
CRegion finalDamage; // damage used for funal off -> main
SRenderModifData renderModif;
float mouseZoomFactor = 1.f;
@ -123,7 +124,7 @@ class CHyprOpenGLImpl {
public:
CHyprOpenGLImpl();
void begin(CMonitor*, CRegion*, CFramebuffer* fb = nullptr /* if provided, it's not a real frame */);
void begin(CMonitor*, const CRegion& damage, CFramebuffer* fb = nullptr, std::optional<CRegion> finalDamage = {});
void end();
void renderRect(CBox*, const CColor&, int round = 0);
@ -174,6 +175,8 @@ class CHyprOpenGLImpl {
void renderOffToMain(CFramebuffer* off);
void bindBackOnMain();
void setDamage(const CRegion& damage, std::optional<CRegion> finalDamage = {});
uint32_t getPreferredReadFormat(CMonitor* pMonitor);
const SGLPixelFormat* getPixelFormatFromDRM(uint32_t drmFormat);

View File

@ -1119,7 +1119,7 @@ void CHyprRenderer::renderMonitor(CMonitor* pMonitor) {
g_pHyprOpenGL->m_RenderData.useNearestNeighbor = false;
}
CRegion damage;
CRegion damage, finalDamage;
if (!beginRender(pMonitor, damage, RENDER_MODE_NORMAL)) {
Debug::log(ERR, "renderer: couldn't beginRender()!");
@ -1135,8 +1135,8 @@ void CHyprRenderer::renderMonitor(CMonitor* pMonitor) {
if (**PDAMAGETRACKINGMODE == DAMAGE_TRACKING_NONE || **PDAMAGETRACKINGMODE == DAMAGE_TRACKING_MONITOR || pMonitor->forceFullFrames > 0 || damageBlinkCleanup > 0 ||
pMonitor->isMirror() /* why??? */) {
damage = {0, 0, (int)pMonitor->vecTransformedSize.x * 10, (int)pMonitor->vecTransformedSize.y * 10};
pMonitor->lastFrameDamage = damage;
damage = {0, 0, (int)pMonitor->vecTransformedSize.x * 10, (int)pMonitor->vecTransformedSize.y * 10};
finalDamage = damage;
} else {
static auto* const PBLURENABLED = (Hyprlang::INT* const*)g_pConfigManager->getConfigValuePtr("decoration:blur:enabled");
@ -1152,16 +1152,15 @@ void CHyprRenderer::renderMonitor(CMonitor* pMonitor) {
// now, prep the damage, get the extended damage region
wlr_region_expand(damage.pixman(), damage.pixman(), BLURRADIUS); // expand for proper blurring
pMonitor->lastFrameDamage = damage;
finalDamage = damage;
wlr_region_expand(damage.pixman(), damage.pixman(), BLURRADIUS); // expand for proper blurring 2
} else {
pMonitor->lastFrameDamage = damage;
}
} else
finalDamage = damage;
}
// update damage in renderdata as we modified it
g_pHyprOpenGL->m_RenderData.damage.set(damage);
g_pHyprOpenGL->setDamage(damage, finalDamage);
if (pMonitor->forceFullFrames > 0) {
pMonitor->forceFullFrames -= 1;
@ -1237,7 +1236,7 @@ void CHyprRenderer::renderMonitor(CMonitor* pMonitor) {
CRegion frameDamage{};
const auto TRANSFORM = wlr_output_transform_invert(pMonitor->output->transform);
wlr_region_transform(frameDamage.pixman(), pMonitor->lastFrameDamage.pixman(), TRANSFORM, (int)pMonitor->vecTransformedSize.x, (int)pMonitor->vecTransformedSize.y);
wlr_region_transform(frameDamage.pixman(), finalDamage.pixman(), TRANSFORM, (int)pMonitor->vecTransformedSize.x, (int)pMonitor->vecTransformedSize.y);
if (**PDAMAGETRACKINGMODE == DAMAGE_TRACKING_NONE || **PDAMAGETRACKINGMODE == DAMAGE_TRACKING_MONITOR)
frameDamage.add(0, 0, (int)pMonitor->vecTransformedSize.x, (int)pMonitor->vecTransformedSize.y);
@ -2471,7 +2470,7 @@ bool CHyprRenderer::beginRender(CMonitor* pMonitor, CRegion& damage, eRenderMode
if (mode == RENDER_MODE_FULL_FAKE) {
RASSERT(fb, "Cannot render FULL_FAKE without a provided fb!");
fb->bind();
g_pHyprOpenGL->begin(pMonitor, &damage, fb);
g_pHyprOpenGL->begin(pMonitor, damage, fb);
return true;
}
@ -2501,7 +2500,7 @@ bool CHyprRenderer::beginRender(CMonitor* pMonitor, CRegion& damage, eRenderMode
wlr_damage_ring_rotate_buffer(&pMonitor->damage, m_pCurrentWlrBuffer, damage.pixman());
m_pCurrentRenderbuffer->bind();
g_pHyprOpenGL->begin(pMonitor, &damage);
g_pHyprOpenGL->begin(pMonitor, damage);
return true;
}