Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
10 changes: 7 additions & 3 deletions qml/PropertiesPanel.qml
Original file line number Diff line number Diff line change
Expand Up @@ -1089,7 +1089,11 @@ Rectangle {
property int activeSlot: TexturePaintController.activeSlotIndex
property int brushTool: TexturePaintController.brushTool
property int paintTarget: TexturePaintController.paintTarget
property string previewUri: TexturePaintController.previewDataUri
// image://paintbuffer/current?v=N — served by PaintBufferImageProvider.
// Switching from PNG-encoded data URIs eliminates the per-stroke
// blink (each new base64 string was a fresh load) and drops the
// PNG encode + base64 churn off the main thread.
property string previewUri: TexturePaintController.fullResPreviewUrl
property string maskOverlayUri: TexturePaintController.maskOverlayDataUri
property bool hasMask: TexturePaintController.hasSelectionMask
property int maskCount: TexturePaintController.selectedPixelCount
Expand All @@ -1111,8 +1115,8 @@ Rectangle {
texPaintCol.slots = TexturePaintController.textureSlots
texPaintCol.activeSlot = TexturePaintController.activeSlotIndex
}
function onPreviewChanged() {
texPaintCol.previewUri = TexturePaintController.previewDataUri
function onFullResPreviewChanged() {
texPaintCol.previewUri = TexturePaintController.fullResPreviewUrl
}
function onBrushToolChanged() {
texPaintCol.brushTool = TexturePaintController.brushTool
Expand Down
36 changes: 7 additions & 29 deletions src/TexturePaintController.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -1958,41 +1958,19 @@

void TexturePaintController::refreshPreviewUri()
{
// Both the Inspector thumbnail and the detached editor window now
// consume `fullResPreviewUrl`, which is served by
// PaintBufferImageProvider (a QImage view of the buffer — no PNG
// encode, no base64). The legacy `previewDataUri` PNG path is
// retained as a property for binary compatibility but no longer
// populated; emitting `previewChanged` keeps any external observer
// notified without paying the encode cost on the main thread.
if (m_buffer.width() <= 0 || m_buffer.height() <= 0) {
if (!m_previewUri.isEmpty()) {

Check warning on line 1969 in src/TexturePaintController.cpp

View check run for this annotation

SonarQubeCloud / SonarCloud Code Analysis

Merge this "if" statement with the enclosing one.

See more on https://sonarcloud.io/project/issues?id=fernandotonon_QtMeshEditor&issues=AZ4z_bEZbrWrxHmeYctZ&open=AZ4z_bEZbrWrxHmeYctZ&pullRequest=541
m_previewUri.clear();
emit previewChanged();
}
// Bump the full-res URL anyway so any bound Image clears.
++m_fullResVersion;
emit fullResPreviewChanged();
return;
}
// Scale down to a thumbnail before PNG-encoding. The preview
// panel is 256×256; encoding a 1024² or 2048² PNG every refresh
// burns most of a frame on the main thread. Qt::FastTransformation
// is the cheapest scaler.
QImage src(const_cast<uchar*>(m_buffer.data().data()),
m_buffer.width(), m_buffer.height(),
m_buffer.width() * 4, QImage::Format_RGBA8888);
constexpr int kPreviewMax = 256;
QImage thumb = (m_buffer.width() > kPreviewMax || m_buffer.height() > kPreviewMax)
? src.scaled(kPreviewMax, kPreviewMax,
Qt::KeepAspectRatio, Qt::FastTransformation)
: src.copy(); // own the pixels — src points at m_buffer
QByteArray bytes;
QBuffer qbuf(&bytes);
qbuf.open(QIODevice::WriteOnly);
thumb.save(&qbuf, "PNG");
const QString next = QStringLiteral("data:image/png;base64,")
+ QString::fromLatin1(bytes.toBase64());
if (next != m_previewUri) {
m_previewUri = next;
emit previewChanged();
}
// The full-res preview channel doesn't need PNG encoding —
// QQuickImageProvider serves the live buffer directly on demand.
// Just bump the version so QML re-fetches.
++m_fullResVersion;
emit fullResPreviewChanged();
}
Expand Down
Loading
Loading