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
27 changes: 27 additions & 0 deletions src/preferences/dialog/dlgprefwaveform.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -217,6 +217,18 @@ DlgPrefWaveform::DlgPrefWaveform(
QOverload<int>::of(&QComboBox::currentIndexChanged),
this,
&DlgPrefWaveform::slotSetUntilMarkTextHeightLimit);
connect(stemReorderLayerOnChangedCheckBox,
&QCheckBox::clicked,
this,
&DlgPrefWaveform::slotStemReorderOnChange);
connect(stemOpacitySpinBox,
&QDoubleSpinBox::valueChanged,
this,
&DlgPrefWaveform::slotStemOpacity);
connect(stemOutlineOpacitySpinBox,
&QDoubleSpinBox::valueChanged,
this,
&DlgPrefWaveform::slotStemOutlineOpacity);

setScrollSafeGuardForAllInputWidgets(this);
}
Expand Down Expand Up @@ -306,6 +318,10 @@ void DlgPrefWaveform::slotUpdate() {
WaveformWidgetFactory::toUntilMarkTextHeightLimitIndex(
factory->getUntilMarkTextHeightLimit()));

stemReorderLayerOnChangedCheckBox->setChecked(factory->isStemReorderOnChange());
stemOpacitySpinBox->setValue(factory->getStemOpacity());
stemOutlineOpacitySpinBox->setValue(factory->getStemOutlineOpacity());

mixxx::OverviewType cfgOverviewType =
m_pConfig->getValue<mixxx::OverviewType>(kOverviewTypeCfgKey, mixxx::OverviewType::RGB);
// Assumes the combobox index is in sync with the ControlPushButton
Expand Down Expand Up @@ -674,6 +690,17 @@ void DlgPrefWaveform::slotSetUntilMarkTextHeightLimit(int index) {
WaveformWidgetFactory::toUntilMarkTextHeightLimit(index));
}

void DlgPrefWaveform::slotStemOpacity(float value) {
WaveformWidgetFactory::instance()->setStemOpacity(value);
}
void DlgPrefWaveform::slotStemReorderOnChange(bool value) {
WaveformWidgetFactory::instance()->setStemReorderOnChange(value);
}

void DlgPrefWaveform::slotStemOutlineOpacity(float value) {
WaveformWidgetFactory::instance()->setStemOutlineOpacity(value);
}

