Browse Source

Go back to have real embed carla UI as VST

Leave the middleware window for non-linux OSes

Signed-off-by: falkTX <falktx@falktx.com>
tags/v2.1-rc1
falkTX 5 years ago
parent
commit
28e8f9ed67
Signed by: falkTX <falktx@falktx.com> GPG Key ID: CDBAA37ABC74FBA0
5 changed files with 217 additions and 17 deletions
  1. +5
    -2
      source/frontend/carla_host.py
  2. +165
    -4
      source/native-plugins/resources/carla-plugin
  3. +7
    -4
      source/plugin/carla-vst-export.cpp
  4. +32
    -5
      source/plugin/carla-vst.cpp
  5. +8
    -2
      source/plugin/carla-vst.hpp

+ 5
- 2
source/frontend/carla_host.py View File

@@ -208,16 +208,19 @@ class HostWindow(QMainWindow):
self.ui.menu_Engine.setEnabled(False) self.ui.menu_Engine.setEnabled(False)
self.ui.menu_Engine.setVisible(False) self.ui.menu_Engine.setVisible(False)
self.ui.menu_Engine.menuAction().setVisible(False) self.ui.menu_Engine.menuAction().setVisible(False)
self.ui.tabWidget.removeTab(2)


if self.host.isControl: if self.host.isControl:
self.ui.act_file_new.setVisible(False) self.ui.act_file_new.setVisible(False)
self.ui.act_file_open.setVisible(False) self.ui.act_file_open.setVisible(False)
self.ui.act_file_save_as.setVisible(False) self.ui.act_file_save_as.setVisible(False)
self.ui.tabUtils.removeTab(0) self.ui.tabUtils.removeTab(0)
self.ui.tabWidget.removeTab(2)
else: else:
self.ui.act_file_save_as.setText(self.tr("Export as...")) self.ui.act_file_save_as.setText(self.tr("Export as..."))


if not withCanvas:
self.ui.tabWidget.tabBar().hide()

else: else:
self.ui.act_engine_start.setEnabled(True) self.ui.act_engine_start.setEnabled(True)


@@ -2333,7 +2336,7 @@ class HostWindow(QMainWindow):
self.ui.pb_dsp_load.setValue(int(load)) self.ui.pb_dsp_load.setValue(int(load))


def getAndRefreshRuntimeInfo(self): def getAndRefreshRuntimeInfo(self):
if not self.isVisible():
if not self.ui.pb_dsp_load.isVisible():
return return
if not self.host.is_engine_running(): if not self.host.is_engine_running():
return return


+ 165
- 4
source/native-plugins/resources/carla-plugin View File

@@ -19,7 +19,7 @@
# ------------------------------------------------------------------------------------------------------------ # ------------------------------------------------------------------------------------------------------------
# Imports (Global) # Imports (Global)


from PyQt5.QtGui import QKeySequence
from PyQt5.QtGui import QKeySequence, QMouseEvent
from PyQt5.QtWidgets import QHBoxLayout from PyQt5.QtWidgets import QHBoxLayout


# ------------------------------------------------------------------------------------------------------------ # ------------------------------------------------------------------------------------------------------------
@@ -81,12 +81,12 @@ class CarlaMiniW(ExternalUI, HostWindow):
def __init__(self, host, isPatchbay, parent=None): def __init__(self, host, isPatchbay, parent=None):
ExternalUI.__init__(self) ExternalUI.__init__(self)
HostWindow.__init__(self, host, isPatchbay, parent) HostWindow.__init__(self, host, isPatchbay, parent)
self.host = host


if False: if False:
# kdevelop likes this :) # kdevelop likes this :)
host = PluginHost() host = PluginHost()
self.host = host

self.host = host


host.setExternalUI(self) host.setExternalUI(self)


@@ -387,6 +387,157 @@ class CarlaMiniW(ExternalUI, HostWindow):
else: else:
print("unknown message: \"" + msg + "\"") print("unknown message: \"" + msg + "\"")


# ------------------------------------------------------------------------------------------------------------
# Embed Widget

class QEmbedWidget(QWidget):
def __init__(self, winId):
QWidget.__init__(self)
self.setAttribute(Qt.WA_LayoutUsesWidgetRect)
self.move(0, 0)

