Detachable windows (#3532)

Allows detaching a window from LMMS's main window, making things like working on multiple screens easier.

The behavior of detached windows can be customized in the Settings.

Closes #1259

---------

Signed-off-by: Dalton Messmer <messmer.dalton@gmail.com>
Co-authored-by: Hyunjin Song <tteu.ingog@gmail.com>
Co-authored-by: Dalton Messmer <messmer.dalton@gmail.com>
Co-authored-by: SpomJ <mihail_a_m@mail.ru>
This commit is contained in:
Lukas W
2026-02-27 06:20:36 +01:00
committed by GitHub
parent 6854a655a4
commit 5d5f319942
50 changed files with 546 additions and 487 deletions

View File

@@ -57,6 +57,7 @@ AmplifierControlDialog::AmplifierControlDialog(AmplifierControls* controls) :
gridLayout->addWidget(makeKnob(tr("PAN"), tr("Panning:"), "%", &controls->m_panModel, false), 0, 1, Qt::AlignHCenter);
gridLayout->addWidget(makeKnob(tr("LEFT"), tr("Left gain:"), "%", &controls->m_leftModel, true), 1, 0, Qt::AlignHCenter);
gridLayout->addWidget(makeKnob(tr("RIGHT"), tr("Right gain:"), "%", &controls->m_rightModel, true), 1, 1, Qt::AlignHCenter);
gridLayout->setSizeConstraint(QLayout::SetFixedSize);
}
} // namespace lmms::gui

View File

@@ -67,6 +67,7 @@ BassBoosterControlDialog::BassBoosterControlDialog( BassBoosterControls* control
tl->addLayout( l );
setLayout( tl );
tl->setSizeConstraint(QLayout::SetFixedSize);
}

View File

@@ -71,7 +71,6 @@ class CompressorControlDialog : public EffectControlDialog
public:
CompressorControlDialog(CompressorControls* controls);
bool isResizable() const override {return true;}
QSize sizeHint() const override {return QSize(COMP_SCREEN_X, COMP_SCREEN_Y);}
// For theming purposes

View File

@@ -43,6 +43,7 @@ DispersionControlDialog::DispersionControlDialog(DispersionControls* controls) :
setAutoFillBackground(true);
auto layout = new QHBoxLayout(this);
layout->setSpacing(5);
layout->setSizeConstraint(QLayout::SetFixedSize);
auto amountBox = new LcdSpinBox(3, this, "Amount");
amountBox->setModel(&controls->m_amountModel);

View File

@@ -44,6 +44,7 @@ FlangerControlsDialog::FlangerControlsDialog( FlangerControls *controls ) :
setPalette( pal );
auto mainLayout = new QVBoxLayout(this);
mainLayout->setSizeConstraint(QLayout::SetFixedSize);
auto knobLayout = new QHBoxLayout();
mainLayout->addLayout(knobLayout);

View File

@@ -140,18 +140,13 @@ LadspaBrowserView::LadspaBrowserView( ToolPlugin * _tool ) :
hlayout->addWidget( ws );
hlayout->addSpacing( 10 );
hlayout->addStretch();
layout()->setSizeConstraint(QLayout::SetFixedSize);
hide();
if( parentWidget() )
{
parentWidget()->hide();
parentWidget()->layout()->setSizeConstraint(
QLayout::SetFixedSize );
Qt::WindowFlags flags = parentWidget()->windowFlags();
flags |= Qt::MSWindowsFixedSizeDialogHint;
flags &= ~Qt::WindowMaximizeButtonHint;
parentWidget()->setWindowFlags( flags );
}
}

View File

