Browse Source

Update dpf, many fixes

master
falkTX 3 days ago
parent
commit
2fcf0634b0
45 changed files with 573 additions and 203 deletions
  1. +6
    -5
      dpf/README.md
  2. +11
    -0
      dpf/cmake/DPF-plugin.cmake
  3. +0
    -1
      dpf/dgl/Application.hpp
  4. +1
    -0
      dpf/dgl/NanoVG.hpp
  5. +19
    -5
      dpf/dgl/StandaloneWindow.hpp
  6. +18
    -3
      dpf/dgl/Window.hpp
  7. +0
    -2
      dpf/dgl/src/Application.cpp
  8. +0
    -2
      dpf/dgl/src/ApplicationPrivateData.cpp
  9. +12
    -8
      dpf/dgl/src/ImageBaseWidgets.cpp
  10. +26
    -3
      dpf/dgl/src/Window.cpp
  11. +58
    -14
      dpf/dgl/src/WindowPrivateData.cpp
  12. +3
    -0
      dpf/dgl/src/WindowPrivateData.hpp
  13. +73
    -13
      dpf/dgl/src/pugl.cpp
  14. +11
    -3
      dpf/dgl/src/pugl.hpp
  15. +1
    -1
      dpf/dgl/src/sofd/libsofd.c
  16. +11
    -2
      dpf/distrho/DistrhoUI.hpp
  17. +23
    -0
      dpf/distrho/DistrhoUI_macOS.mm
  18. +21
    -6
      dpf/distrho/extra/ExternalWindow.hpp
  19. +12
    -3
      dpf/distrho/src/DistrhoPluginLV2.cpp
  20. +116
    -6
      dpf/distrho/src/DistrhoUI.cpp
  21. +3
    -3
      dpf/distrho/src/DistrhoUIInternal.hpp
  22. +7
    -2
      dpf/distrho/src/DistrhoUIPrivateData.hpp
  23. +14
    -0
      dpf/tests/Demo.cpp
  24. +5
    -2
      dpf/tests/FileBrowserDialog.cpp
  25. +7
    -4
      dpf/tests/NanoSubWidgets.cpp
  26. +1
    -0
      dpf/tests/widgets/ExampleColorWidget.hpp
  27. +20
    -55
      dpf/tests/widgets/ExampleImagesWidget.hpp
  28. +32
    -16
      dpf/tests/widgets/ExampleRectanglesWidget.hpp
  29. +32
    -16
      dpf/tests/widgets/ExampleShapesWidget.hpp
  30. +4
    -0
      dpf/tests/widgets/ExampleTextWidget.hpp
  31. +1
    -1
      dpf/utils/generate-vst-bundles.sh
  32. +2
    -2
      dpf/utils/plugin.vst/Contents/Info.plist
  33. +7
    -1
      get-plugins.sh
  34. +1
    -1
      plugins/3BandEQ/Makefile
  35. +1
    -1
      plugins/3BandSplitter/Makefile
  36. +1
    -1
      plugins/AmplitudeImposer/Makefile
  37. +1
    -1
      plugins/CycleShifter/Makefile
  38. +1
    -9
      plugins/Kars/Makefile
  39. +1
    -4
      plugins/MVerb/Makefile
  40. +5
    -0
      plugins/Nekobi/DistrhoUINekobi.cpp
  41. +2
    -1
      plugins/Nekobi/DistrhoUINekobi.hpp
  42. +1
    -1
      plugins/Nekobi/Makefile
  43. +1
    -1
      plugins/PingPongPan/Makefile
  44. +1
    -1
      plugins/SoulForce/Makefile
  45. +0
    -3
      plugins/glBars/Makefile

+ 6
- 5
dpf/README.md View File