self.fPos = (0, 0)
self.fWinId = 0

def finalSetup(self, gui, winId):
self.fWinId = int(self.winId())
gui.ui.centralwidget.installEventFilter(self)
gui.ui.menubar.installEventFilter(self)
gCarla.utils.x11_reparent_window(self.fWinId, winId)
self.show()

def fixPosition(self):
pos = gCarla.utils.x11_get_window_pos(self.fWinId)
if self.fPos == pos:
return
self.fPos = pos
self.move(pos[0], pos[1])
gCarla.utils.x11_move_window(self.fWinId, pos[2], pos[3])

def eventFilter(self, obj, ev):
if isinstance(ev, QMouseEvent):
self.fixPosition()
return False

def enterEvent(self, ev):
self.fixPosition()
QWidget.enterEvent(self, ev)

# ------------------------------------------------------------------------------------------------------------
# Embed plugin UI

class CarlaEmbedW(QEmbedWidget):
def __init__(self, host, winId, isPatchbay):
QEmbedWidget.__init__(self, winId)

if False:
host = CarlaHostPlugin()

self.host = host
self.fWinId = winId
self.setFixedSize(1024, 712)

self.fLayout = QVBoxLayout(self)
self.fLayout.setContentsMargins(0, 0, 0, 0)
self.fLayout.setSpacing(0)
self.setLayout(self.fLayout)

self.gui = CarlaMiniW(host, isPatchbay, self)
self.gui.hide()

self.gui.ui.act_file_quit.setEnabled(False)
self.gui.ui.act_file_quit.setVisible(False)

self.fShortcutActions = []
self.addShortcutActions(self.gui.ui.menu_File.actions())
self.addShortcutActions(self.gui.ui.menu_Plugin.actions())
self.addShortcutActions(self.gui.ui.menu_PluginMacros.actions())
self.addShortcutActions(self.gui.ui.menu_Settings.actions())
self.addShortcutActions(self.gui.ui.menu_Help.actions())

if self.host.processMode == ENGINE_PROCESS_MODE_PATCHBAY:
self.addShortcutActions(self.gui.ui.menu_Canvas.actions())
self.addShortcutActions(self.gui.ui.menu_Canvas_Zoom.actions())

self.addWidget(self.gui.ui.menubar)
self.addLine()
self.addWidget(self.gui.ui.toolBar)

if self.host.processMode == ENGINE_PROCESS_MODE_PATCHBAY:
self.addLine()

self.addWidget(self.gui.centralWidget())
self.finalSetup(self.gui, winId)

def addShortcutActions(self, actions):
for action in actions:
if not action.shortcut().isEmpty():
self.fShortcutActions.append(action)

def addWidget(self, widget):
widget.setParent(self)
self.fLayout.addWidget(widget)

def addLine(self):
line = QFrame(self)
line.setFrameShadow(QFrame.Sunken)
line.setFrameShape(QFrame.HLine)
line.setLineWidth(0)
line.setMidLineWidth(1)
self.fLayout.addWidget(line)

def keyPressEvent(self, event):
modifiers = event.modifiers()
modifiersStr = ""

if modifiers & Qt.ShiftModifier:
modifiersStr += "Shift+"
if modifiers & Qt.ControlModifier:
modifiersStr += "Ctrl+"
if modifiers & Qt.AltModifier:
modifiersStr += "Alt+"
if modifiers & Qt.MetaModifier:
modifiersStr += "Meta+"

keyStr = QKeySequence(event.key()).toString()
keySeq = QKeySequence(modifiersStr + keyStr)

for action in self.fShortcutActions:
if not action.isEnabled():
continue
if keySeq.matches(action.shortcut()) != QKeySequence.ExactMatch:
continue
event.accept()
action.trigger()
return

QEmbedWidget.keyPressEvent(self, event)

def showEvent(self, event):
QEmbedWidget.showEvent(self, event)

# set our gui as parent for all plugins UIs
if self.host.manageUIs:
winIdStr = "%x" % self.fWinId
self.host.set_engine_option(ENGINE_OPTION_FRONTEND_WIN_ID, 0, winIdStr)