void DlgPrefWaveform::calculateCachedWaveformDiskUsage() {
AnalysisDao analysisDao(m_pConfig);
QSqlDatabase dbConnection = mixxx::DbConnectionPooled(m_pLibrary->dbConnectionPool());
Expand Down
3 changes: 3 additions & 0 deletions src/preferences/dialog/dlgprefwaveform.h
Original file line number Diff line number Diff line change
Expand Up @@ -63,6 +63,9 @@ class DlgPrefWaveform : public DlgPreferencePage, public Ui::DlgPrefWaveformDlg
void slotSetUntilMarkAlign(int index);
void slotSetUntilMarkTextPointSize(int value);
void slotSetUntilMarkTextHeightLimit(int index);
void slotStemOpacity(float value);
void slotStemReorderOnChange(bool value);
void slotStemOutlineOpacity(float value);

private:
void initWaveformControl();
Expand Down
90 changes: 90 additions & 0 deletions src/preferences/dialog/dlgprefwaveformdlg.ui
Original file line number Diff line number Diff line change
Expand Up @@ -589,6 +589,96 @@ Select from different types of displays for the waveform, which differ primarily
</widget>
</item>

<item row="14" column="0">
<widget class="QLabel" name="stemOpacityLabel">
<property name="text">
<string>Stem</string>
</property>
<property name="alignment">
<set>Qt::AlignLeading|Qt::AlignLeft|Qt::AlignTop</set>
</property>
<property name="buddy">
<cstring>stemOpacityMainLabel</cstring>
</property>
</widget>
</item>
<item row="14" column="1" colspan="4">
<layout class="QGridLayout" name="stemOpacityGridLayout">
<item row="0" column="0">
<widget class="QLabel" name="stemOpacityMainLabel">
<property name="text">
<string>Channel opacity</string>
</property>
<property name="alignment">
<set>Qt::AlignLeading|Qt::AlignLeft|Qt::AlignVCenter</set>
</property>
<property name="buddy">
<cstring>stemOpacityMainLabel</cstring>
</property>
</widget>
</item>
<item row="0" column="1">
<widget class="QLabel" name="stemOpacityOutlineLabel">
<property name="text">
<string>Channel opacity (outline)</string>
</property>
<property name="alignment">
<set>Qt::AlignLeading|Qt::AlignLeft|Qt::AlignVCenter</set>
</property>
<property name="buddy">
<cstring>stemOpacityMainLabel</cstring>
</property>
</widget>
</item>

<item row="1" column="0">
<widget class="QDoubleSpinBox" name="stemOpacitySpinBox">
<property name="toolTip">
<string>Main stem opacity</string>
</property>
<property name="decimals">
<number>2</number>
</property>
<property name="minimum">
<double>0.010000000000000</double>
</property>
<property name="maximum">
<double>1.000000000000000</double>
</property>
<property name="singleStep">
<double>0.010000000000000</double>
</property>
</widget>
</item>
<item row="1" column="1">
<widget class="QDoubleSpinBox" name="stemOutlineOpacitySpinBox">
<property name="toolTip">
<string>Outline stem opacity</string>
</property>
<property name="decimals">
<number>2</number>
</property>
<property name="minimum">
<double>0.010000000000000</double>
</property>
<property name="maximum">
<double>1.000000000000000</double>
</property>
<property name="singleStep">
<double>0.010000000000000</double>
</property>
</widget>
</item>
<item row="2" column="0" colspan="2">
<widget class="QCheckBox" name="stemReorderLayerOnChangedCheckBox">
<property name="text">
<string>Move channel to foreground when volume is adjusted</string>
</property>
</widget>
</item>
</layout>
</item>

</layout>
</widget>
</item><!-- waveform groupbox -->
Expand Down
53 changes: 45 additions & 8 deletions src/waveform/renderers/allshader/waveformrendererstem.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@
#include <QImage>
#include <QOpenGLTexture>

#include "control/controlproxy.h"
#include "engine/channels/enginedeck.h"
#include "engine/engine.h"
#include "rendergraph/material/rgbamaterial.h"
Expand All @@ -13,6 +14,7 @@
#include "util/math.h"
#include "waveform/renderers/waveformwidgetrenderer.h"
#include "waveform/waveform.h"
#include "waveform/waveformwidgetfactory.h"

namespace {
#ifdef __SCENEGRAPH__
Expand All @@ -34,7 +36,9 @@ WaveformRendererStem::WaveformRendererStem(
::WaveformRendererAbstract::PositionSource type)
: WaveformRendererSignalBase(waveformWidget),
m_isSlipRenderer(type == ::WaveformRendererAbstract::Slip),
m_splitStemTracks(false) {
m_splitStemTracks(false),
m_outlineOpacity(0.15f),
m_opacity(0.75f) {
initForRectangles<RGBAMaterial>(0);
setUsePreprocess(true);
}
Expand All @@ -46,12 +50,43 @@ bool WaveformRendererStem::init() {
for (int stemIdx = 0; stemIdx < mixxx::kMaxSupportedStems; stemIdx++) {
QString stemGroup = EngineDeck::getGroupForStem(m_waveformRenderer->getGroup(), stemIdx);
m_pStemGain.emplace_back(
std::make_unique<PollingControlProxy>(stemGroup,
std::make_unique<ControlProxy>(stemGroup,
QStringLiteral("volume")));
m_pStemMute.emplace_back(
std::make_unique<PollingControlProxy>(stemGroup,
std::make_unique<ControlProxy>(stemGroup,
QStringLiteral("mute")));
auto bringToForeground = [this, stemIdx](double) {
if (!m_reorderOnChange) {
return;
}
m_stackOrder.removeAll(stemIdx);
m_stackOrder.append(stemIdx);
};
m_pStemGain.back()->connectValueChanged(this, bringToForeground);
m_pStemMute.back()->connectValueChanged(this, bringToForeground);
}

m_stackOrder.resize(mixxx::kMaxSupportedStems);
std::iota(m_stackOrder.begin(), m_stackOrder.end(), 0);

#ifndef __SCENEGRAPH__
Comment thread
Swiftb0y marked this conversation as resolved.
auto* pWaveformWidgetFactory = WaveformWidgetFactory::instance();
setReorderOnChange(pWaveformWidgetFactory->isStemReorderOnChange());
connect(pWaveformWidgetFactory,
&WaveformWidgetFactory::stemReorderOnChangeChanged,
this,
&WaveformRendererStem::setReorderOnChange);
setOutlineOpacity(pWaveformWidgetFactory->getStemOutlineOpacity());
connect(pWaveformWidgetFactory,
&WaveformWidgetFactory::stemOutlineOpacityChanged,
this,
&WaveformRendererStem::setOutlineOpacity);
setOpacity(pWaveformWidgetFactory->getStemOpacity());
connect(pWaveformWidgetFactory,
&WaveformWidgetFactory::stemOpacityChanged,
this,
&WaveformRendererStem::setOpacity);
#endif
return true;
}

Expand Down Expand Up @@ -152,15 +187,16 @@ bool WaveformRendererStem::preprocessInner() {
const double maxSamplingRange = visualIncrementPerPixel / 2.0;

for (int visualIdx = 0; visualIdx < stripLength; visualIdx++) {
for (int stemIdx = 0; stemIdx < mixxx::kMaxSupportedStems; stemIdx++) {
int stemLayer = 0;
for (int stemIdx : std::as_const(m_stackOrder)) {
// Stem is drawn twice with different opacity level, this allow to
// see the maximum signal by transparency
for (int layerIdx = 0; layerIdx < 2; layerIdx++) {
QColor stemColor = stemInfo[stemIdx].getColor();
float color_r = stemColor.redF(),
color_g = stemColor.greenF(),
color_b = stemColor.blueF(),
color_a = stemColor.alphaF() * (layerIdx ? 0.75f : 0.15f);
color_a = stemColor.alphaF() * (layerIdx ? m_opacity : m_outlineOpacity);
const int visualFrameStart = std::lround(xVisualFrame - maxSamplingRange);
const int visualFrameStop = std::lround(xVisualFrame + maxSamplingRange);

Expand Down Expand Up @@ -198,15 +234,16 @@ bool WaveformRendererStem::preprocessInner() {
// shadow
vertexUpdater.addRectangle(
{fVisualIdx - halfStripSize,
stemIdx * stemBreadth + halfBreadth -
stemLayer * stemBreadth + halfBreadth -
heightFactor * max},
{fVisualIdx + halfStripSize,
m_isSlipRenderer
? stemIdx * stemBreadth + halfBreadth
: stemIdx * stemBreadth + halfBreadth +
? stemLayer * stemBreadth + halfBreadth
: stemLayer * stemBreadth + halfBreadth +
heightFactor * max},
{color_r, color_g, color_b, color_a});
}
stemLayer++;
}

xVisualFrame += visualIncrementPerPixel;
Expand Down
25 changes: 22 additions & 3 deletions src/waveform/renderers/allshader/waveformrendererstem.h
Original file line number Diff line number Diff line change
Expand Up @@ -2,12 +2,12 @@

#include <vector>

#include "control/pollingcontrolproxy.h"
#include "rendergraph/geometrynode.h"
#include "util/class.h"
#include "waveform/renderers/allshader/waveformrenderersignalbase.h"

class QOpenGLTexture;
class ControlProxy;

namespace allshader {
class WaveformRendererStem;
Expand Down Expand Up @@ -37,13 +37,32 @@ class allshader::WaveformRendererStem final
void setSplitStemTracks(bool splitStemTracks) {
m_splitStemTracks = splitStemTracks;
}
void setReorderOnChange(bool value) {
m_reorderOnChange = value;
// Reset the stem layer stack to the natural order
std::iota(m_stackOrder.begin(), m_stackOrder.end(), 0);
Comment thread
Swiftb0y marked this conversation as resolved.
}
void setOutlineOpacity(float value) {
m_outlineOpacity = value;
markDirtyMaterial();
}
void setOpacity(float value) {
m_opacity = value;
markDirtyMaterial();
}

private:
bool m_isSlipRenderer;
bool m_splitStemTracks;

std::vector<std::unique_ptr<PollingControlProxy>> m_pStemGain;
std::vector<std::unique_ptr<PollingControlProxy>> m_pStemMute;
bool m_reorderOnChange;
float m_outlineOpacity;
float m_opacity;

std::vector<std::unique_ptr<ControlProxy>> m_pStemGain;
std::vector<std::unique_ptr<ControlProxy>> m_pStemMute;

QVarLengthArray<int, mixxx::kMaxSupportedStems> m_stackOrder;

bool preprocessInner();

Expand Down
33 changes: 33 additions & 0 deletions src/waveform/waveformwidgetfactory.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -427,6 +427,12 @@ bool WaveformWidgetFactory::setConfig(UserSettingsPointer config) {
setUntilMarkTextHeightLimit(toUntilMarkTextHeightLimit(
m_config->getValue(ConfigKey("[Waveform]", "UntilMarkTextHeightLimit"),
toUntilMarkTextHeightLimitIndex(m_untilMarkTextHeightLimit))));
setStemReorderOnChange(m_config->getValue(
ConfigKey("[Waveform]", "stem_reorder_on_change"), true));
setStemOpacity(static_cast<float>(
m_config->getValue(ConfigKey("[Waveform]", "stem_opacity"), 0.75)));
setStemOutlineOpacity(static_cast<float>(m_config->getValue(
ConfigKey("[Waveform]", "stem_outline_opacity"), 0.15)));

Comment thread
acolombier marked this conversation as resolved.
return true;
}
Expand Down Expand Up @@ -1362,6 +1368,33 @@ void WaveformWidgetFactory::setUntilMarkTextHeightLimit(float value) {
emit untilMarkTextHeightLimitChanged(value);
}

void WaveformWidgetFactory::setStemReorderOnChange(bool value) {
m_stemReorderOnChange = value;
if (m_config) {
m_config->setValue(ConfigKey("[Waveform]", "stem_reorder_on_change"),
value);
}
emit stemReorderOnChangeChanged(value);
}

void WaveformWidgetFactory::setStemOutlineOpacity(float value) {
m_stemOutlineOpacity = value;
if (m_config) {
m_config->setValue(ConfigKey("[Waveform]", "stem_outline_opacity"),
static_cast<double>(value));
}
emit stemOutlineOpacityChanged(value);
}

void WaveformWidgetFactory::setStemOpacity(float value) {
m_stemOpacity = value;
if (m_config) {
m_config->setValue(ConfigKey("[Waveform]", "stem_opacity"),
static_cast<double>(value));
}
emit stemOpacityChanged(value);
Comment thread
acolombier marked this conversation as resolved.
}

// static
Qt::Alignment WaveformWidgetFactory::toUntilMarkAlign(int index) {
switch (index) {
Expand Down
Loading