@@ -47,6 +47,7 @@ LadspaMatrixControlDialog::LadspaMatrixControlDialog(LadspaControls * ladspaCont
m_stereoLink(nullptr)
{
QVBoxLayout * mainLayout = new QVBoxLayout(this);
mainLayout->setSizeConstraint(QLayout::SetMinAndMaxSize);
m_scrollArea = new QScrollArea(this);
m_scrollArea->setWidgetResizable(true);
@@ -72,11 +73,6 @@ LadspaMatrixControlDialog::LadspaMatrixControlDialog(LadspaControls * ladspaCont
}
}
bool LadspaMatrixControlDialog::isResizable() const
{
return true;
}
bool LadspaMatrixControlDialog::needsLinkColumn() const
{
LadspaControls * ladspaControls = getLadspaControls();

View File

@@ -50,7 +50,6 @@ class LadspaMatrixControlDialog : public EffectControlDialog
Q_OBJECT
public:
LadspaMatrixControlDialog(LadspaControls* ctl);
bool isResizable() const override;
private slots:
void updateEffectView(LadspaControls* ctl);

View File

@@ -95,6 +95,8 @@ PeakControllerEffectControlDialog::PeakControllerEffectControlDialog(
mainLayout->addLayout( knobLayout );
mainLayout->addLayout( ledLayout );
mainLayout->setSizeConstraint(QLayout::SetFixedSize);
setLayout( mainLayout );
}

View File

@@ -44,6 +44,7 @@ ReverbSCControlDialog::ReverbSCControlDialog( ReverbSCControls* controls ) :
setPalette( pal );
auto knobLayout = new QHBoxLayout(this);
knobLayout->setSizeConstraint(QLayout::SetFixedSize);
auto inputGainKnob = new Knob(KnobType::Bright26, tr("Input"), this);
inputGainKnob->setModel( &controls->m_inputGainModel );
@@ -68,4 +69,4 @@ ReverbSCControlDialog::ReverbSCControlDialog( ReverbSCControls* controls ) :
}
} // namespace lmms::gui
} // namespace lmms::gui

View File

@@ -48,7 +48,6 @@ public:
explicit SaControlsDialog(SaControls *controls, SaProcessor *processor);
~SaControlsDialog() override = default;
bool isResizable() const override {return true;}
QSize sizeHint() const override;
private:

View File

@@ -39,6 +39,7 @@ StereoEnhancerControlDialog::StereoEnhancerControlDialog(
EffectControlDialog( _controls )
{
auto l = new QHBoxLayout(this);
l->setSizeConstraint(QLayout::SetFixedSize);
auto widthKnob = new Knob(KnobType::Bright26, tr("WIDTH"), this);
widthKnob->setModel( &_controls->m_widthModel );

View File

@@ -128,10 +128,10 @@ TapTempoView::TapTempoView(TapTempo* plugin)
});
hide();
layout()->setSizeConstraint(QLayout::SetFixedSize);
if (parentWidget())
{
parentWidget()->hide();
parentWidget()->layout()->setSizeConstraint(QLayout::SetFixedSize);
Qt::WindowFlags flags = parentWidget()->windowFlags();
flags |= Qt::MSWindowsFixedSizeDialogHint;

View File

@@ -45,7 +45,6 @@ public:
explicit VecControlsDialog(VecControls *controls);
~VecControlsDialog() override = default;
bool isResizable() const override {return true;}
QSize sizeHint() const override;
private:

View File

@@ -103,8 +103,9 @@ public:
vstSubWin( QWidget * _parent ) :
SubWindow( _parent )
{
setAttribute( Qt::WA_DeleteOnClose, false );
setWindowFlags( Qt::WindowCloseButtonHint );
setAttribute(Qt::WA_DeleteOnClose, false);
setWindowFlag(Qt::WindowMaximizeButtonHint, false);
setDetachable(false);
}
~vstSubWin() override = default;
@@ -918,12 +919,9 @@ ManageVestigeInstrumentView::ManageVestigeInstrumentView( Instrument * _instrume
widget = new QWidget(this);
l = new QGridLayout( this );
m_vi->m_subWindow = getGUI()->mainWindow()->addWindowedWidget(nullptr, Qt::SubWindow |
Qt::CustomizeWindowHint | Qt::WindowTitleHint | Qt::WindowSystemMenuHint);
m_vi->m_subWindow->setSizePolicy( QSizePolicy::Fixed, QSizePolicy::MinimumExpanding );
m_vi->m_subWindow->setFixedWidth( 960 );
m_vi->m_subWindow->setMinimumHeight( 300 );
m_vi->m_subWindow->setWidget(m_vi->m_scrollArea);
m_vi->m_subWindow = getGUI()->mainWindow()->addWindowedWidget(m_vi->m_scrollArea);
m_vi->m_scrollArea->setFixedWidth(960);
m_vi->m_scrollArea->setMinimumHeight(300);
m_vi->m_subWindow->setWindowTitle( m_vi->instrumentTrack()->name()
+ tr( " - VST plugin control" ) );
m_vi->m_subWindow->setWindowIcon( PLUGIN_NAME::getIconPixmap( "logo" ) );

View File

@@ -31,6 +31,7 @@
#include "Instrument.h"
#include "InstrumentView.h"
#include "SubWindow.h"
class QGridLayout;
@@ -86,7 +87,7 @@ private:
QMutex m_pluginMutex;
QString m_pluginDLL;
QMdiSubWindow * m_subWindow;
gui::SubWindow* m_subWindow;
QScrollArea * m_scrollArea;
FloatModel ** knobFModel;
QObject * p_subWindow;