def hideEvent(self, event):
# disable parent
self.host.set_engine_option(ENGINE_OPTION_FRONTEND_WIN_ID, 0, "0")

QEmbedWidget.hideEvent(self, event)

def closeEvent(self, event):
self.gui.close()
self.gui.closeExternalUI()
QEmbedWidget.closeEvent(self, event)

# there might be other qt windows open which will block carla-plugin from quitting
app.quit()

def setLoadRDFsNeeded(self):
self.gui.setLoadRDFsNeeded()

# ------------------------------------------------------------------------------------------------------------ # ------------------------------------------------------------------------------------------------------------
# Main # Main


@@ -415,7 +566,17 @@ if __name__ == '__main__':
# ------------------------------------------------------------- # -------------------------------------------------------------
# Create GUI # Create GUI


gui = CarlaMiniW(host, isPatchbay)
try:
winId = int(os.getenv("CARLA_PLUGIN_EMBED_WINID"))
except:
winId = 0

gCarla.utils.setenv("CARLA_PLUGIN_EMBED_WINID", "0")

if LINUX and winId != 0:
gui = CarlaEmbedW(host, winId, isPatchbay)
else:
gui = CarlaMiniW(host, isPatchbay)


# ------------------------------------------------------------- # -------------------------------------------------------------
# App-Loop # App-Loop


+ 7
- 4
source/plugin/carla-vst-export.cpp View File

@@ -1,6 +1,6 @@
/* /*
* Carla Native Plugins * Carla Native Plugins
* Copyright (C) 2013-2018 Filipe Coelho <falktx@falktx.com>
* Copyright (C) 2013-2019 Filipe Coelho <falktx@falktx.com>
* *
* This program is free software; you can redistribute it and/or * This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License as * modify it under the terms of the GNU General Public License as
@@ -16,10 +16,13 @@
*/ */


#include "carla-vst.hpp" #include "carla-vst.hpp"
#include "ui_launcher.cpp"
#include "ui_launcher_res.cpp"


#include "CarlaDefines.h"
#ifndef CARLA_OS_LINUX
# include "ui_launcher.cpp"
# include "ui_launcher_res.cpp"
#endif

#include <cstring>


#ifdef __WINE__ #ifdef __WINE__
__cdecl static intptr_t cvst_dispatcherCallback(AEffect* effect, int32_t opcode, int32_t index, intptr_t value, void* ptr, float opt) __cdecl static intptr_t cvst_dispatcherCallback(AEffect* effect, int32_t opcode, int32_t index, intptr_t value, void* ptr, float opt)


+ 32
- 5
source/plugin/carla-vst.cpp View File

@@ -84,7 +84,9 @@ public:
fMidiEventCount(0), fMidiEventCount(0),
fTimeInfo(), fTimeInfo(),
fVstRect(), fVstRect(),
#ifndef CARLA_OS_LINUX
fUiLauncher(nullptr), fUiLauncher(nullptr),
#endif
fHostType(kHostTypeNull), fHostType(kHostTypeNull),
fMidiOutEvents(), fMidiOutEvents(),
#ifdef USING_JUCE #ifdef USING_JUCE
@@ -133,8 +135,13 @@ public:


fVstRect.top = 0; fVstRect.top = 0;
fVstRect.left = 0; fVstRect.left = 0;
#ifdef CARLA_OS_LINUX
fVstRect.bottom = 712;
fVstRect.right = 1024;
#else
fVstRect.bottom = ui_launcher_res::carla_uiHeight; fVstRect.bottom = ui_launcher_res::carla_uiHeight;
fVstRect.right = ui_launcher_res::carla_uiWidth; fVstRect.right = ui_launcher_res::carla_uiWidth;
#endif