@@ -1,5 +1,7 @@
# DPF - DISTRHO Plugin Framework
[![Build Status](https://travis-ci.org/DISTRHO/DPF.png)](https://travis-ci.org/DISTRHO/DPF)
[![makefile](https://github.com/DISTRHO/DPF/actions/workflows/makefile.yml/badge.svg)](https://github.com/DISTRHO/DPF/actions/workflows/makefile.yml)
[![cmake](https://github.com/DISTRHO/DPF/actions/workflows/cmake.yml/badge.svg)](https://github.com/DISTRHO/DPF/actions/workflows/cmake.yml)
[![example-plugins](https://github.com/DISTRHO/DPF/actions/workflows/example-plugins.yml/badge.svg)](https://github.com/DISTRHO/DPF/actions/workflows/example-plugins.yml)

DPF is designed to make development of new plugins an easy and enjoyable task.<br/>
It allows developers to create plugins with custom UIs using a simple C++ API.<br/>
@@ -23,7 +25,7 @@ Bug reports happen on the [DPF github project](https://github.com/DISTRHO/DPF/is

Online documentation is available at [https://distrho.github.io/DPF/](https://distrho.github.io/DPF/).

Online help and discussion about DPF happens in the [KXStudio chat DPF room](https://chat.kx.studio/channel/dpf).
Online help and discussion about DPF happens in the [kx.studio chat, DPF room](https://chat.kx.studio/).


## List of plugins made with DPF:
@@ -59,7 +61,6 @@ Online help and discussion about DPF happens in the [KXStudio chat DPF room](htt
- [Shiro Plugins](https://github.com/ninodewit/SHIRO-Plugins/)
- [Shiru Plugins](https://github.com/linuxmao-org/shiru-plugins)

Checking the [github "DPF" tag](https://github.com/topics/dpf) can potentially brings up other DPF-made plugins.
Checking the [github "DPF" tag](https://github.com/topics/dpf) can potentially bring up other DPF-made plugins.

Plugin examples are available in the `example/` folder inside this repo.<br/>
Extra OpenGL UI examples are available [here](https://github.com/DISTRHO/gl-examples).
Plugin examples are available in the `example/` folder inside this repo.

+ 11
- 0
dpf/cmake/DPF-plugin.cmake View File

@@ -317,6 +317,17 @@ function(dpf__build_vst2 NAME DGL_LIBRARY)
ARCHIVE_OUTPUT_DIRECTORY "${PROJECT_BINARY_DIR}/obj/vst2/$<0:>"
OUTPUT_NAME "${NAME}-vst2"
PREFIX "")
if(APPLE)
set_target_properties("${NAME}-vst2" PROPERTIES
LIBRARY_OUTPUT_DIRECTORY "${PROJECT_BINARY_DIR}/bin/${NAME}.vst/Contents/MacOS/$<0:>"
OUTPUT_NAME "${NAME}"
SUFFIX "")
set(INFO_PLIST_PROJECT_NAME "${NAME}")
configure_file("${DPF_ROOT_DIR}/utils/plugin.vst/Contents/Info.plist"
"${PROJECT_BINARY_DIR}/bin/${NAME}.vst/Contents/Info.plist" @ONLY)
file(COPY "${DPF_ROOT_DIR}/utils/plugin.vst/Contents/PkgInfo"
DESTINATION "${PROJECT_BINARY_DIR}/bin/${NAME}.vst/Contents")
endif()
endfunction()

# dpf__add_dgl_cairo


+ 0
- 1
dpf/dgl/Application.hpp View File

@@ -64,7 +64,6 @@ public:
Quit the application.
This stops the event-loop and closes all Windows.
This function is thread-safe.
@note This function is meant for standalones only, *never* call this from plugins.
*/
void quit();



+ 1
- 0
dpf/dgl/NanoVG.hpp View File

@@ -923,6 +923,7 @@ private:
*/
inline void onDisplay() override
{
// NOTE maybe should use BaseWidget::getWindow().getScaleFactor() as 3rd arg ?
NanoVG::beginFrame(BaseWidget::getWidth(), BaseWidget::getHeight());
onNanoDisplay();
NanoVG::endFrame();


+ 19
- 5
dpf/dgl/StandaloneWindow.hpp View File

@@ -33,14 +33,25 @@ public:
*/
StandaloneWindow(Application& app)
: Window(app),
TopLevelWidget((Window&)*this) {}
TopLevelWidget((Window&)*this),
sgc((Window&)*this) {}

/**
Constructor with parent window, typically used to run as modal.
Constructor with a transient parent window, typically used to run as modal.
*/
StandaloneWindow(Application& app, Window& parentWindow)
: Window(app, parentWindow),
TopLevelWidget((Window&)*this) {}
StandaloneWindow(Application& app, Window& transientParentWindow)
: Window(app, transientParentWindow),
TopLevelWidget((Window&)*this),
sgc((Window&)*this, transientParentWindow) {}

/**
Clear current graphics context.
Must be called at the end of your StandaloneWindow constructor.
*/
void done()
{
sgc.done();
}

/**
Overloaded functions to ensure they apply to the Window class.
@@ -66,6 +77,9 @@ public:
bool keepAspectRatio = false, bool automaticallyScale = false)
{ Window::setGeometryConstraints(minimumWidth, minimumHeight, keepAspectRatio, automaticallyScale); }

private:
ScopedGraphicsContext sgc;

DISTRHO_DECLARE_NON_COPYABLE_WITH_LEAK_DETECTOR(StandaloneWindow)
};



+ 18
- 3
dpf/dgl/Window.hpp View File

@@ -49,6 +49,8 @@ class TopLevelWidget;
*/
class Window
{
struct PrivateData;

public:
#ifndef DGL_FILE_BROWSER_DISABLED
/**
@@ -59,6 +61,7 @@ public:
/**
File browser button state.
This allows to customize the behaviour of the file browse dialog buttons.
Note these are merely hints, not all systems support them.
*/
enum ButtonState {
kButtonInvisible,
@@ -87,7 +90,7 @@ public:
Buttons()
: listAllFiles(kButtonVisibleChecked),
showHidden(kButtonVisibleUnchecked),
showPlaces(kButtonVisibleUnchecked) {}
showPlaces(kButtonVisibleChecked) {}
} buttons;

/** Constructor for default values */
@@ -113,7 +116,7 @@ public:
Window win(app);
ScopedPointer<MyCustomTopLevelWidget> widget;
{
const ScopedGraphicsContext sgc(win);
const Window::ScopedGraphicsContext sgc(win);
widget = new MyCustomTopLevelWidget(win);
}
app.exec();
@@ -127,12 +130,25 @@ public:
*/
struct ScopedGraphicsContext
{
/** Constructor that will make the @a window graphics context the current one */
explicit ScopedGraphicsContext(Window& window);

/** Overloaded constructor, gives back context to its transient parent when done */
explicit ScopedGraphicsContext(Window& window, Window& transientParentWindow);

/** Desstructor for clearing current context, if not done yet */
~ScopedGraphicsContext();

/** Early context clearing, useful for standalone windows not created by you. */
void done();

DISTRHO_DECLARE_NON_COPYABLE(ScopedGraphicsContext)
DISTRHO_PREVENT_HEAP_ALLOCATION

private:
Window& window;
Window::PrivateData* ppData;
bool active;
};

/**
@@ -441,7 +457,6 @@ protected:
#endif

private:
struct PrivateData;
PrivateData* const pData;
friend class Application;
friend class PluginWindow;


+ 0
- 2
dpf/dgl/src/Application.cpp View File

@@ -43,8 +43,6 @@ void Application::exec(const uint idleTimeInMs)

void Application::quit()
{
DISTRHO_SAFE_ASSERT_RETURN(pData->isStandalone,);

pData->quit();
}



+ 0
- 2
dpf/dgl/src/ApplicationPrivateData.cpp View File

@@ -127,8 +127,6 @@ void Application::PrivateData::idle(const uint timeoutInMs)

void Application::PrivateData::quit()
{
DISTRHO_SAFE_ASSERT_RETURN(isStandalone,);

if (! isThisTheMainThread(mainThreadHandle))
{
if (! isQuittingInNextCycle)


+ 12
- 8
dpf/dgl/src/ImageBaseWidgets.cpp View File

@@ -29,11 +29,13 @@ ImageBaseAboutWindow<ImageType>::ImageBaseAboutWindow(Window& parentWindow, cons
setResizable(false);
setTitle("About");

if (image.isInvalid())
return;
if (image.isValid())
{
setSize(image.getSize());
setGeometryConstraints(image.getWidth(), image.getHeight(), true, true);
}

setSize(image.getSize());
setGeometryConstraints(image.getWidth(), image.getHeight(), true, true);
done();
}

template <class ImageType>
@@ -44,11 +46,13 @@ ImageBaseAboutWindow<ImageType>::ImageBaseAboutWindow(TopLevelWidget* const pare
setResizable(false);
setTitle("About");

if (image.isInvalid())
return;
if (image.isValid())
{
setSize(image.getSize());
setGeometryConstraints(image.getWidth(), image.getHeight(), true, true);
}

setSize(image.getSize());
setGeometryConstraints(image.getWidth(), image.getHeight(), true, true);
done();
}

template <class ImageType>


+ 26
- 3
dpf/dgl/src/Window.cpp View File

@@ -24,14 +24,37 @@ START_NAMESPACE_DGL
// ScopedGraphicsContext

Window::ScopedGraphicsContext::ScopedGraphicsContext(Window& win)
: window(win)
: window(win),
ppData(nullptr),
active(puglBackendEnter(window.pData->view)) {}

Window::ScopedGraphicsContext::ScopedGraphicsContext(Window& win, Window& transientWin)
: window(win),
ppData(transientWin.pData),
active(false)
{
puglBackendEnter(window.pData->view);
puglBackendLeave(ppData->view);
active = puglBackendEnter(window.pData->view);
}

Window::ScopedGraphicsContext::~ScopedGraphicsContext()
{
puglBackendLeave(window.pData->view);
done();
}

void Window::ScopedGraphicsContext::done()
{
if (active)
{
puglBackendLeave(window.pData->view);
active = false;
}

if (ppData != nullptr)
{
puglBackendEnter(ppData->view);
ppData = nullptr;
}
}

// -----------------------------------------------------------------------


+ 58
- 14
dpf/dgl/src/WindowPrivateData.cpp View File

@@ -94,6 +94,7 @@ Window::PrivateData::PrivateData(Application& a, Window* const s)
minWidth(0),
minHeight(0),
keepAspectRatio(false),
ignoreIdleCallbacks(false),
#ifdef DISTRHO_OS_WINDOWS
win32SelectedFile(nullptr),
#endif
@@ -118,12 +119,12 @@ Window::PrivateData::PrivateData(Application& a, Window* const s, PrivateData* c
minWidth(0),
minHeight(0),
keepAspectRatio(false),
ignoreIdleCallbacks(false),
#ifdef DISTRHO_OS_WINDOWS
win32SelectedFile(nullptr),
#endif
modal(ppData)
{
puglBackendLeave(transientParentView);
puglSetTransientFor(view, puglGetNativeWindow(transientParentView));

initPre(DEFAULT_WIDTH, DEFAULT_HEIGHT, false);
@@ -147,6 +148,7 @@ Window::PrivateData::PrivateData(Application& a, Window* const s,
minWidth(0),
minHeight(0),
keepAspectRatio(false),
ignoreIdleCallbacks(false),
#ifdef DISTRHO_OS_WINDOWS
win32SelectedFile(nullptr),
#endif
@@ -177,6 +179,7 @@ Window::PrivateData::PrivateData(Application& a, Window* const s,
minWidth(0),
minHeight(0),
keepAspectRatio(false),
ignoreIdleCallbacks(false),
#ifdef DISTRHO_OS_WINDOWS
win32SelectedFile(nullptr),
#endif
@@ -266,10 +269,6 @@ bool Window::PrivateData::initPost()
puglShow(view);
}

// give context back to transient parent window
if (transientParentView != nullptr)
puglBackendEnter(transientParentView);

return true;
}

@@ -317,8 +316,10 @@ void Window::PrivateData::show()
PuglRect rect = puglGetFrame(view);
puglSetWindowSize(view, static_cast<uint>(rect.width), static_cast<uint>(rect.height));

#ifdef DISTRHO_OS_WINDOWS
puglWin32ShowWindowCentered(view);
#if defined(DISTRHO_OS_WINDOWS)
puglWin32ShowCentered(view);
#elif defined(DISTRHO_OS_MAC)
puglMacOSShowCentered(view);
#else
puglShow(view);
#endif
@@ -419,6 +420,9 @@ void Window::PrivateData::idleCallback()

bool Window::PrivateData::addIdleCallback(IdleCallback* const callback, const uint timerFrequencyInMs)
{
if (ignoreIdleCallbacks)
return false;

if (timerFrequencyInMs == 0)
{
appData->idleCallbacks.push_back(callback);
@@ -430,6 +434,9 @@ bool Window::PrivateData::addIdleCallback(IdleCallback* const callback, const ui

bool Window::PrivateData::removeIdleCallback(IdleCallback* const callback)
{
if (ignoreIdleCallbacks)
return false;

if (std::find(appData->idleCallbacks.begin(),
appData->idleCallbacks.end(), callback) != appData->idleCallbacks.end())
{
@@ -459,19 +466,19 @@ bool Window::PrivateData::openFileBrowser(const Window::FileBrowserOptions& opti
if (startDir.isEmpty())
{
// TESTING verify this whole thing...
#ifdef DISTRHO_OS_WINDOWS
# ifdef DISTRHO_OS_WINDOWS
if (char* const cwd = _getcwd(nullptr, 0))
{
startDir = cwd;
std::free(cwd);
}
#else
# else
if (char* const cwd = getcwd(nullptr, 0))
{
startDir = cwd;
std::free(cwd);
}
#endif
# endif
}

DISTRHO_SAFE_ASSERT_RETURN(startDir.isNotEmpty(), false);
@@ -497,7 +504,22 @@ bool Window::PrivateData::openFileBrowser(const Window::FileBrowserOptions& opti

# ifdef DISTRHO_OS_MAC
uint flags = 0x0;
// TODO flags

if (options.buttons.listAllFiles == FileBrowserOptions::kButtonVisibleChecked)
flags |= 0x001;
else if (options.buttons.listAllFiles == FileBrowserOptions::kButtonVisibleUnchecked)
flags |= 0x002;

if (options.buttons.showHidden == FileBrowserOptions::kButtonVisibleChecked)
flags |= 0x010;
else if (options.buttons.showHidden == FileBrowserOptions::kButtonVisibleUnchecked)
flags |= 0x020;

if (options.buttons.showPlaces == FileBrowserOptions::kButtonVisibleChecked)
flags |= 0x100;
else if (options.buttons.showPlaces == FileBrowserOptions::kButtonVisibleUnchecked)
flags |= 0x200;

return puglMacOSFilePanelOpen(view, startDir, title, flags, openPanelCallback);
# endif

@@ -529,6 +551,13 @@ bool Window::PrivateData::openFileBrowser(const Window::FileBrowserOptions& opti
ofn.lpstrFile = fileNameW.data();
ofn.nMaxFile = (DWORD)fileNameW.size();

// flags
ofn.Flags = OFN_PATHMUSTEXIST;
if (options.buttons.showHidden == FileBrowserOptions::kButtonVisibleChecked)
ofn.Flags |= OFN_FORCESHOWHIDDEN;
if (options.buttons.showPlaces == FileBrowserOptions::kButtonInvisible)
ofn.FlagsEx |= OFN_EX_NOPLACESBAR;

// TODO synchronous only, can't do better with WinAPI native dialogs.
// threading might work, if someone is motivated to risk it.
if (GetOpenFileNameW(&ofn))
@@ -552,7 +581,22 @@ bool Window::PrivateData::openFileBrowser(const Window::FileBrowserOptions& opti

# ifdef HAVE_X11
uint flags = 0x0;
// TODO flags

if (options.buttons.listAllFiles == FileBrowserOptions::kButtonVisibleChecked)
flags |= 0x001;
else if (options.buttons.listAllFiles == FileBrowserOptions::kButtonVisibleUnchecked)
flags |= 0x002;

if (options.buttons.showHidden == FileBrowserOptions::kButtonVisibleChecked)
flags |= 0x010;
else if (options.buttons.showHidden == FileBrowserOptions::kButtonVisibleUnchecked)
flags |= 0x020;

if (options.buttons.showPlaces == FileBrowserOptions::kButtonVisibleChecked)
flags |= 0x100;
else if (options.buttons.showPlaces == FileBrowserOptions::kButtonVisibleUnchecked)
flags |= 0x200;

return sofdFileDialogShow(view, startDir, title, flags, autoScaling ? autoScaleFactor : scaleFactor);
# endif

@@ -872,9 +916,9 @@ PuglStatus Window::PrivateData::puglEventCallback(PuglView* const view, const Pu

///< View created, a #PuglEventCreate
case PUGL_CREATE:
#ifdef DGL_PUGL_USING_X11
#ifdef HAVE_X11
if (! pData->isEmbed)
puglExtraSetWindowTypeAndPID(view);
puglX11SetWindowTypeAndPID(view);
#endif
break;



+ 3
- 0
dpf/dgl/src/WindowPrivateData.hpp View File

@@ -74,6 +74,9 @@ struct Window::PrivateData : IdleCallback {
uint minWidth, minHeight;
bool keepAspectRatio;

/** Whether to ignore idle callback requests, useful for temporary windows. */
bool ignoreIdleCallbacks;

#ifdef DISTRHO_OS_WINDOWS
/** Selected file for openFileBrowser on windows, stored for fake async operation. */
const char* win32SelectedFile;


+ 73
- 13
dpf/dgl/src/pugl.cpp View File

@@ -159,9 +159,9 @@ START_NAMESPACE_DGL
// --------------------------------------------------------------------------------------------------------------------
// expose backend enter

void puglBackendEnter(PuglView* const view)
bool puglBackendEnter(PuglView* const view)
{
view->backend->enter(view, NULL);
return view->backend->enter(view, NULL) == PUGL_SUCCESS;
}

// --------------------------------------------------------------------------------------------------------------------
@@ -213,10 +213,17 @@ double puglGetDesktopScaleFactor(const PuglView* const view)
typedef HRESULT(WINAPI* PFN_GetProcessDpiAwareness)(HANDLE, DWORD*);
typedef HRESULT(WINAPI* PFN_GetScaleFactorForMonitor)(HMONITOR, DWORD*);

# if defined(__GNUC__) && (__GNUC__ >= 9)
# pragma GCC diagnostic push
# pragma GCC diagnostic ignored "-Wcast-function-type"
# endif
const PFN_GetProcessDpiAwareness GetProcessDpiAwareness
= (PFN_GetProcessDpiAwareness)GetProcAddress(Shcore, "GetProcessDpiAwareness");
const PFN_GetScaleFactorForMonitor GetScaleFactorForMonitor
= (PFN_GetScaleFactorForMonitor)GetProcAddress(Shcore, "GetScaleFactorForMonitor");
# if defined(__GNUC__) && (__GNUC__ >= 9)
# pragma GCC diagnostic pop
# endif

DWORD dpiAware = 0;
if (GetProcessDpiAwareness && GetScaleFactorForMonitor
@@ -494,6 +501,33 @@ puglMacOSRemoveChildWindow(PuglView* const view, PuglView* const child)
return PUGL_FAILURE;
}

// --------------------------------------------------------------------------------------------------------------------
// macOS specific, center view based on parent coordinates (if there is one)

void puglMacOSShowCentered(PuglView* const view)
{
if (puglShow(view) != PUGL_SUCCESS)
return;

if (view->transientParent != 0)
{
NSWindow* const transientWindow = [(NSView*)view->transientParent window];
DISTRHO_SAFE_ASSERT_RETURN(transientWindow != nullptr,);

const NSRect ourFrame = [view->impl->window frame];
const NSRect transientFrame = [transientWindow frame];

const int x = transientFrame.origin.x + transientFrame.size.width / 2 - ourFrame.size.width / 2;
const int y = transientFrame.origin.y + transientFrame.size.height / 2 + ourFrame.size.height / 2;

[view->impl->window setFrameTopLeftPoint:NSMakePoint(x, y)];
}
else
{
[view->impl->window center];
}
}

// --------------------------------------------------------------------------------------------------------------------
// macOS specific, setup file browser dialog

@@ -505,13 +539,18 @@ bool puglMacOSFilePanelOpen(PuglView* const view,

NSOpenPanel* const panel = [NSOpenPanel openPanel];

// TODO flags
[panel setAllowsMultipleSelection:NO];
[panel setCanChooseFiles:YES];
[panel setCanChooseDirectories:NO];
[panel setAllowsMultipleSelection:NO];

[panel setDirectoryURL:[NSURL fileURLWithPath:[NSString stringWithUTF8String:startDir]]];

// TODO file filter using allowedContentTypes: [UTType]

if (flags & 0x001)
[panel setAllowsOtherFileTypes:YES];
if (flags & 0x010)
[panel setShowsHiddenFiles:YES];

NSString* titleString = [[NSString alloc]
initWithBytes:title
length:strlen(title)
@@ -552,7 +591,7 @@ void puglWin32RestoreWindow(PuglView* const view)
// --------------------------------------------------------------------------------------------------------------------
// win32 specific, center view based on parent coordinates (if there is one)

void puglWin32ShowWindowCentered(PuglView* const view)
void puglWin32ShowCentered(PuglView* const view)
{
PuglInternals* impl = view->impl;
DISTRHO_SAFE_ASSERT_RETURN(impl->hwnd != nullptr,);
@@ -596,9 +635,9 @@ void puglWin32SetWindowResizable(PuglView* const view, const bool resizable)
// --------------------------------------------------------------------------------------------------------------------
// X11 specific, safer way to grab focus

PuglStatus puglX11GrabFocus(PuglView* const view)
PuglStatus puglX11GrabFocus(const PuglView* const view)
{
PuglInternals* const impl = view->impl;
const PuglInternals* const impl = view->impl;

XWindowAttributes wa;
std::memset(&wa, 0, sizeof(wa));
@@ -615,6 +654,29 @@ PuglStatus puglX11GrabFocus(PuglView* const view)
return PUGL_SUCCESS;
}

// --------------------------------------------------------------------------------------------------------------------
// X11 specific, set dialog window type and pid hints

void puglX11SetWindowTypeAndPID(const PuglView* const view)
{
const PuglInternals* const impl = view->impl;

const pid_t pid = getpid();
const Atom _nwp = XInternAtom(impl->display, "_NET_WM_PID", False);
XChangeProperty(impl->display, impl->win, _nwp, XA_CARDINAL, 32, PropModeReplace, (const uchar*)&pid, 1);

const Atom _wt = XInternAtom(impl->display, "_NET_WM_WINDOW_TYPE", False);

// Setting the window to both dialog and normal will produce a decorated floating dialog
// Order is important: DIALOG needs to come before NORMAL
const Atom _wts[2] = {
XInternAtom(impl->display, "_NET_WM_WINDOW_TYPE_DIALOG", False),
XInternAtom(impl->display, "_NET_WM_WINDOW_TYPE_NORMAL", False)
};

XChangeProperty(impl->display, impl->win, _wt, XA_ATOM, 32, PropModeReplace, (const uchar*)&_wts, 2);
}

// --------------------------------------------------------------------------------------------------------------------
// X11 specific stuff for sofd

@@ -637,11 +699,9 @@ bool sofdFileDialogShow(PuglView* const view,
DISTRHO_SAFE_ASSERT_RETURN(x_fib_configure(0, startDir) == 0, false);
DISTRHO_SAFE_ASSERT_RETURN(x_fib_configure(1, title) == 0, false);

/*
x_fib_cfg_buttons(3, options.buttons.listAllFiles-1);
x_fib_cfg_buttons(1, options.buttons.showHidden-1);
x_fib_cfg_buttons(2, options.buttons.showPlaces-1);
*/
x_fib_cfg_buttons(3, flags & 0x001 ? 1 : flags & 0x002 ? 0 : -1);
x_fib_cfg_buttons(1, flags & 0x010 ? 1 : flags & 0x020 ? 0 : -1);
x_fib_cfg_buttons(2, flags & 0x100 ? 1 : flags & 0x200 ? 0 : -1);

return (x_fib_show(sofd_display, view->impl->win, 0, 0, scaleFactor + 0.5) == 0);
}


+ 11
- 3
dpf/dgl/src/pugl.hpp View File

@@ -48,7 +48,7 @@ USE_NAMESPACE_DGL
PUGL_BEGIN_DECLS

// expose backend enter
PUGL_API void
PUGL_API bool
puglBackendEnter(PuglView* view);

// expose backend leave
@@ -108,6 +108,10 @@ puglMacOSAddChildWindow(PuglView* view, PuglView* child);
PUGL_API PuglStatus
puglMacOSRemoveChildWindow(PuglView* view, PuglView* child);

// macOS specific, center view based on parent coordinates (if there is one)
PUGL_API void
puglMacOSShowCentered(PuglView* view);

// macOS specific, setup file browser dialog
typedef void (*openPanelCallback)(PuglView* view, const char* path);
bool puglMacOSFilePanelOpen(PuglView* view, const char* startDir, const char* title, uint flags, openPanelCallback callback);
@@ -120,7 +124,7 @@ puglWin32RestoreWindow(PuglView* view);

// win32 specific, center view based on parent coordinates (if there is one)
PUGL_API void
puglWin32ShowWindowCentered(PuglView* view);
puglWin32ShowCentered(PuglView* view);

// win32 specific, set or unset WS_SIZEBOX style flag
PUGL_API void
@@ -130,7 +134,11 @@ puglWin32SetWindowResizable(PuglView* view, bool resizable);
#ifdef HAVE_X11
// X11 specific, safer way to grab focus
PUGL_API PuglStatus
puglX11GrabFocus(PuglView* view);
puglX11GrabFocus(const PuglView* view);

// X11 specific, set dialog window type and pid hints
PUGL_API void
puglX11SetWindowTypeAndPID(const PuglView* view);

// X11 specific, show file dialog via sofd
PUGL_API bool


+ 1
- 1
dpf/dgl/src/sofd/libsofd.c View File

@@ -2072,7 +2072,7 @@ int x_fib_show (Display *dpy, Window parent, int x, int y, double scalefactor) {
sync_button_states () ;

_fib_height = _fib_font_vsep * 15.8 * (1.0 + (scalefactor - 1.0) / 2.0);
_fib_width = MAX (_btn_span, 440 * scalefactor);
_fib_width = MAX (_btn_span, 480 * scalefactor);

XResizeWindow (dpy, _fib_win, _fib_width, _fib_height);



+ 11
- 2
dpf/distrho/DistrhoUI.hpp View File

@@ -303,17 +303,26 @@ protected:
*/
virtual void uiFileBrowserSelected(const char* filename);
# endif
#endif // !DISTRHO_PLUGIN_HAS_EXTERNAL_UI

/* --------------------------------------------------------------------------------------------------------
* UI Resize Handling, internal */

#if DISTRHO_PLUGIN_HAS_EXTERNAL_UI
/**
External Window resize function, called when the window is resized.
This is overriden here so the host knows when the UI is resized by you.
@see ExternalWindow::sizeChanged(uint,uint)
*/
void sizeChanged(uint width, uint height) override;
#else
/**
OpenGL widget resize function, called when the widget is resized.
Widget resize function, called when the widget is resized.
This is overriden here so the host knows when the UI is resized by you.
@see Widget::onResize(const ResizeEvent&)
*/
void onResize(const ResizeEvent& ev) override;
#endif // !DISTRHO_PLUGIN_HAS_EXTERNAL_UI
#endif

// -------------------------------------------------------------------------------------------------------



+ 23
- 0
dpf/distrho/DistrhoUI_macOS.mm View File

@@ -19,6 +19,28 @@
#endif

#include "src/DistrhoPluginChecks.h"
#include "src/DistrhoDefines.h"

#if DISTRHO_PLUGIN_HAS_EXTERNAL_UI
#import <Cocoa/Cocoa.h>
#include <algorithm>
#include <cmath>

START_NAMESPACE_DISTRHO
double getDesktopScaleFactor(const uintptr_t parentWindowHandle)
{
// allow custom scale for testing
if (const char* const scale = getenv("DPF_SCALE_FACTOR"))
return std::max(1.0, std::atof(scale));

if (NSView* const parentView = (NSView*)parentWindowHandle)
if (NSWindow* const parentWindow = [parentView window])
return [parentWindow screen].backingScaleFactor;

return [NSScreen mainScreen].backingScaleFactor;
}
END_NAMESPACE_DISTRHO
#else // DISTRHO_PLUGIN_HAS_EXTERNAL_UI
#include "../dgl/Base.hpp"

#define DISTRHO_MACOS_NAMESPACE_MACRO_HELPER(DGL_NS, SEP, PUGL_NS, INTERFACE) DGL_NS ## SEP ## PUGL_NS ## SEP ## INTERFACE
@@ -33,3 +55,4 @@
#define PuglWrapperView DISTRHO_MACOS_NAMESPACE_MACRO(DGL_NAMESPACE, PUGL_NAMESPACE, WrapperView)

#import "src/pugl.mm"
#endif // DISTRHO_PLUGIN_HAS_EXTERNAL_UI

+ 21
- 6
dpf/distrho/extra/ExternalWindow.hpp View File

@@ -19,9 +19,7 @@

#include "String.hpp"

#ifdef DISTRHO_OS_WINDOWS
# error Unsupported platform!
#else
#ifndef DISTRHO_OS_WINDOWS
# include <cerrno>
# include <signal.h>
# include <sys/wait.h>
@@ -106,9 +104,10 @@ public:
*/
virtual bool isRunning() const
{
#ifndef DISTRHO_OS_WINDOWS
if (ext.inUse)
return ext.isRunning();
#endif
return isVisible();
}

@@ -119,7 +118,11 @@ public:
*/
virtual bool isQuitting() const
{
#ifndef DISTRHO_OS_WINDOWS
return ext.inUse ? ext.isQuitting : pData.isQuitting;
#else
return pData.isQuitting;
#endif
}

/**
@@ -259,9 +262,10 @@ public:
{
pData.isQuitting = true;
hide();
#ifndef DISTRHO_OS_WINDOWS
if (ext.inUse)
terminateAndWaitForExternalProcess();
#endif
}

/**
@@ -293,7 +297,7 @@ public:
{
DISTRHO_SAFE_ASSERT_UINT2_RETURN(width > 1 && height > 1, width, height,);

if (pData.width == width || pData.height == height)
if (pData.width == width && pData.height == height)
return;

pData.width = width;
@@ -357,15 +361,24 @@ protected:

bool startExternalProcess(const char* args[])
{
#ifndef DISTRHO_OS_WINDOWS
ext.inUse = true;

return ext.start(args);
#else
(void)args;
return false; // TODO
#endif
}

void terminateAndWaitForExternalProcess()
{
#ifndef DISTRHO_OS_WINDOWS
ext.isQuitting = true;
ext.terminateAndWait();
#else
// TODO
#endif
}

/* --------------------------------------------------------------------------------------------------------
@@ -414,6 +427,7 @@ private:
friend class PluginWindow;
friend class UI;

#ifndef DISTRHO_OS_WINDOWS
struct ExternalProcess {
bool inUse;
bool isQuitting;
@@ -510,6 +524,7 @@ private:
}
}
} ext;
#endif

struct PrivateData {
uintptr_t parentWindowHandle;


+ 12
- 3
dpf/distrho/src/DistrhoPluginLV2.cpp View File

@@ -85,9 +85,11 @@ public:
fLastControlValues(nullptr),
fSampleRate(sampleRate),
fURIDs(uridMap),
#if DISTRHO_PLUGIN_WANT_PARAMETER_VALUE_CHANGE_REQUEST
fCtrlInPortChangeReq(ctrlInPortChangeReq),
#endif
fUridMap(uridMap),
fWorker(worker),
fCtrlInPortChangeReq(ctrlInPortChangeReq)
fWorker(worker)
{
#if DISTRHO_PLUGIN_NUM_INPUTS > 0
for (uint32_t i=0; i < DISTRHO_PLUGIN_NUM_INPUTS; ++i)
@@ -157,6 +159,11 @@ public:
// unused
(void)fWorker;
#endif

#if ! DISTRHO_PLUGIN_WANT_PARAMETER_VALUE_CHANGE_REQUEST
// unused
(void)ctrlInPortChangeReq;
#endif
}

~PluginLv2()
@@ -1178,9 +1185,11 @@ private:
} fURIDs;

// LV2 features
#if DISTRHO_PLUGIN_WANT_PARAMETER_VALUE_CHANGE_REQUEST
const LV2_ControlInputPort_Change_Request* const fCtrlInPortChangeReq;
#endif
const LV2_URID_Map* const fUridMap;
const LV2_Worker_Schedule* const fWorker;
const LV2_ControlInputPort_Change_Request* const fCtrlInPortChangeReq;

#if DISTRHO_PLUGIN_WANT_STATE
StringToStringMap fStateMap;


+ 116
- 6
dpf/distrho/src/DistrhoUI.cpp View File

@@ -14,21 +14,117 @@
* CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
*/

#include "DistrhoUIPrivateData.hpp"
#include "src/WindowPrivateData.hpp"
#if !DISTRHO_PLUGIN_HAS_EXTERNAL_UI
#include "src/DistrhoPluginChecks.h"

#if DISTRHO_PLUGIN_HAS_EXTERNAL_UI
# if defined(DISTRHO_OS_WINDOWS)
# define WIN32_LEAN_AND_MEAN
# include <windows.h>
# elif defined(HAVE_X11)
# include <X11/Xresource.h>
# endif
#else
# include "src/TopLevelWidgetPrivateData.hpp"
# include "src/WindowPrivateData.hpp"
#endif

#include "DistrhoUIPrivateData.hpp"

START_NAMESPACE_DISTRHO

#if DISTRHO_PLUGIN_HAS_EXTERNAL_UI
/* ------------------------------------------------------------------------------------------------------------
* Static data, see DistrhoUIInternal.hpp */

#if DISTRHO_PLUGIN_HAS_EXTERNAL_UI
uintptr_t g_nextWindowId = 0;
double g_nextScaleFactor = 1.0;
const char* g_nextBundlePath = nullptr;

/* ------------------------------------------------------------------------------------------------------------
* get global scale factor */

#ifdef DISTRHO_OS_MAC
double getDesktopScaleFactor(uintptr_t parentWindowHandle);
#else
static double getDesktopScaleFactor(const uintptr_t parentWindowHandle)
{
// allow custom scale for testing
if (const char* const scale = getenv("DPF_SCALE_FACTOR"))
return std::max(1.0, std::atof(scale));

#if defined(DISTRHO_OS_WINDOWS)
if (const HMODULE Shcore = LoadLibraryA("Shcore.dll"))
{
typedef HRESULT(WINAPI* PFN_GetProcessDpiAwareness)(HANDLE, DWORD*);
typedef HRESULT(WINAPI* PFN_GetScaleFactorForMonitor)(HMONITOR, DWORD*);

# if defined(__GNUC__) && (__GNUC__ >= 9)
# pragma GCC diagnostic push
# pragma GCC diagnostic ignored "-Wcast-function-type"
# endif
const PFN_GetProcessDpiAwareness GetProcessDpiAwareness
= (PFN_GetProcessDpiAwareness)GetProcAddress(Shcore, "GetProcessDpiAwareness");
const PFN_GetScaleFactorForMonitor GetScaleFactorForMonitor
= (PFN_GetScaleFactorForMonitor)GetProcAddress(Shcore, "GetScaleFactorForMonitor");
# if defined(__GNUC__) && (__GNUC__ >= 9)
# pragma GCC diagnostic pop
# endif

DWORD dpiAware = 0;
if (GetProcessDpiAwareness && GetScaleFactorForMonitor
&& GetProcessDpiAwareness(NULL, &dpiAware) == 0 && dpiAware != 0)
{
const HMONITOR hMon = parentWindowHandle != 0
? MonitorFromWindow((HWND)parentWindowHandle, MONITOR_DEFAULTTOPRIMARY)
: MonitorFromPoint(POINT{0,0}, MONITOR_DEFAULTTOPRIMARY);

DWORD scaleFactor = 0;
if (GetScaleFactorForMonitor(hMon, &scaleFactor) == 0 && scaleFactor != 0)
{
FreeLibrary(Shcore);
return static_cast<double>(scaleFactor) / 100.0;
}
}

FreeLibrary(Shcore);
}
#elif defined(HAVE_X11)
::Display* const display = XOpenDisplay(nullptr);
DISTRHO_SAFE_ASSERT_RETURN(display != nullptr, 1.0);

XrmInitialize();

if (char* const rms = XResourceManagerString(display))
{
if (const XrmDatabase sdb = XrmGetStringDatabase(rms))
{
char* type = nullptr;
XrmValue ret;

if (XrmGetResource(sdb, "Xft.dpi", "String", &type, &ret)
&& ret.addr != nullptr
&& type != nullptr
&& std::strncmp("String", type, 6) == 0)
{
if (const double dpi = std::atof(ret.addr))
{
XCloseDisplay(display);
return dpi / 96;
}
}
}
}

XCloseDisplay(display);
#endif

return 1.0;

// might be unused
(void)parentWindowHandle;
}
#endif // !DISTRHO_OS_MAC

#endif

/* ------------------------------------------------------------------------------------------------------------
@@ -50,12 +146,17 @@ UI::PrivateData::createNextWindow(UI* const ui, const uint width, const uint hei
ewData.parentWindowHandle = pData->winId;
ewData.width = width;
ewData.height = height;
ewData.scaleFactor = pData->scaleFactor;
ewData.scaleFactor = pData->scaleFactor != 0.0 ? pData->scaleFactor : getDesktopScaleFactor(pData->winId);
ewData.title = DISTRHO_PLUGIN_NAME;
ewData.isStandalone = DISTRHO_UI_IS_STANDALONE;
return ewData;
#else
pData->window = new PluginWindow(ui, pData->app, pData->winId, width, height, pData->scaleFactor);

// If there are no callbacks, this is most likely a temporary window, so ignore idle callbacks
if (pData->callbacksPtr == nullptr)
pData->window->setIgnoreIdleCallbacks();

return pData->window.getObject();
#endif
}
@@ -209,10 +310,19 @@ void UI::uiFileBrowserSelected(const char*)
{
}
# endif
#endif // !DISTRHO_PLUGIN_HAS_EXTERNAL_UI

/* ------------------------------------------------------------------------------------------------------------
* UI Resize Handling, internal */

#if DISTRHO_PLUGIN_HAS_EXTERNAL_UI
void UI::sizeChanged(const uint width, const uint height)
{
UIWidget::sizeChanged(width, height);

uiData->setSizeCallback(width, height);
}
#else
void UI::onResize(const ResizeEvent& ev)
{
UIWidget::onResize(ev);
@@ -221,7 +331,7 @@ void UI::onResize(const ResizeEvent& ev)
const uint height = ev.size.getHeight();
uiData->setSizeCallback(width, height);
}
#endif // !DISTRHO_PLUGIN_HAS_EXTERNAL_UI
#endif

// -----------------------------------------------------------------------------------------------------------



+ 3
- 3
dpf/distrho/src/DistrhoUIInternal.hpp View File

@@ -91,6 +91,7 @@ public:
g_nextScaleFactor = 0.0;
g_nextBundlePath = nullptr;
#else
// Leave context called in the PluginWindow constructor, see DistrhoUIPrivateData.hpp
uiData->window->leaveContext();
#endif
UI::PrivateData::s_nextPrivateData = nullptr;
@@ -106,6 +107,7 @@ public:

~UIExporter()
{
quit();
delete ui;
delete uiData;
}
@@ -227,9 +229,7 @@ public:
void quit()
{
uiData->window->close();

if (uiData->app.isStandalone())
uiData->app.quit();
uiData->app.quit();
}

// -------------------------------------------------------------------


+ 7
- 2
dpf/distrho/src/DistrhoUIPrivateData.hpp View File

@@ -52,14 +52,14 @@ START_NAMESPACE_DGL
#if DISTRHO_PLUGIN_HAS_EXTERNAL_UI
struct PluginApplication
{
IdleCallback* idleCallback;
DGL_NAMESPACE::IdleCallback* idleCallback;
UI* ui;

explicit PluginApplication()
: idleCallback(nullptr),
ui(nullptr) {}

void addIdleCallback(IdleCallback* const cb)
void addIdleCallback(DGL_NAMESPACE::IdleCallback* const cb)
{
DISTRHO_SAFE_ASSERT_RETURN(cb != nullptr,);
DISTRHO_SAFE_ASSERT_RETURN(idleCallback == nullptr,);
@@ -187,6 +187,11 @@ public:
puglBackendLeave(pData->view);
}

void setIgnoreIdleCallbacks(const bool ignore = true)
{
pData->ignoreIdleCallbacks = ignore;
}

protected:
void onFocus(const bool focus, const DGL_NAMESPACE::CrossingMode mode) override
{


+ 14
- 0
dpf/tests/Demo.cpp View File

@@ -42,6 +42,19 @@ typedef DGL_NAMESPACE::VulkanImage DemoImage;

START_NAMESPACE_DGL

// Partial specialization is not allowed in C++, so we need to define these here
template<> inline
ExampleImagesWidget<SubWidget, DemoImage>::ExampleImagesWidget(Widget* const parentWidget)
: SubWidget(parentWidget) { init(parentWidget->getApp()); }

template<> inline
ExampleImagesWidget<TopLevelWidget, DemoImage>::ExampleImagesWidget(Window& windowToMapTo)
: TopLevelWidget(windowToMapTo) { init(windowToMapTo.getApp()); }

template<>
ExampleImagesWidget<StandaloneWindow, DemoImage>::ExampleImagesWidget(Application& app)
: StandaloneWindow(app) { init(app); done(); }

typedef ExampleImagesWidget<SubWidget, DemoImage> ExampleImagesSubWidget;
typedef ExampleImagesWidget<TopLevelWidget, DemoImage> ExampleImagesTopLevelWidget;
typedef ExampleImagesWidget<StandaloneWindow, DemoImage> ExampleImagesStandaloneWindow;
@@ -435,6 +448,7 @@ public:
resizer = new ResizeHandle(this);

curPageChanged(0);
done();
}

protected:


+ 5
- 2
dpf/tests/FileBrowserDialog.cpp View File

@@ -37,6 +37,11 @@ public:
#ifndef DGL_NO_SHARED_RESOURCES
loadSharedResources();
#endif
setResizable(true);
setSize(500, 200);
setGeometryConstraints(500, 200, true);
setTitle("FileBrowserDialog");
done();
}

protected:
@@ -170,8 +175,6 @@ int main()

Application app(true);
NanoFilePicker win(app);
win.setSize(500, 200);
win.setTitle("FileBrowserDialog");
win.show();
app.exec();



+ 7
- 4
dpf/tests/NanoSubWidgets.cpp View File

@@ -127,9 +127,13 @@ class NanoExampleWindow : public Window
{
public:
explicit NanoExampleWindow(Application& app)
: Window(app),
container(*this)
: Window(app)
{
{
const ScopedGraphicsContext sgc(*this);
container = new NanoRectanglesContainer(*this);
}

const uint targetWidth = 400;
const uint targetHeight = 400;
const double scaleFactor = getScaleFactor();
@@ -141,7 +145,7 @@ public:
}

private:
NanoRectanglesContainer container;
ScopedPointer<NanoRectanglesContainer> container;
};

// --------------------------------------------------------------------------------------------------------------------
@@ -154,7 +158,6 @@ int main()

Application app;
NanoExampleWindow win(app);

win.show();
app.exec();



+ 1
- 0
dpf/tests/widgets/ExampleColorWidget.hpp View File

@@ -165,6 +165,7 @@ ExampleColorWidget<StandaloneWindow>::ExampleColorWidget(Application& app)
{
setSize(300, 300);
addIdleCallback(this);
done();
}

typedef ExampleColorWidget<SubWidget> ExampleColorSubWidget;


+ 20
- 55
dpf/tests/widgets/ExampleImagesWidget.hpp View File

@@ -21,8 +21,8 @@
// DGL Stuff

#include "../../dgl/ImageBase.hpp"
#include "../../dgl/StandaloneWindow.hpp"
#include "../../dgl/SubWidget.hpp"
#include "../../dgl/TopLevelWidget.hpp"

// ------------------------------------------------------
// Images
@@ -55,69 +55,34 @@ public:
static constexpr const char* kExampleWidgetName = "Images";

// SubWidget
ExampleImagesWidget(Widget* const parent)
: BaseWidget(parent),
imgTop1st(1),
imgTop2nd(2),
imgTop3rd(3),
img1x(0),
img2x(kImg2max),
img3y(kImg3max),
img1rev(false),
img2rev(true),
img3rev(true),
img1(CatPics::cat1Data, CatPics::cat1Width, CatPics::cat1Height, kImageFormatBGR),
img2(CatPics::cat2Data, CatPics::cat2Width, CatPics::cat2Height, kImageFormatBGR),
img3(CatPics::cat3Data, CatPics::cat3Width, CatPics::cat3Height, kImageFormatBGR)
{
BaseWidget::setSize(500, 400);

parent->getApp().addIdleCallback(this);
}
explicit ExampleImagesWidget(Widget* const parent);

// TopLevelWidget
ExampleImagesWidget(Window& windowToMapTo)
: BaseWidget(windowToMapTo),
imgTop1st(1),
imgTop2nd(2),
imgTop3rd(3),
img1x(0),
img2x(kImg2max),
img3y(kImg3max),
img1rev(false),
img2rev(true),
img3rev(true),
img1(CatPics::cat1Data, CatPics::cat1Width, CatPics::cat1Height, kImageFormatBGR),
img2(CatPics::cat2Data, CatPics::cat2Width, CatPics::cat2Height, kImageFormatBGR),
img3(CatPics::cat3Data, CatPics::cat3Width, CatPics::cat3Height, kImageFormatBGR)
{
BaseWidget::setSize(500, 400);

windowToMapTo.getApp().addIdleCallback(this);
}
explicit ExampleImagesWidget(Window& windowToMapTo);

// StandaloneWindow
ExampleImagesWidget(Application& app)
: BaseWidget(app),
imgTop1st(1),
imgTop2nd(2),
imgTop3rd(3),
img1x(0),
img2x(kImg2max),
img3y(kImg3max),
img1rev(false),
img2rev(true),
img3rev(true),
img1(CatPics::cat1Data, CatPics::cat1Width, CatPics::cat1Height, kImageFormatBGR),
img2(CatPics::cat2Data, CatPics::cat2Width, CatPics::cat2Height, kImageFormatBGR),
img3(CatPics::cat3Data, CatPics::cat3Width, CatPics::cat3Height, kImageFormatBGR)
explicit ExampleImagesWidget(Application& app);

protected:
void init(Application& app)
{
BaseWidget::setSize(500, 400);
imgTop1st = 1;
imgTop2nd = 2;
imgTop3rd = 3;
img1x = 0;
img2x = kImg2max;
img3y = kImg3max;
img1rev = false;
img2rev = true;
img3rev = true;
img1 = BaseImage(CatPics::cat1Data, CatPics::cat1Width, CatPics::cat1Height, kImageFormatBGR);
img2 = BaseImage(CatPics::cat2Data, CatPics::cat2Width, CatPics::cat2Height, kImageFormatBGR);
img3 = BaseImage(CatPics::cat3Data, CatPics::cat3Width, CatPics::cat3Height, kImageFormatBGR);

BaseWidget::setSize(500, 400);
app.addIdleCallback(this);
}

protected:
void idleCallback() noexcept override
{
if (img1rev)


+ 32
- 16
dpf/tests/widgets/ExampleRectanglesWidget.hpp View File

@@ -21,8 +21,8 @@
// DGL Stuff

#include "../../dgl/Color.hpp"
#include "../../dgl/StandaloneWindow.hpp"
#include "../../dgl/SubWidget.hpp"
#include "../../dgl/TopLevelWidget.hpp"

START_NAMESPACE_DGL

@@ -37,23 +37,14 @@ class ExampleRectanglesWidget : public BaseWidget
public:
static constexpr const char* const kExampleWidgetName = "Rectangles";

explicit ExampleRectanglesWidget(Widget* const parentWidget)
: BaseWidget(parentWidget)
{
init();
}
// SubWidget
explicit ExampleRectanglesWidget(Widget* const parent);

explicit ExampleRectanglesWidget(Window& windowToMapTo)
: BaseWidget(windowToMapTo)
{
init();
}
// TopLevelWidget
explicit ExampleRectanglesWidget(Window& windowToMapTo);

explicit ExampleRectanglesWidget(Application& app)
: BaseWidget(app)
{
init();
}
// StandaloneWindow
explicit ExampleRectanglesWidget(Application& app);

void init()
{
@@ -166,6 +157,31 @@ protected:
}
};

// SubWidget
template<> inline
ExampleRectanglesWidget<SubWidget>::ExampleRectanglesWidget(Widget* const parentWidget)
: SubWidget(parentWidget)
{
init();
}

// TopLevelWidget
template<> inline
ExampleRectanglesWidget<TopLevelWidget>::ExampleRectanglesWidget(Window& windowToMapTo)
: TopLevelWidget(windowToMapTo)
{
init();
}

// StandaloneWindow
template<> inline
ExampleRectanglesWidget<StandaloneWindow>::ExampleRectanglesWidget(Application& app)
: StandaloneWindow(app)
{
init();
done();
}

typedef ExampleRectanglesWidget<SubWidget> ExampleRectanglesSubWidget;
typedef ExampleRectanglesWidget<TopLevelWidget> ExampleRectanglesTopLevelWidget;
typedef ExampleRectanglesWidget<StandaloneWindow> ExampleRectanglesStandaloneWindow;


+ 32
- 16
dpf/tests/widgets/ExampleShapesWidget.hpp View File

@@ -21,8 +21,8 @@
// DGL Stuff

#include "../../dgl/Color.hpp"
#include "../../dgl/StandaloneWindow.hpp"
#include "../../dgl/SubWidget.hpp"
#include "../../dgl/TopLevelWidget.hpp"

START_NAMESPACE_DGL

@@ -40,23 +40,14 @@ class ExampleShapesWidget : public BaseWidget
public:
static constexpr const char* const kExampleWidgetName = "Shapes";

explicit ExampleShapesWidget(Widget* const parentWidget)
: BaseWidget(parentWidget)
{
this->setSize(300, 300);
}
// SubWidget
explicit ExampleShapesWidget(Widget* const parent);

explicit ExampleShapesWidget(Window& windowToMapTo)
: BaseWidget(windowToMapTo)
{
this->setSize(300, 300);
}
// TopLevelWidget
explicit ExampleShapesWidget(Window& windowToMapTo);

explicit ExampleShapesWidget(Application& app)
: BaseWidget(app)
{
this->setSize(300, 300);
}
// StandaloneWindow
explicit ExampleShapesWidget(Application& app);

protected:
void onDisplay() override
@@ -104,6 +95,31 @@ protected:
}
};

// SubWidget
template<> inline
ExampleShapesWidget<SubWidget>::ExampleShapesWidget(Widget* const parentWidget)
: SubWidget(parentWidget)
{
setSize(300, 300);
}

// TopLevelWidget
template<> inline
ExampleShapesWidget<TopLevelWidget>::ExampleShapesWidget(Window& windowToMapTo)
: TopLevelWidget(windowToMapTo)
{
setSize(300, 300);
}

// StandaloneWindow
template<> inline
ExampleShapesWidget<StandaloneWindow>::ExampleShapesWidget(Application& app)
: StandaloneWindow(app)
{
setSize(300, 300);
done();
}

typedef ExampleShapesWidget<SubWidget> ExampleShapesSubWidget;
typedef ExampleShapesWidget<TopLevelWidget> ExampleShapesTopLevelWidget;
typedef ExampleShapesWidget<StandaloneWindow> ExampleShapesStandaloneWindow;


+ 4
- 0
dpf/tests/widgets/ExampleTextWidget.hpp View File

@@ -62,6 +62,7 @@ protected:
}
};

// SubWidget
template<> inline
ExampleTextWidget<NanoSubWidget>::ExampleTextWidget(Widget* const parent)
: NanoSubWidget(parent)
@@ -70,6 +71,7 @@ ExampleTextWidget<NanoSubWidget>::ExampleTextWidget(Widget* const parent)
setSize(500, 300);
}

// TopLevelWidget
template<> inline
ExampleTextWidget<NanoTopLevelWidget>::ExampleTextWidget(Window& windowToMapTo)
: NanoTopLevelWidget(windowToMapTo)
@@ -78,12 +80,14 @@ ExampleTextWidget<NanoTopLevelWidget>::ExampleTextWidget(Window& windowToMapTo)
setSize(500, 300);
}

// StandaloneWindow
template<> inline
ExampleTextWidget<NanoStandaloneWindow>::ExampleTextWidget(Application& app)
: NanoStandaloneWindow(app)
{
loadSharedResources();
setSize(500, 300);
done();
}

template class ExampleTextWidget<NanoSubWidget>;


+ 1
- 1
dpf/utils/generate-vst-bundles.sh View File

@@ -19,7 +19,7 @@ for i in $PLUGINS; do
cp -r ${DPF_DIR}/utils/plugin.vst/ ${BUNDLE}.vst
mv ${i} ${BUNDLE}.vst/Contents/MacOS/${BUNDLE}
rm -f ${BUNDLE}.vst/Contents/MacOS/deleteme
sed -i -e "s/X-PROJECTNAME-X/${BUNDLE}/" ${BUNDLE}.vst/Contents/Info.plist
sed -i -e "s/@INFO_PLIST_PROJECT_NAME@/${BUNDLE}/" ${BUNDLE}.vst/Contents/Info.plist
rm -f ${BUNDLE}.vst/Contents/Info.plist-e
done



+ 2
- 2
dpf/utils/plugin.vst/Contents/Info.plist View File

@@ -5,11 +5,11 @@
<key>CFBundleDevelopmentRegion</key>
<string>English</string>
<key>CFBundleExecutable</key>
<string>X-PROJECTNAME-X</string>
<string>@INFO_PLIST_PROJECT_NAME@</string>
<key>CFBundleIconFile</key>
<string></string>
<key>CFBundleIdentifier</key>
<string>studio.kx.distrho.X-PROJECTNAME-X</string>
<string>studio.kx.distrho.@INFO_PLIST_PROJECT_NAME@</string>
<key>CFBundleInfoDictionaryVersion</key>
<string>6.0</string>
<key>CFBundlePackageType</key>


+ 7
- 1
get-plugins.sh View File

@@ -16,9 +16,15 @@ cd repos
git clone --depth 1 --recursive -b develop git://github.com/DISTRHO/DPF

for PLUGIN in ${PLUGINS[@]}; do
git clone --depth 1 --recursive git://github.com/DISTRHO/$PLUGIN
git clone --depth 1 git://github.com/DISTRHO/$PLUGIN
done

# special case for ProM
cd ProM
git submodule init
git submodule update
cd ..

cd ..

rm -rf dpf


+ 1
- 1
plugins/3BandEQ/Makefile View File

@@ -30,7 +30,7 @@ include ../../dpf/Makefile.plugins.mk

TARGETS += jack
TARGETS += ladspa
TARGETS += vst
TARGETS += vst2

ifeq ($(HAVE_CAIRO_OR_OPENGL),true)
ifeq ($(HAVE_LIBLO),true)


+ 1
- 1
plugins/3BandSplitter/Makefile View File

@@ -30,7 +30,7 @@ include ../../dpf/Makefile.plugins.mk

TARGETS += jack
TARGETS += ladspa
TARGETS += vst
TARGETS += vst2

ifeq ($(HAVE_CAIRO_OR_OPENGL),true)
ifeq ($(HAVE_LIBLO),true)


+ 1
- 1
plugins/AmplitudeImposer/Makefile View File

@@ -30,7 +30,7 @@ include ../../dpf/Makefile.plugins.mk

TARGETS += jack
TARGETS += ladspa
TARGETS += vst
TARGETS += vst2

ifeq ($(HAVE_CAIRO_OR_OPENGL),true)
ifeq ($(HAVE_LIBLO),true)


+ 1
- 1
plugins/CycleShifter/Makefile View File

@@ -30,7 +30,7 @@ include ../../dpf/Makefile.plugins.mk

TARGETS += jack
TARGETS += ladspa
TARGETS += vst
TARGETS += vst2

ifeq ($(HAVE_CAIRO_OR_OPENGL),true)
ifeq ($(HAVE_LIBLO),true)


+ 1
- 9
plugins/Kars/Makefile View File

@@ -23,14 +23,6 @@ include ../../dpf/Makefile.plugins.mk
# --------------------------------------------------------------
# Enable all possible plugin types

ifeq ($(HAVE_JACK),true)
TARGETS += jack
endif

TARGETS += dssi_dsp
TARGETS += lv2_sep
TARGETS += vst

all: $(TARGETS)
all: jack dssi_dsp lv2_dsp vst2

# --------------------------------------------------------------

+ 1
- 4
plugins/MVerb/Makefile View File

@@ -27,12 +27,9 @@ include ../../dpf/Makefile.plugins.mk
# --------------------------------------------------------------
# Enable all possible plugin types

ifeq ($(HAVE_JACK),true)
TARGETS += jack
endif

TARGETS += ladspa
TARGETS += vst
TARGETS += vst2

ifeq ($(HAVE_DGL),true)
ifeq ($(HAVE_LIBLO),true)


+ 5
- 0
plugins/Nekobi/DistrhoUINekobi.cpp View File

@@ -129,6 +129,11 @@ DistrhoUINekobi::DistrhoUINekobi()
addIdleCallback(this, 120);
}

DistrhoUINekobi::~DistrhoUINekobi()
{
removeIdleCallback(this);
}

// -----------------------------------------------------------------------
// DSP Callbacks



+ 2
- 1
plugins/Nekobi/DistrhoUINekobi.hpp View File

@@ -1,6 +1,6 @@
/*
* DISTRHO Nekobi Plugin, based on Nekobee by Sean Bolton and others.
* Copyright (C) 2013-2015 Filipe Coelho <falktx@falktx.com>
* Copyright (C) 2013-2021 Filipe Coelho <falktx@falktx.com>
*
* This program is free software; you can redistribute it and/or
* modify it under the terms of the GNU General Public License as
@@ -42,6 +42,7 @@ class DistrhoUINekobi : public UI,
{
public:
DistrhoUINekobi();
~DistrhoUINekobi() override;

protected:
// -------------------------------------------------------------------


+ 1
- 1
plugins/Nekobi/Makefile View File

@@ -48,7 +48,7 @@ else
TARGETS += lv2_dsp
endif

TARGETS += vst
TARGETS += vst2

all: $(TARGETS)



+ 1
- 1
plugins/PingPongPan/Makefile View File

@@ -30,7 +30,7 @@ include ../../dpf/Makefile.plugins.mk

TARGETS += jack
TARGETS += ladspa
TARGETS += vst
TARGETS += vst2

ifeq ($(HAVE_CAIRO_OR_OPENGL),true)
ifeq ($(HAVE_LIBLO),true)


+ 1
- 1
plugins/SoulForce/Makefile View File

@@ -30,7 +30,7 @@ include ../../dpf/Makefile.plugins.mk

TARGETS += jack
TARGETS += ladspa
TARGETS += vst
TARGETS += vst2

ifeq ($(HAVE_CAIRO_OR_OPENGL),true)
ifeq ($(HAVE_LIBLO),true)


+ 0
- 3
plugins/glBars/Makefile View File

@@ -31,10 +31,7 @@ LINK_FLAGS += -lpthread
# --------------------------------------------------------------
# Enable all possible plugin types

ifeq ($(HAVE_JACK),true)
TARGETS += jack
endif

TARGETS += lv2
TARGETS += vst



Loading…
Cancel
Save