Skip to content

Commit

Permalink
improve alignment of marks and playpos, avoid using half empty images
Browse files Browse the repository at this point in the history
  • Loading branch information
m0dB authored and m0dB committed Nov 30, 2024
1 parent 92acba0 commit 7a1ec50
Show file tree
Hide file tree
Showing 3 changed files with 45 additions and 32 deletions.
21 changes: 9 additions & 12 deletions src/waveform/renderers/allshader/waveformrendermark.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -243,14 +243,13 @@ void allshader::WaveformRenderMark::paintGL() {
// Pixmaps are expected to have the mark stroke at the center,
// and preferably have an odd width in order to have the stroke
// exactly at the sample position.
const float markHalfWidth = pTexture->width() / devicePixelRatio / 2.f;
const float drawOffset = currentMarkPoint - markHalfWidth;
const float markWidth = pTexture->width() / devicePixelRatio;
const float drawOffset = currentMarkPoint + pMark->getOffset();

bool visible = false;
// Check if the current point needs to be displayed.
if (drawOffset > -markHalfWidth &&
drawOffset < m_waveformRenderer->getLength() +
markHalfWidth) {
if (drawOffset > -markWidth &&
drawOffset < m_waveformRenderer->getLength()) {
drawTexture(matrix,
drawOffset,
!m_isSlipRenderer && slipActive
Expand Down Expand Up @@ -299,10 +298,8 @@ void allshader::WaveformRenderMark::paintGL() {
devicePixelRatio;

if (m_playPosMarkTexture.isStorageAllocated()) {
const float markHalfWidth = m_playPosMarkTexture.width() / devicePixelRatio / 2.f;
const float drawOffset = currentMarkPoint - markHalfWidth;

drawTexture(matrix, drawOffset, 0.f, &m_playPosMarkTexture);
const float drawOffset = -(m_playPosMarkTexture.width() / devicePixelRatio - 1.f) / 2.f;
drawTexture(matrix, currentMarkPoint + drawOffset, 0.f, &m_playPosMarkTexture);
}

if (WaveformWidgetFactory::instance()->getUntilMarkShowBeats() ||
Expand Down Expand Up @@ -404,8 +401,8 @@ void allshader::WaveformRenderMark::updatePlayPosMarkTexture() {
// lines next to playpos
// Note: don't draw lines where they would overlap the triangles,
// otherwise both translucent strokes add up to a darker tone.
painter.drawLine(QLineF(lineX + 1.f, 4.f, lineX + 1.f, height));
painter.drawLine(QLineF(lineX - 1.f, 4.f, lineX - 1.f, height));
painter.drawLine(QLineF(lineX + 1.f, 4.f, lineX + 1.f, height / 3));
painter.drawLine(QLineF(lineX - 1.f, 4.f, lineX - 1.f, height / 3));

// triangle at top edge
// Increase line/waveform contrast
Expand All @@ -420,7 +417,7 @@ void allshader::WaveformRenderMark::updatePlayPosMarkTexture() {
painter.setPen(fgColor);
painter.setOpacity(1.0);
// play position line
painter.drawLine(QLineF(lineX, 0.f, lineX, height));
painter.drawLine(QLineF(lineX, 0.f, lineX, height / 3));
// triangle at top edge
{
QPointF baseL = QPointF(lineX - 4.f, 0.f);
Expand Down
51 changes: 31 additions & 20 deletions src/waveform/renderers/waveformmark.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -100,6 +100,7 @@ WaveformMark::WaveformMark(const QString& group,
const WaveformSignalColors& signalColors,
int hotCue)
: m_linePosition{},
m_offset{},
m_breadth{},
m_level{},
m_iPriority(priority),
Expand Down Expand Up @@ -278,6 +279,8 @@ struct MarkerGeometry {
const Qt::Alignment alignH = align & Qt::AlignHorizontal_Mask;
const Qt::Alignment alignV = align & Qt::AlignVertical_Mask;
const bool alignHCenter{alignH == Qt::AlignHCenter};
// when center aligning, make the image width odd (even label width + 1)
// so we can draw the line at a integer pixel position
const qreal widthRounding{alignHCenter ? 2.f : 1.f};

m_labelRect = QRectF{0.f,
Expand All @@ -286,17 +289,9 @@ struct MarkerGeometry {
widthRounding,
std::ceil(capHeight + 2.f * margin)};

m_imageSize = QSizeF{alignHCenter ? m_labelRect.width() + 1.f
: 2.f * m_labelRect.width() + 1.f,
breadth};
m_imageSize = QSizeF{m_labelRect.width() + 1.f, breadth};

if (alignH == Qt::AlignHCenter) {
m_labelRect.moveLeft((m_imageSize.width() - m_labelRect.width()) / 2.f);
} else if (alignH == Qt::AlignRight) {
m_labelRect.moveRight(m_imageSize.width() - 0.5f);
} else {
m_labelRect.moveLeft(0.5f);
}
m_labelRect.moveLeft(0.5f);

const float increment = overlappingMarkerIncrement(
static_cast<float>(m_labelRect.height()), breadth);
Expand Down Expand Up @@ -373,23 +368,39 @@ QImage WaveformMark::generateImage(float devicePixelRatio) {

painter.setWorldMatrixEnabled(false);

// Draw marker lines
const auto hcenter = markerGeometry.m_imageSize.width() / 2.f;
m_linePosition = static_cast<float>(hcenter);
const Qt::Alignment alignH = m_align & Qt::AlignHorizontal_Mask;
switch (alignH) {
case Qt::AlignHCenter:
m_linePosition = markerGeometry.m_imageSize.width() / 2.f;

Check failure on line 374 in src/waveform/renderers/waveformmark.cpp

View workflow job for this annotation

GitHub Actions / Ubuntu 22.04

conversion from ‘qreal’ {aka ‘double’} to ‘float’ may change value [-Werror=float-conversion]

Check warning on line 374 in src/waveform/renderers/waveformmark.cpp

View workflow job for this annotation

GitHub Actions / coverage

conversion from ‘qreal’ {aka ‘double’} to ‘float’ may change value [-Wfloat-conversion]
m_offset = -(markerGeometry.m_imageSize.width() - 1.f) / 2.f;

Check failure on line 375 in src/waveform/renderers/waveformmark.cpp

View workflow job for this annotation

GitHub Actions / Ubuntu 22.04

conversion from ‘qreal’ {aka ‘double’} to ‘float’ may change value [-Werror=float-conversion]

Check warning on line 375 in src/waveform/renderers/waveformmark.cpp

View workflow job for this annotation

GitHub Actions / coverage

conversion from ‘qreal’ {aka ‘double’} to ‘float’ may change value [-Wfloat-conversion]
DEBUG_ASSERT(linePos - std::roundf(linePos) < 0.000001f);

Check failure on line 376 in src/waveform/renderers/waveformmark.cpp

View workflow job for this annotation

GitHub Actions / clazy

use of undeclared identifier 'linePos'

Check failure on line 376 in src/waveform/renderers/waveformmark.cpp

View workflow job for this annotation

GitHub Actions / clazy

use of undeclared identifier 'linePos'

Check failure on line 376 in src/waveform/renderers/waveformmark.cpp

View workflow job for this annotation

GitHub Actions / coverage

‘linePos’ was not declared in this scope
break;
case Qt::AlignLeft:
m_linePosition = markerGeometry.m_imageSize.width() - 1.5f;

Check failure on line 379 in src/waveform/renderers/waveformmark.cpp

View workflow job for this annotation

GitHub Actions / Ubuntu 22.04

conversion from ‘qreal’ {aka ‘double’} to ‘float’ may change value [-Werror=float-conversion]

Check warning on line 379 in src/waveform/renderers/waveformmark.cpp

View workflow job for this annotation

GitHub Actions / coverage

conversion from ‘qreal’ {aka ‘double’} to ‘float’ may change value [-Wfloat-conversion]
m_offset = -markerGeometry.m_imageSize.width() + 2.f;

Check failure on line 380 in src/waveform/renderers/waveformmark.cpp

View workflow job for this annotation

GitHub Actions / Ubuntu 22.04

conversion from ‘qreal’ {aka ‘double’} to ‘float’ may change value [-Werror=float-conversion]

Check warning on line 380 in src/waveform/renderers/waveformmark.cpp

View workflow job for this annotation

GitHub Actions / coverage

conversion from ‘qreal’ {aka ‘double’} to ‘float’ may change value [-Wfloat-conversion]
break;
case Qt::AlignRight:
default:
m_linePosition = 1.5f;
m_offset = -1.f;
break;
}

const float linePos = m_linePosition;

// Draw the center line
painter.setPen(fillColor());
painter.drawLine(QLineF(hcenter, 0.f, hcenter, markerGeometry.m_imageSize.height()));
painter.drawLine(QLineF(linePos, 0.f, linePos, markerGeometry.m_imageSize.height() / 2));

painter.setPen(borderColor());
painter.drawLine(QLineF(hcenter - 1.f,
painter.drawLine(QLineF(linePos - 1.f,
0.f,
hcenter - 1.f,
markerGeometry.m_imageSize.height()));
painter.drawLine(QLineF(hcenter + 1.f,
linePos - 1.f,
markerGeometry.m_imageSize.height() / 2));
painter.drawLine(QLineF(linePos + 1.f,
0.f,
hcenter + 1.f,
markerGeometry.m_imageSize.height()));
linePos + 1.f,
markerGeometry.m_imageSize.height() / 2));

if (useIcon || label.length() != 0) {
painter.setPen(borderColor());
Expand Down
5 changes: 5 additions & 0 deletions src/waveform/renderers/waveformmark.h
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,10 @@ class WaveformMark {
WaveformMark(const WaveformMark&) = delete;
WaveformMark& operator=(const WaveformMark&) = delete;

float getOffset() const {
return m_offset;
}

int getHotCue() const {
return m_iHotCue;
};
Expand Down Expand Up @@ -158,6 +162,7 @@ class WaveformMark {
QString m_iconPath;

float m_linePosition;
float m_offset;
float m_breadth;

// When there are overlapping marks, level is increased for each overlapping mark,
Expand Down

0 comments on commit 7a1ec50

Please sign in to comment.