init(); init();
} }
@@ -288,8 +295,23 @@ public:
case effEditOpen: case effEditOpen:
if (fDescriptor->ui_show != nullptr) if (fDescriptor->ui_show != nullptr)
{ {
#ifdef CARLA_OS_LINUX
char strBuf[0xff+1];
std::snprintf(strBuf, 0xff, P_INTPTR, (intptr_t)ptr);
strBuf[0xff] = '\0';

// set CARLA_PLUGIN_EMBED_WINID for external process
carla_setenv("CARLA_PLUGIN_EMBED_WINID", strBuf);

// show UI now
fDescriptor->ui_show(fHandle, true);

// reset CARLA_PLUGIN_EMBED_WINID just in case
carla_setenv("CARLA_PLUGIN_EMBED_WINID", "0");
#else
destoryUILauncher(fUiLauncher); destoryUILauncher(fUiLauncher);
fUiLauncher = createUILauncher((intptr_t)ptr, fDescriptor, fHandle); fUiLauncher = createUILauncher((intptr_t)ptr, fDescriptor, fHandle);
#endif
ret = 1; ret = 1;
} }
break; break;
@@ -297,20 +319,23 @@ public:
case effEditClose: case effEditClose:
if (fDescriptor->ui_show != nullptr) if (fDescriptor->ui_show != nullptr)
{ {
#ifdef CARLA_OS_LINUX
fDescriptor->ui_show(fHandle, false);
#else
destoryUILauncher(fUiLauncher); destoryUILauncher(fUiLauncher);
fUiLauncher = nullptr; fUiLauncher = nullptr;
#endif
ret = 1; ret = 1;
} }
break; break;


case effEditIdle: case effEditIdle:
#ifndef CARLA_OS_LINUX
if (fUiLauncher != nullptr) if (fUiLauncher != nullptr)
{
idleUILauncher(fUiLauncher); idleUILauncher(fUiLauncher);

if (fDescriptor->ui_idle != nullptr)
fDescriptor->ui_idle(fHandle);
}
#endif
if (fDescriptor->ui_idle != nullptr)
fDescriptor->ui_idle(fHandle);
break; break;


case effGetChunk: case effGetChunk:
@@ -604,8 +629,10 @@ private:
NativeTimeInfo fTimeInfo; NativeTimeInfo fTimeInfo;
ERect fVstRect; ERect fVstRect;


#ifndef CARLA_OS_LINUX
// UI button // UI button
CarlaUILauncher* fUiLauncher; CarlaUILauncher* fUiLauncher;
#endif


// Host data // Host data
enum HostType { enum HostType {


+ 8
- 2
source/plugin/carla-vst.hpp View File

@@ -1,6 +1,6 @@
/* /*
* Carla Native Plugins * Carla Native Plugins
* Copyright (C) 2013-2018 Filipe Coelho <falktx@falktx.com>
* Copyright (C) 2013-2019 Filipe Coelho <falktx@falktx.com>
* *
* This program is free software; you can redistribute it and/or * This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License as * modify it under the terms of the GNU General Public License as
@@ -15,11 +15,15 @@
* For a full copy of the GNU General Public License see the doc/GPL.txt file. * For a full copy of the GNU General Public License see the doc/GPL.txt file.
*/ */


#include "CarlaDefines.h"
#include "CarlaNative.h" #include "CarlaNative.h"
#include "vestige/vestige.h" #include "vestige/vestige.h"
#include "ui_launcher_res.hpp"


#ifndef CARLA_OS_LINUX
# include "ui_launcher_res.hpp"
struct CarlaUILauncher; struct CarlaUILauncher;
#endif

class NativePlugin; class NativePlugin;


struct VstObject { struct VstObject {
@@ -27,11 +31,13 @@ struct VstObject {
NativePlugin* plugin; NativePlugin* plugin;
}; };


#ifndef CARLA_OS_LINUX
CarlaUILauncher* createUILauncher(const intptr_t winId, CarlaUILauncher* createUILauncher(const intptr_t winId,
const NativePluginDescriptor* const d, const NativePluginDescriptor* const d,
const NativePluginHandle h); const NativePluginHandle h);
void idleUILauncher(CarlaUILauncher* const ui); void idleUILauncher(CarlaUILauncher* const ui);
void destoryUILauncher(CarlaUILauncher* const ui); void destoryUILauncher(CarlaUILauncher* const ui);
#endif


const AEffect* VSTPluginMainInit(AEffect* const effect); const AEffect* VSTPluginMainInit(AEffect* const effect);
intptr_t VSTAudioMaster(AEffect*, int32_t, int32_t, intptr_t, void*, float); intptr_t VSTAudioMaster(AEffect*, int32_t, int32_t, intptr_t, void*, float);


Loading…
Cancel
Save