Browse Source

merge conflit

pull/173/head
dreamer 2 years ago
parent
commit
8b6f8e5647
100 changed files with 14858 additions and 5059 deletions
  1. +4
    -0
      .github/FUNDING.yml
  2. +300
    -735
      .github/workflows/build.yml
  3. +6
    -5
      .github/workflows/irc.yml
  4. +2
    -0
      .gitignore
  5. +30
    -6
      .gitmodules
  6. +112
    -110
      Makefile
  7. +209
    -0
      Makefile.base.mk
  8. +97
    -74
      README.md
  9. +1
    -1
      carla
  10. +164
    -125
      deps/Makefile
  11. +1
    -1
      deps/PawPaw
  12. +1
    -1
      deps/unzipfx/Makefile.win32
  13. +40
    -10
      docs/BUILDING.md
  14. +16
    -0
      docs/CARDINAL-MODULES.md
  15. +10
    -7
      docs/DIFFERENCES.md
  16. BIN
      docs/Docs_Remote-Control-1.png
  17. BIN
      docs/Docs_Remote-Control-2.png
  18. +10
    -4
      docs/FAQ.md
  19. +32
    -1
      docs/LICENSES.md
  20. BIN
      docs/Module_AIDA-X.png
  21. +63
    -0
      docs/OSC-REMOTE-CONTROL.md
  22. +1
    -1
      dpf
  23. +39
    -0
      include/OpenGL/gl.h
  24. +9
    -1
      include/common.hpp
  25. +23
    -25
      include/engine/Port.hpp
  26. +20
    -5
      include/helpers.hpp
  27. +9
    -3
      include/linux-compat/execinfo.h
  28. +0
    -58
      include/mingw-compat/cstdio
  29. +2
    -2
      include/mingw-compat/mutex
  30. +2
    -2
      include/mingw-compat/thread
  31. +0
    -1
      include/mingw-std-threads
  32. +7
    -16
      include/simd-compat/emmintrin.h
  33. +27
    -0
      include/simd-compat/immintrin.h
  34. +6
    -4
      include/simd-compat/mmintrin.h
  35. +37
    -6
      include/simd-compat/pmmintrin.h
  36. +26
    -0
      include/simd-compat/xmmintrin.h
  37. +3
    -7
      include/simd/Vector.hpp
  38. +5
    -0
      include/single-precision/algorithm
  39. +0
    -1
      include/sse2neon
  40. +172
    -17
      jucewrapper/CMakeLists.txt
  41. +5
    -5
      jucewrapper/CardinalWrapper.cpp
  42. +0
    -1
      lv2export/Makefile
  43. +1
    -19
      lv2export/export.cpp
  44. +4
    -27
      lv2export/lv2plugin.cpp
  45. +25
    -13
      lv2export/lv2plugin.hpp
  46. +2
    -2
      lv2export/plugins/aubileinstruments-macro-osc-2.cpp
  47. +2
    -2
      lv2export/plugins/aubileinstruments-macro-osc.cpp
  48. +2
    -2
      lv2export/plugins/msm-phaser.cpp
  49. +2
    -2
      lv2export/plugins/rackwindows-mv.cpp
  50. +2
    -2
      lv2export/plugins/rackwindows-vibrato.cpp
  51. +2
    -2
      lv2export/plugins/valleyaudio-plateau.cpp
  52. +6
    -24
      patches/examples/DRMR_-_Interverb.vcv
  53. +6384
    -0
      patches/examples/JTB_-_Waves.vcv
  54. +711
    -0
      patches/examples/SpotlightKid_-_Classic-Polysynth.vcv
  55. +858
    -0
      patches/examples/falkTX_-_Divide-no-Conquer.vcv
  56. +0
    -2299
      patches/mini/JTB_-_Proof-Of-Concept.vcv
  57. +622
    -0
      patches/mini/falkTX_-_Moogy.vcv
  58. +971
    -0
      patches/mini/falkTX_-_Saw_For_One.vcv
  59. +0
    -0
      patches/templates/fx.vcv
  60. +0
    -0
      patches/templates/main.vcv
  61. +283
    -0
      patches/templates/mini.vcv
  62. +0
    -0
      patches/templates/native.vcv
  63. +0
    -0
      patches/templates/synth.vcv
  64. BIN
      patches/touchosc/24-direct-fader-params.tosc
  65. +29
    -14
      patches/welcome-wasm-mini.vcv
  66. +136
    -1064
      patches/welcome-wasm.vcv
  67. +1
    -1
      plugins/AS
  68. +1
    -1
      plugins/AnimatedCircuits
  69. +1
    -1
      plugins/ArableInstruments
  70. +1
    -1
      plugins/AudibleInstruments
  71. +1
    -1
      plugins/BaconPlugs
  72. +1
    -1
      plugins/Befaco
  73. +1
    -1
      plugins/Bidoo
  74. +2
    -3
      plugins/BidooDark/plugin.cpp
  75. +10
    -0
      plugins/Cardinal/plugin.json
  76. +130
    -0
      plugins/Cardinal/res/AIDA-X.svg
  77. BIN
      plugins/Cardinal/res/aida-x-background-p2.png
  78. +46
    -0
      plugins/Cardinal/res/aida-x-knob.svg
  79. BIN
      plugins/Cardinal/res/aida-x-logo.png
  80. +35
    -0
      plugins/Cardinal/res/aida-x-scale.svg
  81. +1114
    -0
      plugins/Cardinal/src/AIDA-X.cpp
  82. +165
    -0
      plugins/Cardinal/src/AIDA-X/Biquad.cpp
  83. +60
    -0
      plugins/Cardinal/src/AIDA-X/Biquad.h
  84. +1
    -0
      plugins/Cardinal/src/AIDA-X/RTNeural
  85. +683
    -0
      plugins/Cardinal/src/AIDA-X/model_variant.hpp
  86. +16
    -14
      plugins/Cardinal/src/AudioFile.cpp
  87. +8
    -0
      plugins/Cardinal/src/AudioToCVPitch.cpp
  88. +10
    -8
      plugins/Cardinal/src/Blank.cpp
  89. +17
    -14
      plugins/Cardinal/src/Carla.cpp
  90. +1
    -1
      plugins/Cardinal/src/DearImGui.cpp
  91. +2
    -2
      plugins/Cardinal/src/DearImGuiColorTextEditor/TextEditor.cpp
  92. +58
    -27
      plugins/Cardinal/src/HostAudio.cpp
  93. +129
    -53
      plugins/Cardinal/src/HostCV.cpp
  94. +13
    -8
      plugins/Cardinal/src/HostMIDI.cpp
  95. +8
    -8
      plugins/Cardinal/src/HostParameters-Map.cpp
  96. +6
    -6
      plugins/Cardinal/src/HostParameters.cpp
  97. +3
    -1
      plugins/Cardinal/src/HostTime.cpp
  98. +780
    -186
      plugins/Cardinal/src/Ildaeil.cpp
  99. +13
    -10
      plugins/Cardinal/src/ImGuiWidget.cpp
  100. +8
    -4
      plugins/Cardinal/src/ModuleWidgets.hpp

+ 4
- 0
.github/FUNDING.yml View File

@@ -0,0 +1,4 @@
github: falkTX
liberapay: falkTX
patreon: falkTX
custom: "https://paypal.me/falkTX"

+ 300
- 735
.github/workflows/build.yml
File diff suppressed because it is too large
View File


+ 6
- 5
.github/workflows/irc.yml View File

@@ -1,6 +1,6 @@
name: irc

on: [push]
on: [push, pull_request]

jobs:
notification:
@@ -8,13 +8,14 @@ jobs:
name: IRC notification
steps:
- name: Format message
id: message
run: |
message="${{ github.actor }} pushed $(echo '${{ github.event.commits[0].message }}' | head -n 1) ${{ github.event.commits[0].url }}"
echo ::set-output name=message::"${message}"
echo commitmessage=$(echo "${{ github.event.commits[0].message }}" | head -n 1) >> $GITHUB_ENV
- name: Format message
run: |
echo message="${{ github.actor }} pushed ${{ env.commitmessage }} ${{ github.event.commits[0].url }}" >> $GITHUB_ENV
- name: IRC notification
uses: Gottox/irc-message-action@v2
with:
channel: '#cardinal'
nickname: github-event-bot
message: ${{ steps.message.outputs.message }}
message: ${{ env.message }}

+ 2
- 0
.gitignore View File

@@ -18,6 +18,8 @@ compile_commands.json

/bin/
/build/
/build-headless/
/deps/surge-build/
/documentation.pdf
/jucewrapper/build/
/jucewrapper/JUCE/


+ 30
- 6
.gitmodules View File

@@ -4,12 +4,6 @@
[submodule "dpf"]
path = dpf
url = https://github.com/DISTRHO/DPF.git
[submodule "plugins/Cardinal/mingw-std-threads"]
path = include/mingw-std-threads
url = https://github.com/meganz/mingw-std-threads.git
[submodule "plugins/Cardinal/sse2neon"]
path = include/sse2neon
url = https://github.com/DLTcollab/sse2neon.git
[submodule "plugins/Befaco"]
path = plugins/Befaco
url = https://github.com/VCVRack/Befaco.git
@@ -209,6 +203,36 @@
[submodule "plugins/myth-modules"]
path = plugins/myth-modules
url = https://github.com/Ahineya/vcv-myth-plugin.git
[submodule "plugins/alefsbits"]
path = plugins/alefsbits
url = https://github.com/alefnull/alefsbits.git
[submodule "plugins/h4n4-modules"]
path = plugins/h4n4-modules
url = https://github.com/hannakoppelaar/h4n4-modules.git
[submodule "plugins/dBiz"]
path = plugins/dBiz
url = https://github.com/dBiz/dBiz.git
[submodule "include/simde"]
path = include/simde
url = https://github.com/simd-everywhere/simde.git
[submodule "plugins/RebelTech"]
path = plugins/RebelTech
url = https://github.com/hemmer/rebel-tech-vcv.git
[submodule "plugins/stoermelder-packone"]
path = plugins/stoermelder-packone
url = https://github.com/stoermelder/vcvrack-packone.git
[submodule "plugins/surgext"]
path = plugins/surgext
url = https://github.com/surge-synthesizer/surge-rack.git
[submodule "plugins/Sapphire"]
path = plugins/Sapphire
url = https://github.com/cosinekitty/sapphire.git
[submodule "plugins/Cardinal/src/AIDA-X/RTNeural"]
path = plugins/Cardinal/src/AIDA-X/RTNeural
url = https://github.com/jatinchowdhury18/RTNeural.git
[submodule "plugins/EnigmaCurry"]
path = plugins/EnigmaCurry
url = https://github.com/EnigmaCurry/EnigmaCurry-vcv-pack.git
[submodule "plugins/StarlingVia"]
path = plugins/StarlingVia
url = https://github.com/starlingcode/Via-for-Rack.git

+ 112
- 110
Makefile View File

@@ -4,16 +4,19 @@
# Created by falkTX
#

ROOT = .
include $(ROOT)/Makefile.base.mk

# -----------------------------------------------------------------------------
# Set version

# also set in:
# jucewrapper/CMakeList.txt `project`
# jucewrapper/CMakeLists.txt `project`
# src/CardinalCommon.cpp `CARDINAL_VERSION`
# src/CardinalPlugin.cpp `getVersion`
VERSION = 22.09

# --------------------------------------------------------------
# Import base definitions

include dpf/Makefile.base.mk
# utils/macOS/Info_{JACK,Native}.plist
# jucewrapper/CMakeLists.txt src/CardinalCommon.cpp src/CardinalPlugin.cpp utils/macOS/Info_{JACK,Native}.plist
VERSION = 23.10

# --------------------------------------------------------------
# Build targets
@@ -26,20 +29,6 @@ all: cardinal carla deps dgl plugins gen resources
PREFIX ?= /usr/local
DESTDIR ?=

ifeq ($(BSD),true)
SYSDEPS ?= true
else
SYSDEPS ?= false
endif

ifeq ($(LINUX),true)
VST3_SUPPORTED = true
else ifeq ($(MACOS),true)
VST3_SUPPORTED = true
else ifeq ($(WINDOWS),true)
VST3_SUPPORTED = true
endif

# --------------------------------------------------------------
# Carla config

@@ -56,32 +45,21 @@ ifneq ($(DEBUG),true)
CARLA_EXTRA_ARGS += EXTERNAL_PLUGINS=true
endif

# --------------------------------------------------------------
# DGL config

DGL_EXTRA_ARGS = \
DISTRHO_NAMESPACE=CardinalDISTRHO \
DGL_NAMESPACE=CardinalDGL \
NVG_DISABLE_SKIPPING_WHITESPACE=true \
NVG_FONT_TEXTURE_FLAGS=NVG_IMAGE_NEAREST \
USE_NANOVG_FBO=true \
WINDOWS_ICON_ID=401

# --------------------------------------------------------------
# Check for required system-wide dependencies

ifeq ($(SYSDEPS),true)

ifneq ($(shell pkg-config --exists jansson && echo true),true)
ifneq ($(shell $(PKG_CONFIG) --exists jansson && echo true),true)
$(error jansson dependency not installed/available)
endif
ifneq ($(shell pkg-config --exists libarchive && echo true),true)
ifneq ($(shell $(PKG_CONFIG) --exists libarchive && echo true),true)
$(error libarchive dependency not installed/available)
endif
ifneq ($(shell pkg-config --exists samplerate && echo true),true)
ifneq ($(shell $(PKG_CONFIG) --exists samplerate && echo true),true)
$(error samplerate dependency not installed/available)
endif
ifneq ($(shell pkg-config --exists speexdsp && echo true),true)
ifneq ($(shell $(PKG_CONFIG) --exists speexdsp && echo true),true)
$(error speexdsp dependency not installed/available)
endif

@@ -89,7 +67,7 @@ endif

ifeq ($(HEADLESS),true)

ifneq ($(shell pkg-config --exists liblo && echo true),true)
ifneq ($(shell $(PKG_CONFIG) --exists liblo && echo true),true)
$(error liblo dependency not installed/available)
endif

@@ -119,6 +97,8 @@ endif

else

CARLA_EXTRA_ARGS += HAVE_DBUS=false
CARLA_EXTRA_ARGS += HAVE_DGL=false
CARLA_EXTRA_ARGS += HAVE_OPENGL=false
CARLA_EXTRA_ARGS += HAVE_X11=false
CARLA_EXTRA_ARGS += HAVE_XCURSOR=false
@@ -140,8 +120,7 @@ endif
# --------------------------------------------------------------
# MOD builds

EXTRA_MOD_FLAGS = -I../include/single-precision -fsingle-precision-constant

EXTRA_MOD_FLAGS = -I../include/single-precision -fsingle-precision-constant -Wno-attributes
ifeq ($(MODDUO),true)
EXTRA_MOD_FLAGS += -mno-unaligned-access
endif
@@ -149,51 +128,9 @@ ifeq ($(WITH_LTO),true)
EXTRA_MOD_FLAGS += -ffat-lto-objects
endif

MOD_WORKDIR ?= $(HOME)/mod-workdir
MOD_ENVIRONMENT = \
AR=${1}/host/usr/bin/${2}-gcc-ar \
CC=${1}/host/usr/bin/${2}-gcc \
CPP=${1}/host/usr/bin/${2}-cpp \
CXX=${1}/host/usr/bin/${2}-g++ \
LD=${1}/host/usr/bin/${2}-ld \
PKG_CONFIG=${1}/host/usr/bin/pkg-config \
STRIP=${1}/host/usr/bin/${2}-strip \
CFLAGS="-I${1}/staging/usr/include $(EXTRA_MOD_FLAGS)" \
CPPFLAGS= \
CXXFLAGS="-I${1}/staging/usr/include $(EXTRA_MOD_FLAGS) -Wno-attributes" \
LDFLAGS="-L${1}/staging/usr/lib $(EXTRA_MOD_FLAGS)" \
EXE_WRAPPER="qemu-${3}-static -L ${1}/target" \
HEADLESS=true \
MOD_BUILD=true \
NOOPT=true \
STATIC_BUILD=true

modduo:
$(MAKE) $(call MOD_ENVIRONMENT,$(MOD_WORKDIR)/modduo-static,arm-mod-linux-gnueabihf.static,arm)

modduox:
$(MAKE) $(call MOD_ENVIRONMENT,$(MOD_WORKDIR)/modduox-static,aarch64-mod-linux-gnueabi.static,aarch64)

moddwarf:
$(MAKE) $(call MOD_ENVIRONMENT,$(MOD_WORKDIR)/moddwarf,aarch64-mod-linux-gnu,aarch64)

publish:
tar -C bin -cz $(subst bin/,,$(wildcard bin/*.lv2)) | base64 | curl -F 'package=@-' http://192.168.51.1/sdk/install && echo

ifneq (,$(findstring modduo-,$(MAKECMDGOALS)))
$(MAKECMDGOALS):
$(MAKE) $(call MOD_ENVIRONMENT,$(MOD_WORKDIR)/modduo-static,arm-mod-linux-gnueabihf.static,arm) $(subst modduo-,,$(MAKECMDGOALS))
endif

ifneq (,$(findstring modduox-,$(MAKECMDGOALS)))
$(MAKECMDGOALS):
$(MAKE) $(call MOD_ENVIRONMENT,$(MOD_WORKDIR)/modduox-static,aarch64-mod-linux-gnueabi.static,aarch64) $(subst modduox-,,$(MAKECMDGOALS))
endif

ifneq (,$(findstring moddwarf-,$(MAKECMDGOALS)))
$(MAKECMDGOALS):
$(MAKE) $(call MOD_ENVIRONMENT,$(MOD_WORKDIR)/moddwarf,aarch64-mod-linux-gnu,aarch64) $(subst moddwarf-,,$(MAKECMDGOALS))
endif
MOD_ENVIRONMENT += HEADLESS=true
MOD_ENVIRONMENT += MOD_BUILD=true
MOD_ENVIRONMENT += STATIC_BUILD=true

# --------------------------------------------------------------
# Individual targets
@@ -210,9 +147,35 @@ ifneq ($(STATIC_BUILD),true)
USING_CUSTOM_DPF=true
endif

carla-win32:
ifneq ($(STATIC_BUILD),true)
$(MAKE) all -C carla $(CARLA_EXTRA_ARGS) \
CAN_GENERATE_LV2_TTL=false \
CUSTOM_DPF_PATH=$(CURDIR)/dpf \
DGL_NAMESPACE=CardinalDGL \
HAVE_FRONTEND=true \
HAVE_PYQT=true \
HAVE_QT5=true \
HAVE_QT5PKG=true \
STATIC_PLUGIN_TARGET=true \
USING_CUSTOM_DPF=true
ifeq ($(CPU_X86_64),true)
$(MAKE) win32r -C carla $(CARLA_EXTRA_ARGS) \
CAN_GENERATE_LV2_TTL=false \
CUSTOM_DPF_PATH=$(CURDIR)/dpf \
DGL_NAMESPACE=CardinalDGL \
HAVE_FRONTEND=true \
HAVE_PYQT=true \
HAVE_QT5=true \
HAVE_QT5PKG=true \
STATIC_PLUGIN_TARGET=true \
USING_CUSTOM_DPF=true
endif
endif

deps:
ifeq ($(SYSDEPS),true)
$(MAKE) quickjs -C deps
$(MAKE) quickjs surge -C deps
else
$(MAKE) all -C deps
endif
@@ -222,7 +185,7 @@ endif

dgl:
ifneq ($(HEADLESS),true)
$(MAKE) -C dpf/dgl opengl $(DGL_EXTRA_ARGS)
$(MAKE) opengl -C dpf/dgl $(DGL_EXTRA_ARGS)
endif

plugins: deps
@@ -241,27 +204,51 @@ else
gen:
endif

# --------------------------------------------------------------
# extra rules, for quick testing

jack: carla deps dgl plugins resources
$(MAKE) jack -C src $(CARLA_EXTRA_ARGS)

native: carla deps dgl plugins resources
$(MAKE) native -C src $(CARLA_EXTRA_ARGS)

mini: carla deps dgl plugins resources
$(MAKE) mini -C src $(CARLA_EXTRA_ARGS)

clap: carla deps dgl plugins resources
$(MAKE) clap -C src $(CARLA_EXTRA_ARGS)

lv2: carla deps dgl plugins resources
$(MAKE) lv2 -C src $(CARLA_EXTRA_ARGS)

vst2: carla deps dgl plugins resources
$(MAKE) vst2 -C src $(CARLA_EXTRA_ARGS)

vst3: carla deps dgl plugins resources
$(MAKE) vst3 -C src $(CARLA_EXTRA_ARGS)

# --------------------------------------------------------------
# Packaging standalone for CI

unzipfx: deps/unzipfx/unzipfx2cat$(APP_EXT) CardinalJACK.zip CardinalNative.zip
cat deps/unzipfx/unzipfx2cat$(APP_EXT) CardinalJACK.zip > CardinalJACK
cat deps/unzipfx/unzipfx2cat$(APP_EXT) CardinalNative.zip > CardinalNative
chmod +x CardinalJACK CardinalNative
cat deps/unzipfx/unzipfx2cat$(APP_EXT) CardinalJACK.zip > CardinalJACK$(APP_EXT)
cat deps/unzipfx/unzipfx2cat$(APP_EXT) CardinalNative.zip > CardinalNative$(APP_EXT)
chmod +x CardinalJACK$(APP_EXT) CardinalNative$(APP_EXT)

CardinalJACK.zip: bin/Cardinal bin/CardinalFX.lv2/resources
CardinalJACK.zip: bin/Cardinal$(APP_EXT) bin/CardinalFX.lv2/resources
mkdir -p build/unzipfx-jack
ln -sf ../../bin/Cardinal build/unzipfx-jack/Cardinal
ln -s ../../bin/CardinalFX.lv2/resources build/unzipfx-jack/resources
ln -sf ../../bin/Cardinal$(APP_EXT) build/unzipfx-jack/Cardinal$(APP_EXT)
ln -sf ../../bin/CardinalFX.lv2/resources build/unzipfx-jack/resources
cd build/unzipfx-jack && \
zip -r -9 ../../$@ Cardinal resources
zip -r -9 ../../$@ Cardinal$(APP_EXT) resources

CardinalNative.zip: bin/CardinalNative bin/CardinalFX.lv2/resources
CardinalNative.zip: bin/CardinalNative$(APP_EXT) bin/CardinalFX.lv2/resources
mkdir -p build/unzipfx-native
ln -sf ../../bin/CardinalNative build/unzipfx-native/Cardinal
ln -s ../../bin/CardinalFX.lv2/resources build/unzipfx-native/resources
ln -sf ../../bin/CardinalNative$(APP_EXT) build/unzipfx-native/Cardinal$(APP_EXT)
ln -sf ../../bin/CardinalFX.lv2/resources build/unzipfx-native/resources
cd build/unzipfx-native && \
zip -r -9 ../../$@ Cardinal resources
zip -r -9 ../../$@ Cardinal$(APP_EXT) resources

deps/unzipfx/unzipfx2cat:
make -C deps/unzipfx -f Makefile.linux
@@ -280,7 +267,10 @@ clean:
$(MAKE) clean -C dpf/utils/lv2-ttl-generator
$(MAKE) clean -C plugins
$(MAKE) clean -C src
rm -rf bin build
rm -rf bin build build-headless dpf/utils/lv2_ttl_generator.d
# FIXME
rm -f src/Rack/BaconMusic/default-skin.json
rm -f src/Rack/SurgeXTRack/default-skin.json

# --------------------------------------------------------------
# Install step
@@ -289,32 +279,39 @@ install:
install -d $(DESTDIR)$(PREFIX)/bin
install -d $(DESTDIR)$(PREFIX)/lib/lv2/Cardinal.lv2
install -d $(DESTDIR)$(PREFIX)/lib/lv2/CardinalFX.lv2
install -d $(DESTDIR)$(PREFIX)/lib/lv2/CardinalMini.lv2
install -d $(DESTDIR)$(PREFIX)/lib/lv2/CardinalSynth.lv2
install -d $(DESTDIR)$(PREFIX)/lib/clap/Cardinal.clap
install -d $(DESTDIR)$(PREFIX)/lib/vst/Cardinal.vst
ifeq ($(VST3_SUPPORTED),true)
install -d $(DESTDIR)$(PREFIX)/lib/vst3/Cardinal.vst3/Contents
install -d $(DESTDIR)$(PREFIX)/lib/vst3/CardinalFX.vst3/Contents
install -d $(DESTDIR)$(PREFIX)/lib/vst3/CardinalSynth.vst3/Contents
ifneq ($(VST3_BINARY_DIR),)
install -d $(DESTDIR)$(PREFIX)/lib/vst3/Cardinal.vst3/$(VST3_BINARY_DIR)
install -d $(DESTDIR)$(PREFIX)/lib/vst3/CardinalFX.vst3/$(VST3_BINARY_DIR)
install -d $(DESTDIR)$(PREFIX)/lib/vst3/CardinalSynth.vst3/$(VST3_BINARY_DIR)
endif
install -d $(DESTDIR)$(PREFIX)/share/cardinal
install -d $(DESTDIR)$(PREFIX)/share/doc/cardinal/docs

install -m 644 bin/Cardinal.lv2/*.* $(DESTDIR)$(PREFIX)/lib/lv2/Cardinal.lv2/
install -m 644 bin/CardinalFX.lv2/*.* $(DESTDIR)$(PREFIX)/lib/lv2/CardinalFX.lv2/
install -m 644 bin/CardinalMini.lv2/*.* $(DESTDIR)$(PREFIX)/lib/lv2/CardinalMini.lv2/
install -m 644 bin/CardinalSynth.lv2/*.* $(DESTDIR)$(PREFIX)/lib/lv2/CardinalSynth.lv2/

install -m 644 bin/Cardinal.clap/*.* $(DESTDIR)$(PREFIX)/lib/clap/Cardinal.clap/
install -m 644 bin/Cardinal.vst/*.* $(DESTDIR)$(PREFIX)/lib/vst/Cardinal.vst/

ifeq ($(VST3_SUPPORTED),true)
cp -rL bin/Cardinal.vst3/Contents/*-* $(DESTDIR)$(PREFIX)/lib/vst3/Cardinal.vst3/Contents/
cp -rL bin/CardinalFX.vst3/Contents/*-* $(DESTDIR)$(PREFIX)/lib/vst3/CardinalFX.vst3/Contents/
cp -rL bin/CardinalSynth.vst3/Contents/*-* $(DESTDIR)$(PREFIX)/lib/vst3/CardinalSynth.vst3/Contents/
ifneq ($(VST3_BINARY_DIR),)
install -m 644 bin/Cardinal.vst3/$(VST3_BINARY_DIR)/* $(DESTDIR)$(PREFIX)/lib/vst3/Cardinal.vst3/$(VST3_BINARY_DIR)/
install -m 644 bin/CardinalFX.vst3/$(VST3_BINARY_DIR)/* $(DESTDIR)$(PREFIX)/lib/vst3/CardinalFX.vst3/$(VST3_BINARY_DIR)/
install -m 644 bin/CardinalSynth.vst3/$(VST3_BINARY_DIR)/* $(DESTDIR)$(PREFIX)/lib/vst3/CardinalSynth.vst3/$(VST3_BINARY_DIR)/
endif

install -m 755 bin/Cardinal$(APP_EXT) $(DESTDIR)$(PREFIX)/bin/
install -m 755 bin/Cardinal$(APP_EXT) $(DESTDIR)$(PREFIX)/bin/
install -m 755 bin/CardinalMini$(APP_EXT) $(DESTDIR)$(PREFIX)/bin/
install -m 755 bin/CardinalNative$(APP_EXT) $(DESTDIR)$(PREFIX)/bin/

cp -rL bin/Cardinal.lv2/resources/* $(DESTDIR)$(PREFIX)/share/cardinal/

install -m 644 README.md $(DESTDIR)$(PREFIX)/share/doc/cardinal/
install -m 644 README.md $(DESTDIR)$(PREFIX)/share/doc/cardinal/
install -m 644 docs/*.md docs/*.png $(DESTDIR)$(PREFIX)/share/doc/cardinal/docs/

# --------------------------------------------------------------
@@ -330,7 +327,6 @@ TAR_ARGS = \
--exclude="*.kdev*" \
--exclude=".travis*" \
--exclude=".vscode*" \
--exclude="carla/source/modules/juce_*" \
--exclude="carla/source/native-plugins/external/zynaddsubfx*" \
--exclude="src/Rack/dep/osdialog/osdialog_*" \
--exclude="src/Rack/icon.*" \
@@ -365,7 +361,10 @@ TAR_ARGS = \
--exclude=plugins/BogaudioModules/res-src \
--exclude=plugins/Cardinal/orig \
--exclude=plugins/GrandeModular/res-src \
--exclude=src/MOD \
--exclude=plugins/surgext/surge/libs/JUCE \
--exclude=plugins/surgext/surge/resources/data/patches_3rdparty \
--exclude=plugins/surgext/surge/resources/data/patches_factory \
--exclude=plugins/surgext/surge/resources/data/wavetables_3rdparty \
--exclude=src/Rack/adapters \
--exclude=src/Rack/dep/filesystem/cmake \
--exclude=src/Rack/dep/filesystem/examples \
@@ -400,10 +399,13 @@ TAR_ARGS = \
--exclude=src/Rack/src/app/AudioDisplay.cpp \
--exclude=src/Rack/src/app/MenuBar.cpp \
--exclude=src/Rack/src/app/MidiDisplay.cpp \
--exclude=src/Rack/src/app/ModuleWidget.cpp \
--exclude=src/Rack/src/app/Scene.cpp \
--exclude=src/Rack/src/app/TipWindow.cpp \
--exclude=src/Rack/src/dsp/minblep.cpp \
--exclude=src/Rack/src/engine/Engine.cpp \
--exclude=src/Rack/src/plugin/Model.cpp \
--exclude=src/Rack/src/widget/OpenGlWidget.cpp \
--exclude=src/Rack/src/window/Window.cpp \
--exclude=src/Rack/res/Core \
--exclude=src/Rack/res/icon.png \


+ 209
- 0
Makefile.base.mk View File

@@ -0,0 +1,209 @@
#!/usr/bin/make -f
# Makefile for Cardinal #
# --------------------- #
# Created by falkTX
#

ifeq ($(ROOT),)
$(error invalid usage)
endif

ifeq ($(NOSIMD),true)
ifneq (,$(findstring -msse,$(CXXFLAGS)))
$(error NOSIMD build requested but -msse compiler flag is present in CXXFLAGS)
endif
endif

# -----------------------------------------------------------------------------
# Import base definitions

export DISTRHO_NAMESPACE = CardinalDISTRHO
export DGL_NAMESPACE = CardinalDGL
export NVG_DISABLE_SKIPPING_WHITESPACE = true
export NVG_FONT_TEXTURE_FLAGS = NVG_IMAGE_NEAREST
export USE_NANOVG_FBO = true
export WASM_EXCEPTIONS = true
export WINDOWS_ICON_ID = 401
export X11_WINDOW_ICON_NAME = gCardinalX11Icon
export X11_WINDOW_ICON_SIZE = 18950
include $(ROOT)/dpf/Makefile.base.mk

DGL_EXTRA_ARGS = \
DISTRHO_NAMESPACE=$(DISTRHO_NAMESPACE) \
DGL_NAMESPACE=$(DGL_NAMESPACE) \
NVG_DISABLE_SKIPPING_WHITESPACE=$(NVG_DISABLE_SKIPPING_WHITESPACE) \
NVG_FONT_TEXTURE_FLAGS=$(NVG_FONT_TEXTURE_FLAGS) \
USE_NANOVG_FBO=$(USE_NANOVG_FBO) \
WASM_EXCEPTIONS=$(WASM_EXCEPTIONS) \
WINDOWS_ICON_ID=$(WINDOWS_ICON_ID) \
X11_WINDOW_ICON_NAME=$(X11_WINDOW_ICON_NAME) \
X11_WINDOW_ICON_SIZE=$(X11_WINDOW_ICON_SIZE)

# -----------------------------------------------------------------------------
# Build config

ifeq ($(BSD),true)
SYSDEPS ?= true
else
SYSDEPS ?= false
endif

ifeq ($(SYSDEPS),true)
RACK_DEP_PATH = $(abspath $(ROOT)/deps/sysroot)
else
RACK_DEP_PATH = $(abspath $(ROOT)/src/Rack/dep)
endif

# -----------------------------------------------------------------------------
# Custom build flags

BASE_FLAGS += -I$(abspath $(ROOT)/include)
BASE_FLAGS += -I$(abspath $(ROOT)/include/simd-compat)
BASE_FLAGS += -I$(RACK_DEP_PATH)/include

ifeq ($(MOD_BUILD),true)
BASE_FLAGS += -DSIMDE_ENABLE_OPENMP -fopenmp
LINK_FLAGS += -fopenmp
endif

ifeq ($(NOSIMD),true)
BASE_FLAGS += -DCARDINAL_NOSIMD
endif

ifeq ($(SYSDEPS),true)
BASE_FLAGS += -DCARDINAL_SYSDEPS
BASE_FLAGS += $(shell $(PKG_CONFIG) --cflags jansson libarchive samplerate speexdsp)
else
BASE_FLAGS += -DZSTDLIB_VISIBILITY=
endif

ifeq ($(BSD)$(HAIKU),true)
BASE_FLAGS += -DCLOCK_MONOTONIC_RAW=CLOCK_MONOTONIC
endif

ifeq ($(HAIKU)$(WASM),true)
BASE_FLAGS += -I$(abspath $(ROOT)/include/linux-compat)
else
BASE_FLAGS += -pthread
endif

ifeq ($(WINDOWS),true)
BASE_FLAGS += -D_USE_MATH_DEFINES
BASE_FLAGS += -DWIN32_LEAN_AND_MEAN
BASE_FLAGS += -D_WIN32_WINNT=0x0600
BASE_FLAGS += -I$(abspath $(ROOT)/include/mingw-compat)
endif

# make sure these flags always end up last
BUILD_C_FLAGS += -fno-finite-math-only -fno-strict-aliasing
BUILD_CXX_FLAGS += -fno-finite-math-only -fno-strict-aliasing

# -----------------------------------------------------------------------------
# simde flags

BASE_FLAGS += -I$(abspath $(ROOT)/src/Rack/dep/simde)
BASE_FLAGS += -DSIMDE_ACCURACY_PREFERENCE=0
BASE_FLAGS += -DSIMDE_FAST_CONVERSION_RANGE
BASE_FLAGS += -DSIMDE_FAST_MATH
BASE_FLAGS += -DSIMDE_FAST_NANS
BASE_FLAGS += -DSIMDE_FAST_ROUND_MODE
BASE_FLAGS += -DSIMDE_FAST_ROUND_TIES

# unwanted
BASE_FLAGS += -DSIMDE_X86_SSE4_1_H
BASE_FLAGS += -DSIMDE_X86_SSE4_2_H

# -----------------------------------------------------------------------------
# Rack build flags

ifeq ($(BUILDING_RACK),true)

# Rack code is not tested for this flag, unset it
BUILD_CXX_FLAGS += -U_GLIBCXX_ASSERTIONS -Wp,-U_GLIBCXX_ASSERTIONS

# Ignore bad behaviour from Rack API
BUILD_CXX_FLAGS += -Wno-format-security

# Ignore warnings from simde
ifeq ($(MOD_BUILD),true)
BUILD_CXX_FLAGS += -Wno-overflow
endif

# lots of warnings from VCV side
BASE_FLAGS += -Wno-unused-parameter
BASE_FLAGS += -Wno-unused-variable

ifeq ($(CPU_ARM_OR_ARM64)$(CPU_RISCV64),true)
BASE_FLAGS += -Wno-attributes
endif

ifeq ($(MACOS),true)
BASE_FLAGS += -DARCH_MAC
else ifeq ($(WINDOWS),true)
BASE_FLAGS += -DARCH_WIN
else
BASE_FLAGS += -DARCH_LIN
endif

ifeq ($(DEBUG),true)
BASE_FLAGS += -UDEBUG
endif

ifeq ($(HEADLESS),true)
BASE_FLAGS += -DHEADLESS
endif

ifeq ($(USE_GLES2),true)
BASE_FLAGS += -DNANOVG_GLES2_FORCED
else ifeq ($(USE_GLES3),true)
BASE_FLAGS += -DNANOVG_GLES3_FORCED
endif

# needed for enabling SSE in pffft
ifeq ($(CPU_I386),true)
ifneq ($(NOSIMD),true)
BASE_FLAGS += -Di386
endif
endif

# SIMD must always be enabled, even in debug builds
ifneq ($(NOSIMD),true)
ifeq ($(DEBUG),true)

ifeq ($(WASM),true)
BASE_FLAGS += -msse -msse2 -msse3 -msimd128
else ifeq ($(CPU_ARM32),true)
BASE_FLAGS += -mfpu=neon-vfpv4 -mfloat-abi=hard
else ifeq ($(CPU_I386_OR_X86_64),true)
BASE_FLAGS += -msse -msse2 -mfpmath=sse
endif

endif
endif

BASE_FLAGS += -I$(abspath $(ROOT)/dpf/dgl/src/nanovg)
BASE_FLAGS += -I$(abspath $(ROOT)/dpf/distrho)

BASE_FLAGS += -I$(abspath $(ROOT)/src)
BASE_FLAGS += -I$(abspath $(ROOT)/src/Rack/include)
BASE_FLAGS += -I$(abspath $(ROOT)/src/Rack/include/dsp)
BASE_FLAGS += -I$(abspath $(ROOT)/src/Rack/dep/filesystem/include)
BASE_FLAGS += -I$(abspath $(ROOT)/src/Rack/dep/fuzzysearchdatabase/src)
BASE_FLAGS += -I$(abspath $(ROOT)/src/Rack/dep/glfw/include)
BASE_FLAGS += -I$(abspath $(ROOT)/src/Rack/dep/nanosvg/src)
BASE_FLAGS += -I$(abspath $(ROOT)/src/Rack/dep/oui-blendish)
BASE_FLAGS += -I$(abspath $(ROOT)/src/Rack/dep/pffft)
BASE_FLAGS += -I$(abspath $(ROOT)/src/Rack/dep/tinyexpr)

BUILD_C_FLAGS += -std=gnu11

ifneq ($(MACOS),true)
BUILD_CXX_FLAGS += -faligned-new -Wno-abi
ifeq ($(MOD_BUILD),true)
BUILD_CXX_FLAGS += -std=gnu++17
endif
endif

endif

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

+ 97
- 74
README.md View File

@@ -3,13 +3,13 @@
*Cardinal, the Rack!*

Cardinal is a free and open-source virtual modular synthesizer plugin,
available as JACK standalone and AU, LV2, VST2 and VST3 audio plugin for FreeBSD, Linux, macOS and Windows.
available in AudioUnit/CLAP/LV2/VST2/VST3 plugin formats and as a standalone app for FreeBSD, Linux, macOS, Windows and the Web.
It is based on the popular [VCV Rack](https://vcvrack.com/) but with a focus on being a fully self-contained plugin version.

More specifically, this is a [DPF-based](https://github.com/DISTRHO/DPF/)
plugin wrapper around [VCV Rack](https://github.com/VCVRack/Rack/),
using its code directly instead of forking the project,
with the target of having a **proper, self-contained, fully free and open-source plugin version of Rack**.
with the target of having a **self-contained, fully free and open-source plugin version of Rack**.
See the [why section](#Why) below for the reasons Cardinal exists,
also for frequently asked questions check this [FAQ document](docs/FAQ.md).

@@ -25,14 +25,16 @@ All VCV branding has been removed (to the best of our knowledge) in order to avo
Cardinal should be considered stable, if you spot any bugs please report them.
Currently the following should be noted:

- Windows 32bit builds do not work well [#80](https://github.com/DISTRHO/Cardinal/issues/80)
- CLAP support is a work-in-progress [DPF#383](https://github.com/DISTRHO/DPF/issues/383)
- VST3 plugin hosting (inside Carla or Ildaeil modules) mostly works but is considered experimental
- Windows 32bit builds still have a few problematic modules [#80](https://github.com/DISTRHO/Cardinal/issues/80)

### Stable release

Cardinal releases have official builds for Linux, macOS and Windows.
You can find these under https://github.com/DISTRHO/Cardinal/releases.

There are Linux builds for various architectures (armhf, arm64, i686 and x86_64), macOS "universal" (arm64 + intel) and Windows 32 and 64bit builds.
There are Linux builds for various architectures (armhf, arm64, i686, riscv64 and x86_64), macOS "universal" (arm64 + intel) and Windows 32 and 64bit builds.
Both macOS and Windows builds have an installer.
Install instructions are available [here](https://github.com/DISTRHO/Cardinal/wiki/Install).

@@ -62,9 +64,10 @@ All variants have MIDI input and output support.

### Main

This variant provides 8 audio inputs and outputs and 10 CV inputs and outputs.
This variant provides 8 audio inputs and outputs and 10 CV inputs and outputs.

NOTE: Due to AU and VST2 formats not supporting CV ports, this variant is not available for those formats.
NOTE: Due to AU and VST2 formats not supporting CV ports, this variant is not available for those formats.
NOTE: This variant is not available in CLAP yet, to be added in a later release

### Synth

@@ -76,6 +79,19 @@ Plugin type is set as "instrument".
This variant provides 2 audio inputs and outputs, but no CV ports.
Plugin type is set as regular "effect".

### Mini

This is a special variant with a very small, hand-picked module selection and limited IO (2 audio ports plus 5 CV).
It only exists as LV2 and Standalone plugin.

For now the list of selected modules is quite small, intentionally. We will add a few more as the need appears.
All included modules support polyphony, reducing confusion for new users not yet used to mono vs poly approach in Rack/Cardinal.

The main reason for this variant to exist is being able to support DSP/UI separation, which is only possible with more simple modules.
The DSP/UI separation means we can run the DSP on a different machine than the UI.
This is particularly interesting for running Cardinal on embed systems, being controlled remotely via a web browser or a native desktop application.
Such setup is already in use in [Cardinal Mini for MOD Audio](https://forum.mod.audio/t/distrho-cardinal-mini/9262/).


## Screenshots

@@ -103,77 +119,85 @@ But a couple of modules background's have their colors flipped, because damn we

At the moment the following 3rd-party modules are provided:

- 21kHz
- 8Mode
- Aaron Static
- AlgoritmArte
- Amalgamated Harmonics
- Animated Circuits
- Arable Instruments
- Aria Salvatrice
- AS
- Audible Instruments
- Autinn
- Axioma
- Bacon Music
- Befaco
- Bidoo
- Bogaudio
- Catro/Modulo
- cf
- ChowDSP
- DrumKit
- E-Series
- ExpertSleepers Encoders
- Extratone
- Fehler Fabrik
- forsitan modulare
- Fundamental
- Glue the Giant
- GoodSheperd
- Grande
- Hampton Harmonics
- HetrickCV
- ihtsyn
- Impromptu
- JW-Modules
- kocmoc
- LifeFormModular
- Lilac Loop
- Little Utils
- Lomas Modules
- Lyrae Modules
- Meander
- MindMeld
- ML Modules
- Mockba Modular
- Mog
- mscHack
- MSM
- Myth
- Nonlinear Circuits
- Orbits
- Parable Instruments
- Path Set
- PinkTrombone
- Prism
- rackwindows
- repelzen
- Sonus Modular
- Starling Via
- stocaudio
- unless_modules
- Valley
- Voxglitch
- WhatTheRack
- ZetaCarinae
- ZZC
- [21kHz](https://github.com/netboy3/21kHz-rack-plugins)
- [8Mode](https://github.com/8Mode/8Mode-VCV_Modules)
- [Aaron Static](https://github.com/aaronstatic/AaronStatic_modules)
- [alef's bits](https://github.com/alefnull/alefsbits)
- [AlgoritmArte](https://github.com/algoritmarte/AlgoritmarteVCVPlugin)
- [Amalgamated Harmonics](https://github.com/jhoar/AmalgamatedHarmonics)
- [Animated Circuits](https://github.com/AnimatedCircuits/RackModules)
- [Arable Instruments](https://github.com/adbrant/ArableInstruments)
- [Aria Salvatrice](https://aria.dog/modules/)
- [AS](https://github.com/AScustomWorks/AS)
- [Audible Instruments](https://vcvrack.com/AudibleInstruments)
- [Autinn](https://github.com/NikolaiVChr/Autinn)
- [Axioma](https://github.com/kauewerner/Axioma)
- [Bacon Music](https://github.com/baconpaul/BaconPlugs)
- [Befaco](https://github.com/VCVRack/Befaco)
- [Bidoo](https://github.com/sebastien-bouffier/Bidoo)
- [Bogaudio](https://github.com/bogaudio/BogaudioModules)
- [Catro/Modulo](https://github.com/catronomix/catro-modulo)
- [cf](https://github.com/cfoulc/cf)
- [ChowDSP](https://github.com/jatinchowdhury18/ChowDSP-VCV)
- [dBiz](https://github.com/dBiz/dBiz)
- [DrumKit](https://svmodular.com/plugin/vcv/drumkit.html)
- [EnigmaCurry](https://github.com/EnigmaCurry/EnigmaCurry-vcv-pack)
- [E-Series](https://github.com/VCVRack/ESeries)
- [ExpertSleepers Encoders](https://expert-sleepers.co.uk/vcvrack_encoders.html)
- [Extratone](http://extratone.xyz/modules)
- [Fehler Fabrik](https://github.com/RCameron93/FehlerFabrik)
- [forsitan modulare](https://github.com/gosub/forsitan-modulare)
- [Fundamental](https://github.com/VCVRack/Fundamental)
- [Glue the Giant](https://github.com/gluethegiant/gtg-rack)
- [GoodSheperd](https://github.com/jensschulze/GoodSheperd)
- [Grande](https://github.com/dbgrande/GrandeModular)
- [H4N4 Modules](https://github.com/hannakoppelaar/h4n4-modules)
- [Hampton Harmonics](https://gitlab.com/hampton-harmonics/hampton-harmonics-modules)
- [HetrickCV](https://github.com/mhetrick/hetrickcv)
- [ihtsyn](https://github.com/nysthi/ihtsyn)
- [Impromptu](https://github.com/MarcBoule/ImpromptuModular)
- [JW-Modules](https://github.com/jeremywen/JW-Modules)
- [kocmoc](https://github.com/janne808/kocmoc-rack-modules)
- [LifeFormModular](https://github.com/TimeControlledOrganism/LifeFormModular)
- [Lilac Loop](https://grough.github.io/lilac-loop-vcv)
- [Little Utils](https://github.com/mgunyho/Little-Utils)
- [Lomas Modules](https://github.com/LomasModules/LomasModules)
- [Lyrae Modules](https://github.com/VegaDeftwing/LyraeModules)
- [Meander](https://github.com/knchaffin/Meander)
- [MindMeld](https://github.com/MarcBoule/MindMeldModular)
- [ML Modules](https://github.com/martin-lueders/ML_modules)
- [Mockba Modular](https://github.com/MockbaTheBorg/MockbaModular)
- [Mog](https://github.com/JustMog/Mog-VCV)
- [mscHack](https://github.com/mschack/VCV-Rack-Plugins)
- [MSM](https://github.com/netboy3/MSM-vcvrack-plugin)
- [Myth](https://github.com/Ahineya/vcv-myth-plugin)
- [Nonlinear Circuits](https://github.com/mhetrick/nonlinearcircuits)
- [Orbits](https://github.com/RareBreeds/Orbits)
- [Parable Instruments](https://github.com/adbrant/ArableInstruments)
- [Path Set](https://github.com/patheros/PathSetModules)
- [PinkTrombone](https://github.com/VegaDeftwing/PinkTromboneVCV)
- [Prism](https://github.com/SteveRussell33/Prism)
- [rackwindows](https://github.com/n0jo/rackwindows)
- [RebelTech](https://github.com/hemmer/rebel-tech-vcv)
- [repelzen](https://github.com/wiqid/repelzen)
- [Sapphire](https://github.com/cosinekitty/sapphire)
- [Sonus Modular](https://gitlab.com/sonusdept/sonusmodular)
- [stocaudio](https://github.com/aptrn/stocaudio-modules)
- [Starling Via](https://github.com/starlingcode/Via-for-Rack)
- [Stoermelder Pack-One](https://github.com/stoermelder/vcvrack-packone)
- [Surge XT](https://github.com/surge-synthesizer/surge-rack)
- [unless_modules](https://gitlab.com/unlessgames/unless_modules)
- [Valley](https://github.com/ValleyAudio/ValleyRackFree)
- [Voxglitch](https://github.com/clone45/voxglitch)
- [WhatTheRack](https://github.com/korfuri/WhatTheRack)
- [ZetaCarinae](https://github.com/mhampton/ZetaCarinaeModules)
- [ZZC](https://github.com/zezic/ZZC)

Additionally Cardinal provides its own modules for DAW/Host automation, time position, audio to CV pitch conversion and internal plugin hosting.

### Adding modules

Install new modules on a Cardinal build is not possible, but we can add new modules to the build.
Installing new modules on a Cardinal build is not possible, but we can integrate existing open-source modules to be part of Cardinal.
Details on this are available [here](https://github.com/DISTRHO/Cardinal/discussions/28).
Also check [this wiki page](https://github.com/DISTRHO/Cardinal/wiki/Possible-modules-to-include)
where we discuss possible modules to include.
@@ -223,7 +247,6 @@ Other relevant reasons include:

- LV2 plugin version from the start
- Proper dark mode support
- Proper optimized build (because all code is compiled to a single file, we can use LTO over the whole thing)
- Real CV ports to and from the plugin
- Removing online access from the plugin and included modules (no phone-home here!)
- Works as a test case for [DPF](https://github.com/DISTRHO/DPF/) and [Carla](https://github.com/falkTX/Carla/)
@@ -250,4 +273,4 @@ An overview of the included code and linked submodules can be seen [here](docs/L
## Community chat

Currently we are all on #cardinal IRC room in irc.libera.chat server.
Come join us in your favorite IRC client or through a Matrix bridge.
Come join us in your favorite IRC client.

+ 1
- 1
carla

@@ -1 +1 @@
Subproject commit 963f194b0ed93829188ffda23320b1dc848f07d8
Subproject commit 41f07e119252b8b14627bec8345cb7304485a815

+ 164
- 125
deps/Makefile View File

@@ -4,76 +4,27 @@
# Created by falkTX
#

# --------------------------------------------------------------
# Import base definitions

DISTRHO_NAMESPACE = CardinalDISTRHO
DGL_NAMESPACE = CardinalDGL
USE_NANOVG_FBO = true
WASM_EXCEPTIONS = true
include ../dpf/Makefile.base.mk

# --------------------------------------------------------------
# Build config

ifeq ($(BSD),true)
SYSDEPS ?= true
else
SYSDEPS ?= false
endif

ifeq ($(SYSDEPS),true)
DEP_PATH = $(abspath sysroot)
else
DEP_PATH = $(abspath ../src/Rack/dep)
endif

# --------------------------------------------------------------
# custom build flags

BASE_FLAGS += -I../include
BASE_FLAGS += -I../include/simd-compat

ifeq ($(HEADLESS),true)
ifeq ($(WITH_LTO),true)
BASE_FLAGS += -ffat-lto-objects
endif
endif

ifneq ($(SYSDEPS),true)
BASE_FLAGS += -DZSTDLIB_VISIBILITY=
endif

ifneq ($(HAIKU),true)
ifneq ($(WASM),true)
BASE_FLAGS += -pthread
endif
endif

ifeq ($(WINDOWS),true)
BASE_FLAGS += -D_USE_MATH_DEFINES
BASE_FLAGS += -DWIN32_LEAN_AND_MEAN
BASE_FLAGS += -I../include/mingw-compat
BASE_FLAGS += -I../include/mingw-std-threads
endif

BUILD_C_FLAGS += -fno-finite-math-only -fno-strict-aliasing
BUILD_CXX_FLAGS += -fno-finite-math-only -fno-strict-aliasing

# Rack code is not tested for this flag, unset it
BUILD_CXX_FLAGS += -U_GLIBCXX_ASSERTIONS -Wp,-U_GLIBCXX_ASSERTIONS
ROOT = ..
include $(ROOT)/Makefile.base.mk

# --------------------------------------------------------------
# override VCV arch.mk stuff so we can build more architectures

ifeq ($(CPU_ARM32),true)
ARCH_NAME = arm
MACHINE = i686-the-rack
MACHINE = arm64
else ifeq ($(CPU_ARM64),true)
ARCH_NAME = arm64
MACHINE = x86_64-the-rack
MACHINE = arm64
else ifeq ($(CPU_I386),true)
ARCH_NAME = i686
MACHINE = x86_64
else ifeq ($(CPU_RISCV64),true)
ARCH_NAME = riscv64
MACHINE = arm64
else ifeq ($(WASM),true)
MACHINE = i686-wasm
ARCH_NAME = wasm
MACHINE = x86_64
else
MACHINE = $(TARGET_MACHINE)
endif
@@ -105,7 +56,7 @@ SPACE +=

CMAKE = cmake
CMAKE += -DCMAKE_INSTALL_LIBDIR=lib
CMAKE += -DCMAKE_INSTALL_PREFIX='$(DEP_PATH)'
CMAKE += -DCMAKE_INSTALL_PREFIX='$(RACK_DEP_PATH)'
CMAKE += -DBUILD_SHARED_LIBS=OFF

# make sure debug/release matches
@@ -145,6 +96,27 @@ ifeq ($(shell uname -s),Darwin)
CMAKE += -DCMAKE_CROSSCOMPILING=ON
CMAKE += -DCMAKE_SYSTEM_NAME=Generic
endif
CMAKE += -DCMAKE_SKIP_COMPATIBILITY_TESTS=1
CMAKE += -DCMAKE_SIZEOF_CHAR=1
CMAKE += -DCMAKE_SIZEOF_UNSIGNED_SHORT=2
CMAKE += -DCMAKE_SIZEOF_SHORT=2
CMAKE += -DCMAKE_SIZEOF_INT=4
CMAKE += -DCMAKE_SIZEOF_UNSIGNED_LONG=4
CMAKE += -DCMAKE_SIZEOF_UNSIGNED_INT=4
CMAKE += -DCMAKE_SIZEOF_LONG=4
CMAKE += -DCMAKE_SIZEOF_VOID_P=4
CMAKE += -DCMAKE_SIZEOF_FLOAT=4
CMAKE += -DCMAKE_SIZEOF_DOUBLE=8
CMAKE += -DCMAKE_C_SIZEOF_DATA_PTR=4
CMAKE += -DCMAKE_CXX_SIZEOF_DATA_PTR=4
CMAKE += -DCMAKE_HAVE_LIMITS_H=1
CMAKE += -DCMAKE_HAVE_UNISTD_H=1
CMAKE += -DCMAKE_HAVE_PTHREAD_H=1
CMAKE += -DCMAKE_HAVE_SYS_PRCTL_H=1
CMAKE += -DCMAKE_WORDS_BIGENDIAN=0
CMAKE += -DCMAKE_DL_LIBS=''
CMAKE += -DCMAKE_C_BYTE_ORDER=LITTLE_ENDIAN
CMAKE += -DCMAKE_CXX_BYTE_ORDER=LITTLE_ENDIAN
endif

# fix cross-compilation for windows
@@ -158,7 +130,7 @@ endif
# Fix up configure

CONFIGURE = ./configure
CONFIGURE += --prefix="$(DEP_PATH)"
CONFIGURE += --prefix="$(RACK_DEP_PATH)"
CONFIGURE += --host=$(TARGET_MACHINE)
CONFIGURE += --enable-static
CONFIGURE += --disable-shared
@@ -167,6 +139,7 @@ CONFIGURE += --disable-alsa
# NOTE speex fails to build when neon is enabled, so we disable that
CONFIGURE += --disable-neon
# NOTE libsamplerate fails with invalid host, so we force ac_cv_host
CONFIGURE += ac_cv_build=$(TARGET_MACHINE)
CONFIGURE += ac_cv_host=$(TARGET_MACHINE)

# --------------------------------------------------------------
@@ -200,58 +173,54 @@ DEP_MAKE2 += CONFIGURE="$(ENV) $(CONFIGURE)"
# --------------------------------------------------------------
# Rack internal dependencies target

$(DEP_PATH)/lib/%.a:
$(DEP_MAKE2) -C $(DEP_PATH) lib/$*.a
$(RACK_DEP_PATH)/lib/%.a:
$(DEP_MAKE2) -C $(RACK_DEP_PATH) lib/$*.a

$(DEP_PATH)/jansson-2.12:
$(DEP_MAKE2) -C $(DEP_PATH) jansson-2.12
$(RACK_DEP_PATH)/jansson-2.12:
$(DEP_MAKE2) -C $(RACK_DEP_PATH) jansson-2.12

# libarchive: skip shared lib and ensure libzstd is enabled
$(DEP_PATH)/lib/libarchive.a: $(DEP_PATH)/lib/libzstd.a $(DEP_PATH)/libarchive-3.4.3/.stamp-patched
$(RACK_DEP_PATH)/lib/libarchive.a: $(RACK_DEP_PATH)/lib/libzstd.a $(RACK_DEP_PATH)/libarchive-3.4.3/.stamp-patched

$(DEP_PATH)/lib/libarchive_static.a: $(DEP_PATH)/lib/libzstd.a $(DEP_PATH)/libarchive-3.4.3/.stamp-patched
$(RACK_DEP_PATH)/lib/libarchive_static.a: $(RACK_DEP_PATH)/lib/libzstd.a $(RACK_DEP_PATH)/libarchive-3.4.3/.stamp-patched

$(DEP_PATH)/libarchive-3.4.3/.stamp-patched:
$(DEP_MAKE2) -C $(DEP_PATH) libarchive-3.4.3
sed -i -e "618,625d" $(DEP_PATH)/libarchive-3.4.3/CMakeLists.txt
awk 'NR==616{print " SET(HAVE_LIBZSTD 1)"}1' $(DEP_PATH)/libarchive-3.4.3/CMakeLists.txt > $(DEP_PATH)/libarchive-3.4.3/CMakeLists.txt2
mv $(DEP_PATH)/libarchive-3.4.3/CMakeLists.txt2 $(DEP_PATH)/libarchive-3.4.3/CMakeLists.txt
sed -i -e "238,243d" $(DEP_PATH)/libarchive-3.4.3/libarchive/CMakeLists.txt
sed -i -e "s/TARGETS archive archive_static/TARGETS archive_static/" $(DEP_PATH)/libarchive-3.4.3/libarchive/CMakeLists.txt
$(RACK_DEP_PATH)/libarchive-3.4.3/.stamp-patched:
$(DEP_MAKE2) -C $(RACK_DEP_PATH) libarchive-3.4.3
sed -i -e "618,625d" $(RACK_DEP_PATH)/libarchive-3.4.3/CMakeLists.txt
awk 'NR==616{print " SET(HAVE_LIBZSTD 1)"}1' $(RACK_DEP_PATH)/libarchive-3.4.3/CMakeLists.txt > $(RACK_DEP_PATH)/libarchive-3.4.3/CMakeLists.txt2
mv $(RACK_DEP_PATH)/libarchive-3.4.3/CMakeLists.txt2 $(RACK_DEP_PATH)/libarchive-3.4.3/CMakeLists.txt
sed -i -e "238,243d" $(RACK_DEP_PATH)/libarchive-3.4.3/libarchive/CMakeLists.txt
sed -i -e "s/TARGETS archive archive_static/TARGETS archive_static/" $(RACK_DEP_PATH)/libarchive-3.4.3/libarchive/CMakeLists.txt
touch $@

# libsamplerate: skip tests, fails to build in some systems and are not needed or wanted anyway
$(DEP_PATH)/lib/libsamplerate.a: $(DEP_PATH)/libsamplerate-0.1.9/.stamp-patched
$(RACK_DEP_PATH)/lib/libsamplerate.a: $(RACK_DEP_PATH)/libsamplerate-0.1.9/.stamp-patched

$(DEP_PATH)/libsamplerate-0.1.9/.stamp-patched:
$(DEP_MAKE2) -C $(DEP_PATH) libsamplerate-0.1.9
sed -i -e "s/src doc examples tests/src/" $(DEP_PATH)/libsamplerate-0.1.9/Makefile.in
$(RACK_DEP_PATH)/libsamplerate-0.1.9/.stamp-patched:
$(DEP_MAKE2) -C $(RACK_DEP_PATH) libsamplerate-0.1.9
sed -i -e "s/src doc examples tests/src/" $(RACK_DEP_PATH)/libsamplerate-0.1.9/Makefile.in
touch $@

# libspeexdsp: hide symbols
$(DEP_PATH)/lib/libspeexdsp.a: $(DEP_PATH)/speexdsp-SpeexDSP-1.2rc3/.stamp-patched

$(DEP_PATH)/speexdsp-SpeexDSP-1.2rc3/.stamp-patched:
$(DEP_MAKE2) -C $(DEP_PATH) speexdsp-SpeexDSP-1.2rc3 \
WGET="wget -c http://downloads.xiph.org/releases/speex/speexdsp-1.2rc3.tar.gz && mv speexdsp-1.2rc3.tar.gz speexdsp-SpeexDSP-1.2rc3.tgz #" \
SHA256SUM="true" \
UNTAR="mkdir -p speexdsp-SpeexDSP-1.2rc3 && tar -x --strip-components=1 --directory=$(DEP_PATH)/speexdsp-SpeexDSP-1.2rc3 -f"
sed -i -e "s/#pragma GCC visibility push/#error we dont want this/" $(DEP_PATH)/speexdsp-SpeexDSP-1.2rc3/configure
$(RACK_DEP_PATH)/lib/libspeexdsp.a: $(RACK_DEP_PATH)/speexdsp/.stamp-patched

$(RACK_DEP_PATH)/speexdsp/.stamp-patched:
sed -i -e 's/__attribute__((visibility("default")))//' $(RACK_DEP_PATH)/speexdsp/configure.ac
touch $@

# custom zstd build for only building static libs
$(DEP_PATH)/lib/libzstd.a: $(DEP_PATH)/zstd-1.4.5/.stamp-patched
cd $(DEP_PATH)/zstd-1.4.5/build/cmake && $(CMAKE) -DZSTD_BUILD_STATIC=ON -DZSTD_BUILD_PROGRAMS=OFF -DZSTD_BUILD_SHARED=OFF -DZSTD_MULTITHREAD_SUPPORT=OFF .
$(DEP_MAKE2) -C $(DEP_PATH)/zstd-1.4.5/build/cmake
$(DEP_MAKE2) -C $(DEP_PATH)/zstd-1.4.5/build/cmake install
$(RACK_DEP_PATH)/lib/libzstd.a: $(RACK_DEP_PATH)/zstd-1.4.5/.stamp-patched
cd $(RACK_DEP_PATH)/zstd-1.4.5/build/cmake && $(CMAKE) -DZSTD_BUILD_STATIC=ON -DZSTD_BUILD_PROGRAMS=OFF -DZSTD_BUILD_SHARED=OFF -DZSTD_MULTITHREAD_SUPPORT=OFF .
$(DEP_MAKE2) -C $(RACK_DEP_PATH)/zstd-1.4.5/build/cmake
$(DEP_MAKE2) -C $(RACK_DEP_PATH)/zstd-1.4.5/build/cmake install

# zstd cmake is borked, see https://github.com/facebook/zstd/issues/1401
# zstd also fails to build on old systems, patch that too
$(DEP_PATH)/zstd-1.4.5/.stamp-patched:
$(DEP_MAKE2) -C $(DEP_PATH) zstd-1.4.5
sed -i -e "56,66d" $(DEP_PATH)/zstd-1.4.5/build/cmake/CMakeModules/AddZstdCompilationFlags.cmake
sed -i -e "146,175d" $(DEP_PATH)/zstd-1.4.5/programs/util.c
sed -i -e "142,144d" $(DEP_PATH)/zstd-1.4.5/programs/util.c
$(RACK_DEP_PATH)/zstd-1.4.5/.stamp-patched:
$(DEP_MAKE2) -C $(RACK_DEP_PATH) zstd-1.4.5
sed -i -e "56,66d" $(RACK_DEP_PATH)/zstd-1.4.5/build/cmake/CMakeModules/AddZstdCompilationFlags.cmake
sed -i -e "146,175d" $(RACK_DEP_PATH)/zstd-1.4.5/programs/util.c
sed -i -e "142,144d" $(RACK_DEP_PATH)/zstd-1.4.5/programs/util.c
touch $@

# --------------------------------------------------------------
@@ -272,53 +241,123 @@ else ifeq ($(MACOS),true)
QUICKJS_MAKE_FLAGS += CONFIG_DARWIN=y
endif

$(DEP_PATH)/lib/libquickjs.a:
$(RACK_DEP_PATH)/lib/libquickjs.a:
$(DEP_MAKE) $(QUICKJS_MAKE_FLAGS) -C $(CURDIR)/QuickJS
install -d $(DEP_PATH)/include
install -d $(DEP_PATH)/lib
install -d $(RACK_DEP_PATH)/include
install -d $(RACK_DEP_PATH)/lib
install -m644 $(CURDIR)/QuickJS/libquickjs.a $@
install -m644 $(CURDIR)/QuickJS/quickjs.h $(DEP_PATH)/include/quickjs.h
install -m644 $(CURDIR)/QuickJS/quickjs.h $(RACK_DEP_PATH)/include/quickjs.h

# --------------------------------------------------------------
# SurgeXT target

SURGE_DEP_PATH = $(abspath surge-build)
SURGE_SRC_PATH = $(abspath ../plugins/surgext/surge)
SURGE_NAMES = HysteresisProcessing Patch SolverType Tunings Wavetable clouds ghc plaits stmlib

SURGE_CXX_FLAGS = $(filter-out -fsingle-precision-constant,$(filter-out -std=gnu++11,$(BUILD_CXX_FLAGS)))
SURGE_CXX_FLAGS += $(foreach n,$(SURGE_NAMES),-D$(n)=surgext$(n))

# fix build with gcc13
SURGE_CXX_FLAGS += -include cstdint

# fix JUCE build https://github.com/juce-framework/JUCE/issues/374
ifeq ($(CPU_I386),true)
SURGE_CXX_FLAGS += -D__sigemptyset=sigemptyset
endif

# use custom JUCE from DISTRHO and Carla
SURGE_CXX_FLAGS += -I$(abspath ../carla/source/modules)

# SIMD must always be enabled, even in debug builds
ifeq ($(NOSIMD),true)
SURGE_CXX_FLAGS += -DCARDINAL_NOSIMD
else ifeq ($(DEBUG),true)
ifeq ($(WASM),true)
SURGE_CXX_FLAGS += -msse -msse2 -msse3 -msimd128
else ifeq ($(CPU_ARM32),true)
SURGE_CXX_FLAGS += -mfpu=neon-vfpv4 -mfloat-abi=hard
else ifeq ($(CPU_I386_OR_X86_64),true)
SURGE_CXX_FLAGS += -msse -msse2 -mfpmath=sse
endif
endif

# possibly use fftw?
# ifeq ($(shell $(PKG_CONFIG) --exists fftw3 fftw3f && echo true),true)
# SURGE_CXX_FLAGS += -DJUCE_DSP_USE_STATIC_FFTW=1
# endif

# JUCE_USE_CURL
SURGE_ENV = env \
AR=$(AR) \
CC=$(CC) \
CXX=$(CXX) \
CFLAGS='$(BUILD_C_FLAGS) -w' \
CXXFLAGS='$(SURGE_CXX_FLAGS) -w' \
LDFLAGS='$(LINK_FLAGS)'

SURGE_LIB = $(SURGE_DEP_PATH)/src/common/libsurge-common.a

$(SURGE_LIB): $(SURGE_DEP_PATH)/Makefile
$(DEP_MAKE) -C $(SURGE_DEP_PATH) surge-common

$(SURGE_DEP_PATH)/Makefile: $(SURGE_SRC_PATH)/CMakeLists.txt
mkdir -p $(SURGE_DEP_PATH)
cd $(SURGE_DEP_PATH) && \
$(SURGE_ENV) $(CMAKE) \
-DSURGE_COMPILE_BLOCK_SIZE=8 \
-DSURGE_SKIP_AIRWINDOWS=TRUE \
-DSURGE_SKIP_JUCE_FOR_RACK=TRUE \
-DSURGE_SKIP_LUA=TRUE \
-DSURGE_SKIP_ODDSOUND_MTS=TRUE \
-DSURGE_JUCE_PATH=$(abspath ../carla/source) \
-DSURGE_SIMDE_PATH=$(abspath ../src/Rack/dep/simde) \
$(SURGE_SRC_PATH)

# --------------------------------------------------------------
# Build targets

TARGETS += $(DEP_PATH)/lib/libjansson.a
TARGETS += $(DEP_PATH)/lib/libquickjs.a
TARGETS += $(DEP_PATH)/lib/libsamplerate.a
TARGETS += $(DEP_PATH)/lib/libspeexdsp.a
ifneq ($(NOPLUGINS),true)
TARGETS += $(SURGE_LIB)
endif

TARGETS += $(RACK_DEP_PATH)/lib/libjansson.a
TARGETS += $(RACK_DEP_PATH)/lib/libquickjs.a
TARGETS += $(RACK_DEP_PATH)/lib/libsamplerate.a
TARGETS += $(RACK_DEP_PATH)/lib/libspeexdsp.a

ifeq ($(WINDOWS),true)
TARGETS += $(DEP_PATH)/lib/libarchive_static.a
TARGETS += $(RACK_DEP_PATH)/lib/libarchive_static.a
else
TARGETS += $(DEP_PATH)/lib/libarchive.a
TARGETS += $(RACK_DEP_PATH)/lib/libarchive.a
endif

TARGETS += $(DEP_PATH)/lib/libzstd.a
TARGETS += $(RACK_DEP_PATH)/lib/libzstd.a

all: $(TARGETS)

clean:
$(DEP_MAKE) $(QUICKJS_MAKE_FLAGS) -C $(CURDIR)/QuickJS clean
rm -f $(TARGETS)
rm -f $(DEP_PATH)/*.tgz
rm -f $(DEP_PATH)/*.tar.gz
rm -rf $(DEP_PATH)/bin
rm -rf $(DEP_PATH)/include
rm -rf $(DEP_PATH)/lib
rm -rf $(DEP_PATH)/share
rm -rf $(DEP_PATH)/jansson-2.12
rm -rf $(DEP_PATH)/libarchive-3.4.3
rm -rf $(DEP_PATH)/libsamplerate-0.1.9
rm -rf $(DEP_PATH)/speexdsp-SpeexDSP-1.2rc3
rm -rf $(DEP_PATH)/zstd-1.4.5
rm -f $(RACK_DEP_PATH)/*.tgz
rm -f $(RACK_DEP_PATH)/*.tar.gz
rm -rf $(RACK_DEP_PATH)/bin
rm -rf $(RACK_DEP_PATH)/include
rm -rf $(RACK_DEP_PATH)/lib
rm -rf $(RACK_DEP_PATH)/share
rm -rf $(RACK_DEP_PATH)/jansson-2.12
rm -rf $(RACK_DEP_PATH)/libarchive-3.4.3
rm -rf $(RACK_DEP_PATH)/libsamplerate-0.1.9
rm -rf $(RACK_DEP_PATH)/zstd-1.4.5
rm -rf $(SURGE_DEP_PATH)

download: \
$(DEP_PATH)/jansson-2.12 \
$(DEP_PATH)/libarchive-3.4.3/.stamp-patched \
$(DEP_PATH)/libsamplerate-0.1.9/.stamp-patched \
$(DEP_PATH)/speexdsp-SpeexDSP-1.2rc3/.stamp-patched \
$(DEP_PATH)/zstd-1.4.5/.stamp-patched
$(RACK_DEP_PATH)/jansson-2.12 \
$(RACK_DEP_PATH)/libarchive-3.4.3/.stamp-patched \
$(RACK_DEP_PATH)/libsamplerate-0.1.9/.stamp-patched \
$(RACK_DEP_PATH)/zstd-1.4.5/.stamp-patched

quickjs: $(DEP_PATH)/lib/libquickjs.a
quickjs: $(RACK_DEP_PATH)/lib/libquickjs.a
surge: $(SURGE_LIB)

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

+ 1
- 1
deps/PawPaw

@@ -1 +1 @@
Subproject commit 4f7f9eb6ff1677606a85fe701bbb535f8fe7086c
Subproject commit 6a3c6a65a89abe221858c3f7635140074506bfc3

+ 1
- 1
deps/unzipfx/Makefile.win32 View File

@@ -21,7 +21,7 @@ all: unzipfx2cat.exe
unzipfx2cat.exe: $(OBJ)
$(CC) $^ $(LINK_FLAGS) -o $@

icon.o: ../../../resources/ico/carla.rc
icon.o: ../../utils/distrho.rc
$(WINDRES) -i $< -o $@ -O coff

clean:


+ 40
- 10
docs/BUILDING.md View File

@@ -22,7 +22,7 @@ Use them as `make SOMEOPTION=SOMEVALUE` syntax. You can specify as many options
Developer related options:

* `DEBUG=true` build non-stripped debug binaries (terrible performance, only useful for developers)
* `NOPLUGINS=true` build only the Cardinal Core plugins (not recommended, only useful for developers)
* `NOSIMD=true` build without SIMD (not recommended, only useful for developers)

Packaging related options:

@@ -51,7 +51,7 @@ Dependencies for using system libraries:

```
# common
sudo pkg install -A dbus libglvnd liblo libsndfile libX11 libXcursor libXext libXrandr python3
sudo pkg install -A cmake dbus fftw libglvnd liblo libsndfile libX11 libXcursor libXext libXrandr python3
# system libraries
sudo pkg install -A libarchive libsamplerate jansson speexdsp
```
@@ -67,7 +67,7 @@ Dependencies for using system libraries, that is, with `SYSDEPS=true`:

```
# common
sudo pacman -S dbus file libgl liblo libsndfile libx11 libxcursor libxext libxrandr python3
sudo pacman -S cmake dbus file fftw libgl liblo libsndfile libx11 libxcursor libxext libxrandr python3
# system libraries
sudo pacman -S libarchive libsamplerate jansson speexdsp
```
@@ -76,9 +76,9 @@ Dependencies for vendored libraries:

```
# common
sudo pacman -S dbus file libgl liblo libsndfile libx11 libxcursor libxext libxrandr python3
sudo pacman -S cmake dbus file fftw libgl liblo libsndfile libx11 libxcursor libxext libxrandr python3
# nedeed by vendored libraries
sudo pacman -S cmake wget
sudo pacman -S wget
```

### Debian
@@ -87,7 +87,7 @@ Dependencies for using system libraries, that is, with `SYSDEPS=true`:

```
# common
sudo apt install libdbus-1-dev libgl1-mesa-dev liblo-dev libmagic-dev libsndfile1-dev libx11-dev libxcursor-dev libxext-dev libxrandr-dev python3
sudo apt install cmake libdbus-1-dev libgl1-mesa-dev liblo-dev libfftw3-dev libmagic-dev libsndfile1-dev libx11-dev libxcursor-dev libxext-dev libxrandr-dev python3
# system libraries
sudo apt install libarchive-dev libjansson-dev libsamplerate0-dev libspeexdsp-dev
```
@@ -96,9 +96,9 @@ Dependencies for vendored libraries:

```
# common
sudo apt install libdbus-1-dev libgl1-mesa-dev liblo-dev libmagic-dev libsndfile1-dev libx11-dev libxcursor-dev libxext-dev libxrandr-dev python3
sudo apt install cmake libdbus-1-dev libgl1-mesa-dev liblo-dev libfftw3-dev libmagic-dev libsndfile1-dev libx11-dev libxcursor-dev libxext-dev libxrandr-dev python3
# nedeed by vendored libraries
sudo apt install cmake wget
sudo apt install wget
```

## macOS
@@ -115,20 +115,50 @@ export CXXFLAGS="${CFLAGS}"
# make etc..
```

## Web assembly

Cardinal uses emscripten for its web version, see the official instructions on installing emscripten [here](https://emscripten.org/docs/getting_started/downloads.html).
Once installed, setup the build by importing the emscripten environment and setup the default build tools to point to them, like so:

```
source /path/to/emsdk/emsdk_env.sh
export AR=emar
export CC=emcc
export CXX=em++
export NM=emnm
export RANLIB=emranlib
export STRIP=emstrip
```

Then for the actual build we just need to force graphics rendering to use GLES2 instead of the default "desktop" OpenGL mode, like so:

```
make USE_GLES2=true # add any other relevant options..
```

You can place the generated files on a webserver, or run `emrun bin/CardinalNative.html` for an easy way to test it.

Please note the web build only contains CardinalNative, no other variants will be built.
This is expected and intentional.

## Windows

Cardinal does not support msvc, using mingw is required.
You can either cross-compile Cardinal for Windows from Linux, or install and use msys2 natively on a Windows system.
It also requires a file-system with support for symbolic links, which Windows cannot do.
For these reasons it is only possible to build Cardinal for Windows from a Linux, macOS or any regular POSIX system.

### Cross-compile

For cross-compilation, first install the relevant mingw packages.
On Ubuntu these are `binutils-mingw-w64-x86-64 g++-mingw-w64-x86-64 mingw-w64`.
Then build with `CC` and `CXX` pointing to the mingw compiler, like so:
Then build with `AR`, `CC` and `CXX` pointing to the mingw compiler tools, like so:

```
export AR=x86_64-w64-mingw32-gcc
export CC=x86_64-w64-mingw32-gcc
export CXX=x86_64-w64-mingw32-g++
export EXE_WRAPPER=wine # for running generated windows binaries
export PKG_CONFIG=false # ignore pkg-config from base system
# make etc..
```



+ 16
- 0
docs/CARDINAL-MODULES.md View File

@@ -4,6 +4,22 @@ This file contains documentation for the DISTRHO Cardinal modules.

## Main modules

### AIDA-X

![screenshot](Module_AIDA-X.png)

[AIDA-X](https://github.com/AidaDSP/AIDA-X) is an Amp Model Player leveraging AI and machine learning, with a target of providing high fidelity simulations of guitar amplifiers.
It is also possible to run entire signal chains consisting of any combination of amp, cab, dist, drive, fuzz, boost and eq.

The module loads AIDA-X files that have been trained to match a desired sound output.
Right-click on the module and select "Load model file..." to load an AIDA-X model file from disk.

A quick model pack can be downloaded from [AIDA DSP's Google Drive folder](https://drive.google.com/drive/folders/18MwNhuo9fjK8hlne6SAdhpGtL4bWsVz-).

Check out the [MOD Forum's Neural Modelling section](https://forum.mod.audio/c/neural/62) for an online place for discussion, sharing and all things related to Amp Models.

This module is a port of the [AIDA-X audio plugin](https://github.com/AidaDSP/AIDA-X), also available separately.

### Audio File

![screenshot](Module_AudioFile.png)


+ 10
- 7
docs/DIFFERENCES.md View File

@@ -20,26 +20,28 @@ Bellow follows a list of features comparing the official plugin to Cardinal.
| Contains internal modules | Core only | Everything is internal | |
| Loads external modules | Yes | No | |
| Supports closed-source modules | Yes | No | |
| Supports physical devices | Yes | No | Audio + MIDI only through the DAW/Host or via JACK in standalone |
| Plugin in AU format | No | Yes | |
| Supports physical devices | Yes | No (*) | CardinalNative binary provides native audio+midi as standalone |
| Plugin in AU format | Yes | Yes | |
| Plugin in LV2 format | No | Yes | |
| Plugin in VST2 format | Yes | Yes | |
| Plugin in VST3 format | No | Yes | |
| Plugin in CLAP format | No | WIP | |
| Plugin in VST3 format | Yes | Yes | |
| Plugin in CLAP format | Yes | Yes | |
| Plugin inside itself | No, will crash | Yes | Technical limitations prevent Rack Pro from loading inside itself |
| Module processing order | Same as insertion order | Based on cable connections | In Cardinal module processing order changes automatically depending on cable connections |
| Multi-threaded engine | Yes | No, uses host audio thread | Intentional in Cardinal, for removing jitter |
| Supports ARM systems | No | Yes | This means Apple M1 too, yes |
| Supports ARM systems | WIP | Yes | This means Apple M1 too, yes |
| Supports BSD systems | No | Yes | Available as FreeBSD port |
| Supports RISC-V systems | No | Yes | |
| Synth plugin variant | 16 ins, 16 outs | 2 ins, 2 outs | |
| FX plugin variant | 16 ins, 16 outs | 2 ins, 2 outs | |
| Raw-CV plugin variant | Unsupported | 8 audio IO + 10 CV IO | Available in JACK, LV2 and VST3 formats, not possible in AU and VST2 |
| Arbitrary parameter automation | Yes | No | Unsupported in Cardinal, tricky to do for many plugin formats at once |
| Arbitrary parameter automation | Yes | No (*) | Static 24 automatable params, use Host Params/Map modules to map them to module parameters |
| Integrated plugin host | No, Host payed separately | Yes, using Carla or Ildaeil | |
| Host sync/timing | Using MIDI signals | Using dedicated module | |
| Linux/X11 event handling | Runs on 2nd thread | Runs on main/GUI thread | |
| v1 module compatibility | No | No, but with less restrictions | Module widgets can load resources at any point |
| Online phone-home | Yes | No | Online access is strictly forbidden in Cardinal |
| Proper dark theme | No, only room brightness | Yes | All dark panel variants have explicit permission when required |
| Proper dark theme | WIP | Yes | All dark panel variants have explicit permission when required |
| Proper Linux headless mode | No, always requires X11 | Yes | |

Additionally, Cardinal contains the following built-in modules not present in the official plugin or standalone:
@@ -48,6 +50,7 @@ Additionally, Cardinal contains the following built-in modules not present in th
* Mog (never updated to v2)
* mscHack (never updated to v2)
* rackwindows
* AIDA-X
* Audio File
* Audio to CV Pitch converter
* Carla Plugin Host


BIN
docs/Docs_Remote-Control-1.png View File

Before After
Width: 688  |  Height: 607  |  Size: 163KB

BIN
docs/Docs_Remote-Control-2.png View File

Before After
Width: 688  |  Height: 607  |  Size: 28KB

+ 10
- 4
docs/FAQ.md View File

@@ -43,10 +43,16 @@ where we discuss possible modules to include.

## Changes are lost on restart

This is intentional.
Cardinal is meant to be a self-contained plugin, and as such it does not save any files whatsoever.
This includes user preferences (like list of favourites) or last used project.
As a plugin, the state will be saved together with the host/DAW project.
This is intentional. Unlike VCV Rack, Cardinal does not automatically save.

Also, different variants (main vs FX vs Synth) use different files for saving their settings, so there might be some confusion arising from that.
But on the other hand this allows you to have a different template and other defaults per variant, which is quite handy.

## Scaling/High-DPI not working properly, how to fix it?

Cardinal, using [DPF](https://github.com/DISTRHO/DPF), will try to automatically detect the system scaling and adjust to that.
On cases where that does not work you can set `DPF_SCALE_FACTOR` environment variable to a value of your choosing in order to force a custom scale factor.
Note that this applies to all DPF-based plugins and not just Cardinal.

## On BSD/Linux/X11 the menu item "Save As/Export..." does nothing



+ 32
- 1
docs/LICENSES.md View File

@@ -16,6 +16,7 @@ Bellow follows a list of all code licenses used in Cardinal and linked submodule
| 21kHz | MIT | |
| 8Mode | BSD-3-Clause | |
| Aaron Static | MIT | |
| alef's bits | GPL-3.0-or-later | |
| AlgoritmArte | GPL-3.0-or-later | |
| Amalgamated Harmonics | BSD-3-Clause | |
| Animated Circuits | GPL-3.0-or-later | |
@@ -32,7 +33,9 @@ Bellow follows a list of all code licenses used in Cardinal and linked submodule
| Catro/Modulo | BSD-3-Clause | |
| cf | BSD-3-Clause | |
| ChowDSP | GPL-3.0-or-later | |
| dBiz | GPL-3.0-or-later | |
| DrumKit | CC0-1.0 | |
| EnigmaCurry | GPL-3.0-or-later | |
| E-Series | GPL-3.0-or-later | |
| ExpertSleepers Encoders | MIT | |
| Extratone | GPL-3.0-or-later | |
@@ -42,6 +45,7 @@ Bellow follows a list of all code licenses used in Cardinal and linked submodule
| Glue the Giant | GPL-3.0-or-later | |
| GoodSheperd | GPL-3.0-or-later | |
| Grande | GPL-3.0-or-later | |
| H4N4 Modules | GPL-3.0-or-later | |
| Hampton Harmonics | MIT | |
| HetrickCV | CC0-1.0 | |
| ihtsyn | GPL-3.0-or-later | |
@@ -69,9 +73,13 @@ Bellow follows a list of all code licenses used in Cardinal and linked submodule
| Prism | BSD-3-Clause | |
| Rackwindows | MIT | |
| repelzen | GPL-3.0-or-later | |
| RebelTech | GPL-2.0-or-later | |
| Sapphire | GPL-3.0-or-later | |
| Sonus Modular | GPL-3.0-or-later | |
| Starling Via | MIT | |
| stocaudio | GPL-3.0-or-later | |
| Stoermelder Pack-One | GPL-3.0-or-later | |
| Surge XT | GPL-3.0-or-later | |
| unless_modules | GPL-3.0-or-later | |
| Valley | GPL-3.0-or-later | |
| Voxglitch | GPL-3.0-or-later | |
@@ -99,6 +107,7 @@ Below is a list of artwork licenses from plugins
| 8Mode | BSD-3-Clause | No artwork specific license provided |
| AaronStatic/* | MIT | No artwork specific license provided |
| AaronStatic/fonts/PixelOperator.ttf | CC0-1.0 | |
| alefsbits/* | GPL-3.0-or-later | No artwork specific license provided |
| Algoritmarte/* | GPL-3.0-or-later | No artwork specific license provided |
| Algoritmarte/LEDSliderGreenHandle.svg | CC-BY-NC-4.0 | |
| AmalgamatedHarmonics/* | BSD-3-Clause | No artwork specific license provided |
@@ -122,8 +131,15 @@ Below is a list of artwork licenses from plugins
| BaconPlugs/* | GPL-3.0-or-later | No artwork specific license provided |
| BaconPlugs/midi/* | CC-BY-SA-3.0-DE | |
| BaconPlugs/midi/beeth/* | ??? | Unused in Cardinal, taken from http://www.jsbach.net/ |
| BaconPlugs/1f953.svg | CC-BY-4.0 | |
| BaconPlugs/FiraMono-Regular.ttf | OFL-1.1-RFN | |
| BaconPlugs/Monitorica-Bd.ttf | CC-BY-SA-4.0 | |
| BaconPlugs/Keypunch029.json | OFL-1.1 | |
| BaconPlugs/1f953.svg | CC-BY-4.0 | |
| BaconPlugs/1f60d.svg | CC-BY-4.0 | |
| BaconPlugs/HelpActive.svg | CC0-1.0 | |
| BaconPlugs/HelpActiveSmall.svg | CC0-1.0 | |
| BaconPlugs/SABROG-*.svg | CC0-1.0 | |
| BaconPlugs/sabrog-*.svg | CC0-1.0 | |
| Bidoo/* | CC-BY-NC-ND-4.0 | [Special permission granted for runtime dark mode](https://github.com/sebastien-bouffier/Bidoo/issues/191) |
| Befaco/components/* | CC-BY-NC-4.0 | |
| Befaco/fonts/Segment7Standard.otf | OFL-1.1-RFN | |
@@ -141,8 +157,15 @@ Below is a list of artwork licenses from plugins
| cf/VT323-Regular.ttf | OFL-1.1-no-RFN | |
| ChowDSP/* | GPL-3.0-or-later | Same license as source code |
| ChowDSP/fonts/RobotoCondensed-*.ttf | Apache-2.0 | |
| dBiz/* | CC-BY-NC-ND-4.0 | |
| dBiz/DejaVuSansMono.ttf | Bitstream-Vera | |
| dBiz/ShareTechMono-Regular.ttf | OFL-1.1 | |
| DrumKit/* | CC0-1.0 | |
| DrumKit/component/NovaMono.ttf | OFL-1.1-RFN | |
| EnigmaCurry/res/fonts/dseg/* | OFL-1.1-RFN | |
| EnigmaCurry/res/fonts/Fantasque/* | OFL-1.1 | |
| EnigmaCurry/res/fonts/manrope/* | OFL-1.1 | |
| EnigmaCurry/res/*.svg | CC0-1.0 | |
| E-Series/* | Custom | Copyright © Synthesis Technology, [used and distributed with permission](LICENSE-PERMISSIONS.md#eseries-paul-schreiber--synthtech) |
| ExpertSleepers-Encoders/* | MIT | [Same license as source code](https://github.com/expertsleepersltd/vcvrack-encoders/issues/3) |
| Extratone/* | GPL-3.0-or-later | [Same license as source code](https://github.com/EaterOfSheep/Extratone/issues/7) |
@@ -153,6 +176,7 @@ Below is a list of artwork licenses from plugins
| GlueTheGiant/fonts/DSEG7-* | OFL-1.1-RFN | |
| GoodSheperd/* | GPL-3.0-or-later | No artwork specific license provided |
| GrandeModular/* | CC-BY-NC-ND-4.0 | |
| h4n4-modules/* | GPL-3.0-or-later | No artwork specific license provided |
| HamptonHarmonics/* | MIT | No artwork specific license provided |
| HamptonHarmonics/PixelOperator.ttf | CC0-1.0 | |
| HetrickCV/* | CC0-1.0 | |
@@ -201,9 +225,16 @@ Below is a list of artwork licenses from plugins
| Prism/RobotoCondensed-Regular.ttf | Apache-2.0 | |
| Rackwindows/* | MIT | [Same license as source code](https://github.com/n0jo/rackwindows/issues/15) |
| repelzen/* | CC-BY-SA-4.0 | |
| RebelTech/* | CC-BY-NC-4.0 | |
| Sapphire/* | GPL-3.0-or-later | No artwork specific license provided |
| sonusmodular/* | GPL-3.0-or-later | [Same license as source code](https://gitlab.com/sonusdept/sonusmodular/-/issues/14) |
| StarlingVia/* | MIT | No artwork specific license provided |
| stocaudio/* | GPL-3.0-or-later | No artwork specific license provided |
| stoermelder-packone/* | GPL-3.0-or-later | No artwork specific license provided |
| stoermelder-packone/fonts/RedkostComic.otf | OFL-1.1-RFN | |
| surgext/* | GPL-3.0-or-later | |
| surgext/xt/* | CC-BY-NC-SA-4.0 | |
| surgext/xt/fonts/quicksand/* | OFL-1.1-RFN | |
| unless_modules/* | CC-BY-NC-ND-4.0 | |
| unless_modules/font/CuteFont-Regular.ttf| OFL-1.1 | |
| unless_modules/font/Terminus.ttf | GPL-2.0-or-later | [Starting from v4.32, font license is OFL-1.1](https://files.ax86.net/terminus-ttf/#license) |


BIN
docs/Module_AIDA-X.png View File

Before After
Width: 690  |  Height: 760  |  Size: 91KB

+ 63
- 0
docs/OSC-REMOTE-CONTROL.md View File

@@ -0,0 +1,63 @@
# OSC Remote Control

OSC (Open Sound Control) is a protocol commonly used for remote control over the network.
Starting with version 23.09, Cardinal allows remote control of the entire patch/project and individual parameters through OSC.

Please note **OSC Remote Control is not available when using Cardinal as a plugin**, only in standalone.

## Activating remote control

Make sure you are using version 23.09 or later of Cardinal, start up the standalone (both Native and JACK variants will work) and under "Engine" menu click on "Enable OSC remote control".

![screenshot](Docs_Remote-Control-1.png "Screenshot")

This will ask you for which network port to use, Cardinal will default to 2228.
Valid range is typically between 1025 and 32767.
If unsure just stick the default value.

![screenshot](Docs_Remote-Control-2.png "Screenshot")

Depending on the OS security features you might be asked to allow network usage at this point.
If all went well opening the "Engine" menu again should show a checkmark, indicating that OSC remote control is enabled.

For the moment there is no error dialog or information in case things go wrong.
If you are unable to connect, make sure your OS network firewall settings allows opening port 2228.

## TouchOSC example setup

A TouchOSC compatible file is available [here](https://github.com/DISTRHO/Cardinal/raw/main/patches/touchosc/24-direct-fader-params.tosc).

It maps Cardinal's 24 parameters into 3 pages of sliders, 8 per page, each with a different color.
Inside Cardinal the Host Parameters and Host Parameters Map modules can be used as a way to control module knobs and other controls with it.

## Available messages

The following OSC messages are available:

#### /hello

Sending a `/hello` message will make Cardinal reply back with another hello, using `/resp` path and "hello" message.
Useful when testing if the connection works.

#### /host-param i:port f:value

Sending a `/host-param` message will set a port value of the "Host Params" module.
The port index starts from 0.

There is no reply back from Cardinal.

#### /param h:moduleId i:paramId f:value

Sending a `/param` message will change the parameter value of any loaded module.
(TODO: describe a way to find the module and param id)

There is no reply back from Cardinal.

NOTE: the first argument must of be int64 type, as regular 32-bit integer is not enough to fit the whole range of values used inside Cardinal/Rack.

#### /load b:patch-blob

Sending a `/load` message will load the patch file contained in the message.
Patch contents must be in compressed format, not plain-text json.

Cardinal replies back indicating either success or failure, using `/resp` path and "load" message.

+ 1
- 1
dpf

@@ -1 +1 @@
Subproject commit 5ddaeefc47bd215c630b372304461a62f3464924
Subproject commit 6876fd08ec9f0d1926158a4b60ed68ce9d33c6d4

+ 39
- 0
include/OpenGL/gl.h View File

@@ -0,0 +1,39 @@
/*
* DISTRHO Cardinal Plugin
* Copyright (C) 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
* published by the Free Software Foundation; either version 3 of
* the License, or any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* For a full copy of the GNU General Public License see the LICENSE file.
*/

#pragma once

#ifdef HEADLESS
# define GL_COLOR_BUFFER_BIT 0
# define GL_DEPTH_BUFFER_BIT 0
# define GL_STENCIL_BUFFER_BIT 0
# define GL_PROJECTION 0
# define GL_TRIANGLES 0
static inline void glBegin(int) {}
static inline void glEnd() {}
static inline void glColor3f(float, float, float) {}
static inline void glVertex3f(float, float, float) {}
static inline void glClear(int) {}
static inline void glClearColor(double, double, double, double) {}
static inline void glLoadIdentity() {}
static inline void glMatrixMode(int) {}
static inline void glOrtho(double, double, double, double, double, double) {}
static inline void glViewport(double, double, double, double) {}
typedef unsigned int GLuint;
#else
# include_next <OpenGL/gl.h>
#endif

+ 9
- 1
include/common.hpp View File

@@ -1,6 +1,6 @@
/*
* DISTRHO Cardinal Plugin
* Copyright (C) 2021-2022 Filipe Coelho <falktx@falktx.com>
* Copyright (C) 2021-2023 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
@@ -97,3 +97,11 @@ void async_dialog_message(const char* message, std::function<void()> action);
// opens a text input dialog, message and text can be null
// action is always triggered on close (newText can be null), must be freed if not null
void async_dialog_text_input(const char* message, const char* text, std::function<void(char* newText)> action);

// Cardinal specific config dir (might be equal to userDir)
namespace rack {
namespace asset {
extern std::string configDir;
std::string config(std::string filename = "");
}
}

+ 23
- 25
include/engine/Port.hpp View File

@@ -33,11 +33,7 @@
#include <list>

/** NOTE alignas is required in some systems in order to allow SSE usage. */
#ifndef ARCH_MAC
#define SIMD_ALIGN alignas(32)
#else
#define SIMD_ALIGN
#endif
#define SIMD_ALIGN alignas(16)


namespace rack {
@@ -82,40 +78,40 @@ struct Port {
};

/** Sets the voltage of the given channel. */
void setVoltage(float voltage, int channel = 0) {
void setVoltage(float voltage, int channel = 0) noexcept {
voltages[channel] = voltage;
}

/** Returns the voltage of the given channel.
Because of proper bookkeeping, all channels higher than the input port's number of channels should be 0V.
*/
float getVoltage(int channel = 0) {
float getVoltage(int channel = 0) const noexcept {
return voltages[channel];
}

/** Returns the given channel's voltage if the port is polyphonic, otherwise returns the first voltage (channel 0). */
float getPolyVoltage(int channel) {
float getPolyVoltage(int channel) const noexcept {
return isMonophonic() ? getVoltage(0) : getVoltage(channel);
}

/** Returns the voltage if a cable is connected, otherwise returns the given normal voltage. */
float getNormalVoltage(float normalVoltage, int channel = 0) {
float getNormalVoltage(float normalVoltage, int channel = 0) const noexcept {
return isConnected() ? getVoltage(channel) : normalVoltage;
}

float getNormalPolyVoltage(float normalVoltage, int channel) {
float getNormalPolyVoltage(float normalVoltage, int channel) const noexcept {
return isConnected() ? getPolyVoltage(channel) : normalVoltage;
}

/** Returns a pointer to the array of voltages beginning with firstChannel.
The pointer can be used for reading and writing.
*/
float* getVoltages(int firstChannel = 0) {
float* getVoltages(int firstChannel = 0) noexcept {
return &voltages[firstChannel];
}

/** Copies the port's voltages to an array of size at least `channels`. */
void readVoltages(float* v) {
void readVoltages(float* v) const noexcept {
for (int c = 0; c < channels; c++) {
v[c] = voltages[c];
}
@@ -131,14 +127,14 @@ struct Port {
}

/** Sets all voltages to 0. */
void clearVoltages() {
void clearVoltages() noexcept {
for (int c = 0; c < channels; c++) {
voltages[c] = 0.f;
}
}

/** Returns the sum of all voltages. */
float getVoltageSum() {
float getVoltageSum() const noexcept {
float sum = 0.f;
for (int c = 0; c < channels; c++) {
sum += voltages[c];
@@ -149,7 +145,7 @@ struct Port {
/** Returns the root-mean-square of all voltages.
Uses sqrt() which is slow, so use a custom approximation if calling frequently.
*/
float getVoltageRMS() {
float getVoltageRMS() const {
if (channels == 0) {
return 0.f;
}
@@ -166,22 +162,22 @@ struct Port {
}

template <typename T>
T getVoltageSimd(int firstChannel) {
T getVoltageSimd(int firstChannel) const noexcept {
return T::load(&voltages[firstChannel]);
}

template <typename T>
T getPolyVoltageSimd(int firstChannel) {
T getPolyVoltageSimd(int firstChannel) const noexcept {
return isMonophonic() ? getVoltage(0) : getVoltageSimd<T>(firstChannel);
}

template <typename T>
T getNormalVoltageSimd(T normalVoltage, int firstChannel) {
T getNormalVoltageSimd(T normalVoltage, int firstChannel) const noexcept {
return isConnected() ? getVoltageSimd<T>(firstChannel) : normalVoltage;
}

template <typename T>
T getNormalPolyVoltageSimd(T normalVoltage, int firstChannel) {
T getNormalPolyVoltageSimd(T normalVoltage, int firstChannel) const noexcept {
return isConnected() ? getPolyVoltageSimd<T>(firstChannel) : normalVoltage;
}

@@ -195,13 +191,15 @@ struct Port {
If disconnected, this does nothing (`channels` remains 0).
If 0 is given, `channels` is set to 1 but all voltages are cleared.
*/
void setChannels(int channels) {
void setChannels(int channels) noexcept {
// If disconnected, keep the number of channels at 0.
if (this->channels == 0) {
return;
}
// Set higher channel voltages to 0
for (int c = channels; c < this->channels; c++) {
if (c >= PORT_MAX_CHANNELS)
__builtin_unreachable();
voltages[c] = 0.f;
}
// Don't allow caller to set port as disconnected
@@ -214,29 +212,29 @@ struct Port {
/** Returns the number of channels.
If the port is disconnected, it has 0 channels.
*/
int getChannels() {
int getChannels() const noexcept {
return channels;
}

/** Returns whether a cable is connected to the Port.
You can use this for skipping code that generates output voltages.
*/
bool isConnected() {
bool isConnected() const noexcept {
return channels > 0;
}

/** Returns whether the cable exists and has 1 channel. */
bool isMonophonic() {
bool isMonophonic() const noexcept {
return channels == 1;
}

/** Returns whether the cable exists and has more than 1 channel. */
bool isPolyphonic() {
bool isPolyphonic() const noexcept {
return channels > 1;
}

/** Use getNormalVoltage() instead. */
DEPRECATED float normalize(float normalVoltage) {
DEPRECATED float normalize(float normalVoltage) const noexcept {
return getNormalVoltage(normalVoltage);
}
};


+ 20
- 5
include/helpers.hpp View File

@@ -1,6 +1,6 @@
/*
* DISTRHO Cardinal Plugin
* Copyright (C) 2021 Filipe Coelho <falktx@falktx.com>
* Copyright (C) 2021-2022 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
@@ -36,6 +36,12 @@

namespace rack {

#ifndef HEADLESS
namespace asset {
void updateForcingBlackSilverScrewMode(std::string slug);
}
#endif

struct CardinalPluginModelHelper : plugin::Model {
virtual app::ModuleWidget* createModuleWidgetFromEngineLoad(engine::Module* m) = 0;
virtual void removeCachedModuleWidget(engine::Module* m) = 0;
@@ -47,6 +53,11 @@ struct CardinalPluginModel : CardinalPluginModelHelper
std::unordered_map<engine::Module*, TModuleWidget*> widgets;
std::unordered_map<engine::Module*, bool> widgetNeedsDeletion;

CardinalPluginModel(const std::string slug)
{
this->slug = slug;
}

engine::Module* createModule() override
{
engine::Module* const m = new TModule;
@@ -67,6 +78,9 @@ struct CardinalPluginModel : CardinalPluginModelHelper
}
tm = dynamic_cast<TModule*>(m);
}
#ifndef HEADLESS
asset::updateForcingBlackSilverScrewMode(slug);
#endif
app::ModuleWidget* const tmw = new TModuleWidget(tm);
DISTRHO_CUSTOM_SAFE_ASSERT_RETURN(m != nullptr ? m->model->name.c_str() : "null", tmw->module == m, nullptr);
tmw->setModel(this);
@@ -81,6 +95,9 @@ struct CardinalPluginModel : CardinalPluginModelHelper
TModule* const tm = dynamic_cast<TModule*>(m);
DISTRHO_SAFE_ASSERT_RETURN(tm != nullptr, nullptr);

#ifndef HEADLESS
asset::updateForcingBlackSilverScrewMode(slug);
#endif
TModuleWidget* const tmw = new TModuleWidget(tm);
DISTRHO_SAFE_ASSERT_RETURN(tmw->module == m, nullptr);
tmw->setModel(this);
@@ -107,11 +124,9 @@ struct CardinalPluginModel : CardinalPluginModelHelper
};

template <class TModule, class TModuleWidget>
CardinalPluginModel<TModule, TModuleWidget>* createModel(std::string slug)
CardinalPluginModel<TModule, TModuleWidget>* createModel(const std::string slug)
{
CardinalPluginModel<TModule, TModuleWidget>* const o = new CardinalPluginModel<TModule, TModuleWidget>();
o->slug = slug;
return o;
return new CardinalPluginModel<TModule, TModuleWidget>(slug);
}

}


+ 9
- 3
include/linux-compat/execinfo.h View File

@@ -17,19 +17,25 @@

#pragma once

#define pthread_setname_np(...)
#include <pthread.h>

int pthread_getcpuclockid(pthread_t, clockid_t* const clock_id)
static inline
int pthread_getcpuclockid_custom(pthread_t, clockid_t* const clock_id)
{
*clock_id = CLOCK_REALTIME;
return 0;
}

static int backtrace(void**, int)
#define pthread_getcpuclockid pthread_getcpuclockid_custom
#define pthread_setname_np(...)

static inline
int backtrace(void**, int)
{
return 0;
}

static inline
char** backtrace_symbols(void* const*, int)
{
return nullptr;


+ 0
- 58
include/mingw-compat/cstdio View File

@@ -1,58 +0,0 @@
/*
* DISTRHO Cardinal Plugin
* Copyright (C) 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
* published by the Free Software Foundation; either version 3 of
* the License, or any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* For a full copy of the GNU General Public License see the LICENSE file.
*/

#pragma once

/* On mingw stdio functions like printf are not inline, and thus get defined every time they are used.
* Its <cstdio> also does `#undef printf` which invalidates our macros :(
* We go through a few steps to ensure unique symbol names.
*/
#ifdef STDIO_OVERRIDE

// helper macros
# define STDIO_OVERRIDE_HELPER(NS, SEP, FN) NS ## SEP ## FN
# define STDIO_OVERRIDE_MACRO(NS, FN) STDIO_OVERRIDE_HELPER(NS, _, FN)

// step 1: prefix the needed stdio functions
# define printf STDIO_OVERRIDE_MACRO(STDIO_OVERRIDE, printf)

// step 2: inlude <stdio.h> which will use our prefixed names
# include <stdio.h>

// step 3: undef and define dummy functions required for <cstdio> (it uses `using ::printf` syntax)
# undef printf
static inline void printf() {}

// step 4: we can safely include <cstdio> now
# include_next <cstdio>

// step 5: define the same macros as in step 1
# define printf STDIO_OVERRIDE_MACRO(STDIO_OVERRIDE, printf)

// step 6: place the macro prefixed names in std namespace
/*
namespace std {
using ::printf;
}
*/

#else // STDIO_OVERRIDE

// if STDIO_OVERRIDE is not defined, we have nothing to do
# include_next <cstdio>

#endif // STDIO_OVERRIDE

+ 2
- 2
include/mingw-compat/mutex View File

@@ -1,6 +1,6 @@
/*
* DISTRHO Cardinal Plugin
* Copyright (C) 2021 Filipe Coelho <falktx@falktx.com>
* Copyright (C) 2021-2023 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
@@ -17,8 +17,8 @@

#pragma once
#include_next <mutex>
#include "mingw.mutex.h"

// fix macro pollution from Windows headers
#undef IN
#undef OUT
#undef far


+ 2
- 2
include/mingw-compat/thread View File

@@ -1,6 +1,6 @@
/*
* DISTRHO Cardinal Plugin
* Copyright (C) 2021 Filipe Coelho <falktx@falktx.com>
* Copyright (C) 2021-2023 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
@@ -17,8 +17,8 @@

#pragma once
#include_next <thread>
#include "mingw.thread.h"

// fix macro pollution from Windows headers
#undef IN
#undef OUT
#undef far


+ 0
- 1
include/mingw-std-threads

@@ -1 +0,0 @@
Subproject commit f6365f900fb9b1cd6014c8d1cf13ceacf8faf3de

include/rack.hpp → include/simd-compat/emmintrin.h View File

@@ -1,6 +1,6 @@
/*
* DISTRHO Cardinal Plugin
* Copyright (C) 2021 Filipe Coelho <falktx@falktx.com>
* Copyright (C) 2021-2023 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
@@ -17,19 +17,10 @@

#pragma once

#include_next <rack.hpp>

#ifdef BUILDING_PLUGIN_MODULES
namespace rack {
namespace app {
struct CardinalModuleWidget : ModuleWidget {
CardinalModuleWidget() : ModuleWidget() {}
DEPRECATED CardinalModuleWidget(engine::Module* module) : ModuleWidget() {
setModule(module);
}
void onButton(const ButtonEvent& e) override;
};
}
}
# define ModuleWidget CardinalModuleWidget
#if (defined(__i386__) || defined(__x86_64__) || defined(__EMSCRIPTEN__)) && !defined(CARDINAL_NOSIMD)
# include_next <emmintrin.h>
#else
# define SIMDE_ENABLE_NATIVE_ALIASES
# include "simde/x86/sse.h"
# undef SIMDE_ENABLE_NATIVE_ALIASES
#endif

+ 27
- 0
include/simd-compat/immintrin.h View File

@@ -0,0 +1,27 @@
/*
* DISTRHO Cardinal Plugin
* Copyright (C) 2021-2023 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
* published by the Free Software Foundation; either version 3 of
* the License, or any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* For a full copy of the GNU General Public License see the LICENSE file.
*/

#pragma once

#if (defined(__i386__) || defined(__x86_64__) || defined(__EMSCRIPTEN__)) && !defined(CARDINAL_NOSIMD)
# include_next <immintrin.h>
#else
# define SIMDE_ENABLE_NATIVE_ALIASES
# include "../simde/simde/x86/sse.h"
# include "../simde/simde/x86/sse2.h"
# undef SIMDE_ENABLE_NATIVE_ALIASES
#endif

+ 6
- 4
include/simd-compat/mmintrin.h View File

@@ -1,6 +1,6 @@
/*
* DISTRHO Cardinal Plugin
* Copyright (C) 2021-2022 Filipe Coelho <falktx@falktx.com>
* Copyright (C) 2021-2023 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
@@ -17,10 +17,12 @@

#pragma once

#if defined(__i386__) || defined(__x86_64__)
#if (defined(__i386__) || defined(__x86_64__)) && !defined(CARDINAL_NOSIMD)
# include_next <mmintrin.h>
#elif defined(__EMSCRIPTEN__)
#elif defined(__EMSCRIPTEN__) && !defined(CARDINAL_NOSIMD)
# include <wasm_simd128.h>
#else
# include "../sse2neon/sse2neon.h"
# define SIMDE_ENABLE_NATIVE_ALIASES
# include "../simde/simde/x86/mmx.h"
# undef SIMDE_ENABLE_NATIVE_ALIASES
#endif

+ 37
- 6
include/simd-compat/pmmintrin.h View File

@@ -1,6 +1,6 @@
/*
* DISTRHO Cardinal Plugin
* Copyright (C) 2021-2022 Filipe Coelho <falktx@falktx.com>
* Copyright (C) 2021-2023 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
@@ -17,19 +17,43 @@

#pragma once

#if defined(__i386__) || defined(__x86_64__)
#if (defined(__i386__) || defined(__x86_64__)) && !defined(CARDINAL_NOSIMD)
# include_next <pmmintrin.h>

#elif defined(__EMSCRIPTEN__)
// bring in extra SSE3 support via simde
# define SIMDE_X86_SSE2_NATIVE
# define SIMDE_X86_SSE3_ENABLE_NATIVE_ALIASES

// make sure to not include windows.h here
# ifdef _WIN32
# define _WIN32_WAS_DEFINED
# undef _WIN32
# endif

// assume SSE3 only on macOS
# ifndef ARCH_MAC
# include "simde/x86/sse3.h"
# endif

# ifdef _WIN32_WAS_DEFINED
# define _WIN32
# undef _WIN32_WAS_DEFINED
# endif

# undef SIMDE_X86_SSE2_NATIVE
# undef SIMDE_X86_SSE3_ENABLE_NATIVE_ALIASES

#elif defined(__EMSCRIPTEN__) && !defined(CARDINAL_NOSIMD)
# include_next <pmmintrin.h>

static inline
__m64 _mm_set1_pi16(short w)
static __inline__ __m64 __attribute__((__always_inline__, __nodebug__))
_mm_set1_pi16(short w)
{
return __extension__ (__m64){ static_cast<float>(w), static_cast<float>(w) };
}

#else
/*
#elif defined(__ARM_NEON)
# include "../sse2neon/sse2neon.h"

static inline
@@ -43,5 +67,12 @@ __m64 _mm_set1_pi16(short w)
{
return vreinterpret_s64_s16(vdup_n_s16(w));
}
*/

#else
# define SIMDE_ENABLE_NATIVE_ALIASES
# include "simde/x86/sse.h"
# include "simde/x86/sse2.h"
# include "simde/x86/sse3.h"
# undef SIMDE_ENABLE_NATIVE_ALIASES
#endif

+ 26
- 0
include/simd-compat/xmmintrin.h View File

@@ -0,0 +1,26 @@
/*
* DISTRHO Cardinal Plugin
* Copyright (C) 2021-2023 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
* published by the Free Software Foundation; either version 3 of
* the License, or any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* For a full copy of the GNU General Public License see the LICENSE file.
*/

#pragma once

#if (defined(__i386__) || defined(__x86_64__) || defined(__EMSCRIPTEN__)) && !defined(CARDINAL_NOSIMD)
# include_next <xmmintrin.h>
#else
# define SIMDE_ENABLE_NATIVE_ALIASES
# include "simde/x86/avx.h"
# undef SIMDE_ENABLE_NATIVE_ALIASES
#endif

+ 3
- 7
include/simd/Vector.hpp View File

@@ -31,11 +31,7 @@
#include <pmmintrin.h>

/** NOTE alignas is required in some systems in order to allow SSE usage. */
#ifndef ARCH_MAC
#define SIMD_ALIGN alignas(32)
#else
#define SIMD_ALIGN
#endif
#define SIMD_ALIGN alignas(16)


namespace rack {
@@ -359,12 +355,12 @@ inline Vector<int32_t, 4> operator~(const Vector<int32_t, 4>& a) {

/** `a << b` */
inline Vector<int32_t, 4> operator<<(const Vector<int32_t, 4>& a, const int& b) {
return Vector<int32_t, 4>(_mm_slli_epi32(a.v, b));
return Vector<int32_t, 4>(_mm_sll_epi32(a.v, _mm_cvtsi32_si128(b)));
}

/** `a >> b` */
inline Vector<int32_t, 4> operator>>(const Vector<int32_t, 4>& a, const int& b) {
return Vector<int32_t, 4>(_mm_srli_epi32(a.v, b));
return Vector<int32_t, 4>(_mm_srl_epi32(a.v, _mm_cvtsi32_si128(b)));
}




+ 5
- 0
include/single-precision/algorithm View File

@@ -26,6 +26,11 @@ float max(const float a, const double b) {
return std::max<float>(a, static_cast<float>(b));
}

static inline
float min(const float a, const double b) {
return std::min<float>(a, static_cast<float>(b));
}

static inline
std::complex<float> operator*(const std::complex<double>& a, const float b) {
return static_cast<std::complex<float>>(a) * b;


+ 0
- 1
include/sse2neon

@@ -1 +0,0 @@
Subproject commit 1dfa40113a03a682dc79ba42235c5b0d1c50aaf2

+ 172
- 17
jucewrapper/CMakeLists.txt View File

@@ -1,7 +1,13 @@
cmake_minimum_required(VERSION 3.15)
project(Cardinal VERSION 22.09)
project(Cardinal VERSION 23.10)

add_subdirectory(JUCE)
include(FetchContent)
FetchContent_Declare(JUCE
GIT_REPOSITORY https://github.com/DISTRHO/JUCE.git
GIT_TAG v6.1.6
GIT_SHALLOW TRUE
)
FetchContent_MakeAvailable(JUCE)

# Config

@@ -37,9 +43,6 @@ set_property(TARGET lilv PROPERTY IMPORTED_LOCATION "${PROJECT_SOURCE_DIR}/../ca
add_library(rtmempool STATIC IMPORTED)
set_property(TARGET rtmempool PROPERTY IMPORTED_LOCATION "${PROJECT_SOURCE_DIR}/../carla/build/modules/${CMAKE_BUILD_TYPE}/rtmempool.a")

add_library(sfzero STATIC IMPORTED)
set_property(TARGET sfzero PROPERTY IMPORTED_LOCATION "${PROJECT_SOURCE_DIR}/../carla/build/modules/${CMAKE_BUILD_TYPE}/sfzero.a")

add_library(water STATIC IMPORTED)
set_property(TARGET water PROPERTY IMPORTED_LOCATION "${PROJECT_SOURCE_DIR}/../carla/build/modules/${CMAKE_BUILD_TYPE}/water.a")

@@ -89,6 +92,30 @@ set_property(TARGET libspeexdsp PROPERTY IMPORTED_LOCATION "${PROJECT_SOURCE_DIR
add_library(libzstd STATIC IMPORTED)
set_property(TARGET libzstd PROPERTY IMPORTED_LOCATION "${PROJECT_SOURCE_DIR}/../src/Rack/dep/lib/libzstd.a")

set(SURGE_DEP_PATH "${PROJECT_SOURCE_DIR}/../deps/surge-build")

add_library(surgedep01 STATIC IMPORTED)
add_library(surgedep02 STATIC IMPORTED)
add_library(surgedep03 STATIC IMPORTED)
add_library(surgedep04 STATIC IMPORTED)
add_library(surgedep05 STATIC IMPORTED)
add_library(surgedep06 STATIC IMPORTED)
add_library(surgedep07 STATIC IMPORTED)
#add_library(surgedep08 STATIC IMPORTED)
add_library(surgedep09 STATIC IMPORTED)
add_library(surgedep10 STATIC IMPORTED)

set_property(TARGET surgedep01 PROPERTY IMPORTED_LOCATION "${SURGE_DEP_PATH}/src/common/libsurge-common.a")
set_property(TARGET surgedep02 PROPERTY IMPORTED_LOCATION "${SURGE_DEP_PATH}/src/common/libjuce_dsp_rack_sub.a")
set_property(TARGET surgedep03 PROPERTY IMPORTED_LOCATION "${SURGE_DEP_PATH}/libs/airwindows/libairwindows.a")
set_property(TARGET surgedep04 PROPERTY IMPORTED_LOCATION "${SURGE_DEP_PATH}/libs/eurorack/libeurorack.a")
set_property(TARGET surgedep05 PROPERTY IMPORTED_LOCATION "${SURGE_DEP_PATH}/libs/fmt/libfmt.a")
set_property(TARGET surgedep06 PROPERTY IMPORTED_LOCATION "${SURGE_DEP_PATH}/libs/sqlite-3.23.3/libsqlite.a")
set_property(TARGET surgedep07 PROPERTY IMPORTED_LOCATION "${SURGE_DEP_PATH}/libs/sst/sst-plugininfra/libsst-plugininfra.a")
#set_property(TARGET surgedep08 PROPERTY IMPORTED_LOCATION "${SURGE_DEP_PATH}/libs/sst/sst-plugininfra/libs/filesystem/libfilesystem.a")
set_property(TARGET surgedep09 PROPERTY IMPORTED_LOCATION "${SURGE_DEP_PATH}/libs/sst/sst-plugininfra/libs/strnatcmp/libstrnatcmp.a")
set_property(TARGET surgedep10 PROPERTY IMPORTED_LOCATION "${SURGE_DEP_PATH}/libs/sst/sst-plugininfra/libs/tinyxml/libtinyxml.a")

# dependencies

find_package(PkgConfig REQUIRED)
@@ -139,6 +166,7 @@ target_sources(Cardinal
target_include_directories(Cardinal
PRIVATE
../dpf/distrho
../dpf/dgl/src/pugl-upstream/include
../src/Cardinal)

target_compile_definitions(Cardinal
@@ -155,9 +183,9 @@ target_compile_definitions(Cardinal
JUCE_USE_OGGVORBIS=0
JUCE_USE_XINERAMA=0
JUCE_VST3_CAN_REPLACE_VST2=0
JUCE_ALSA=1
JUCE_ALSA=0
JUCE_DIRECTSOUND=0
JUCE_JACK=1
JUCE_JACK=0
JUCE_WASAPI=0
JUCE_WEB_BROWSER=0)

@@ -176,11 +204,20 @@ target_link_libraries(Cardinal
jackbridge
lilv
rtmempool
sfzero
water
ysfx
zita_resampler
dgl
surgedep01
surgedep02
surgedep03
surgedep04
surgedep05
surgedep06
surgedep07
#surgedep08
surgedep09
surgedep10
libaubio
libarchive
libjansson
@@ -203,7 +240,6 @@ target_link_libraries(Cardinal
-lmagic
PUBLIC
juce::juce_recommended_config_flags
juce::juce_recommended_lto_flags
juce::juce_recommended_warning_flags)
#]]

@@ -232,6 +268,7 @@ target_sources(CardinalFX
target_include_directories(CardinalFX
PRIVATE
../dpf/distrho
../dpf/dgl/src/pugl-upstream/include
../src/CardinalFX)

target_compile_definitions(CardinalFX
@@ -248,9 +285,9 @@ target_compile_definitions(CardinalFX
JUCE_USE_OGGVORBIS=0
JUCE_USE_XINERAMA=0
JUCE_VST3_CAN_REPLACE_VST2=0
JUCE_ALSA=1
JUCE_ALSA=0
JUCE_DIRECTSOUND=0
JUCE_JACK=1
JUCE_JACK=0
JUCE_WASAPI=0
JUCE_WEB_BROWSER=0)

@@ -269,11 +306,121 @@ target_link_libraries(CardinalFX
jackbridge
lilv
rtmempool
sfzero
water
ysfx
zita_resampler
dgl
surgedep01
surgedep02
surgedep03
surgedep04
surgedep05
surgedep06
surgedep07
#surgedep08
surgedep09
surgedep10
libaubio
libarchive
libjansson
libquickjs
libsamplerate
libspeexdsp
libzstd
${STATIC_LIBS_END}
${GL_LIBRARIES}
${DBUS_LIBRARIES}
-L${LIBLO_LIBRARY_DIRS}
${FFTW3F_LIBRARIES}
${LIBLO_LIBRARIES}
${SNDFILE_LIBRARIES}
${X11_LIBRARIES}
${XCURSOR_LIBRARIES}
${XEXT_LIBRARIES}
${XRANDR_LIBRARIES}
${EXTRA_LIBS}
-lmagic
PUBLIC
juce::juce_recommended_config_flags
juce::juce_recommended_warning_flags)

# MIDI variant

juce_add_plugin(CardinalMIDI
AU_MAIN_TYPE kAudioUnitType_MIDIProcessor
COMPANY_COPYRIGHT "GPL-3.0-or-later"
COMPANY_NAME "DISTRHO"
COMPANY_WEBSITE "https://github.com/DISTRHO/Cardinal"
DESCRIPTION "Virtual modular synthesizer plugin"
EDITOR_WANTS_KEYBOARD_FOCUS FALSE
FORMATS ${PLUGIN_FORMATS}
IS_MIDI_EFFECT TRUE
IS_SYNTH FALSE
NEEDS_MIDI_INPUT TRUE
NEEDS_MIDI_OUTPUT TRUE
PLUGIN_CODE DcnM
PLUGIN_MANUFACTURER_CODE Dstr
PRODUCT_NAME "CardinalMIDI")

target_sources(CardinalMIDI
PRIVATE
CardinalWrapper.cpp)

target_include_directories(CardinalMIDI
PRIVATE
../dpf/distrho
../dpf/dgl/src/pugl-upstream/include
../src/CardinalFX)

target_compile_definitions(CardinalMIDI
PUBLIC
DISTRHO_NAMESPACE=CardinalDISTRHO
DGL_NAMESPACE=CardinalDGL
JucePlugin_PreferredChannelConfigurations=2,2
JUCE_CHECK_MEMORY_LEAKS=0
JUCE_DISABLE_NATIVE_FILECHOOSERS=1
JUCE_DISPLAY_SPLASH_SCREEN=0
JUCE_MODAL_LOOPS_PERMITTED=0
JUCE_USE_CURL=0
JUCE_USE_FLAC=0
JUCE_USE_OGGVORBIS=0
JUCE_USE_XINERAMA=0
JUCE_VST3_CAN_REPLACE_VST2=0
JUCE_ALSA=0
JUCE_DIRECTSOUND=0
JUCE_JACK=0
JUCE_WASAPI=0
JUCE_WEB_BROWSER=0)

target_link_libraries(CardinalMIDI
PRIVATE
juce::juce_audio_utils
${STATIC_LIBS_START}
sPlugins
sCardinalFX
sRack
carla_host_plugin
carla_engine_plugin
carla_plugin
native_plugins
audio_decoder
jackbridge
lilv
rtmempool
water
ysfx
zita_resampler
dgl
surgedep01
surgedep02
surgedep03
surgedep04
surgedep05
surgedep06
surgedep07
#surgedep08
surgedep09
surgedep10
libaubio
libarchive
libjansson
@@ -296,7 +443,6 @@ target_link_libraries(CardinalFX
-lmagic
PUBLIC
juce::juce_recommended_config_flags
juce::juce_recommended_lto_flags
juce::juce_recommended_warning_flags)

# Synth variant
@@ -324,6 +470,7 @@ target_sources(CardinalSynth
target_include_directories(CardinalSynth
PRIVATE
../dpf/distrho
../dpf/dgl/src/pugl-upstream/include
../src/CardinalSynth)

target_compile_definitions(CardinalSynth
@@ -340,9 +487,9 @@ target_compile_definitions(CardinalSynth
JUCE_USE_OGGVORBIS=0
JUCE_USE_XINERAMA=0
JUCE_VST3_CAN_REPLACE_VST2=0
JUCE_ALSA=1
JUCE_ALSA=0
JUCE_DIRECTSOUND=0
JUCE_JACK=1
JUCE_JACK=0
JUCE_WASAPI=0
JUCE_WEB_BROWSER=0)

@@ -361,11 +508,20 @@ target_link_libraries(CardinalSynth
jackbridge
lilv
rtmempool
sfzero
water
ysfx
zita_resampler
dgl
surgedep01
surgedep02
surgedep03
surgedep04
surgedep05
surgedep06
surgedep07
#surgedep08
surgedep09
surgedep10
libaubio
libarchive
libjansson
@@ -388,5 +544,4 @@ target_link_libraries(CardinalSynth
-lmagic
PUBLIC
juce::juce_recommended_config_flags
juce::juce_recommended_lto_flags
juce::juce_recommended_warning_flags)

+ 5
- 5
jucewrapper/CardinalWrapper.cpp View File

@@ -18,7 +18,7 @@
#include <juce_audio_processors/juce_audio_processors.h>

#include <AvailabilityMacros.h>
#if MAC_OS_X_VERSION_MAX_ALLOWED > 101200
#if MAC_OS_X_VERSION_MAX_ALLOWED > 101500
#error unwanted macOS version, too new
#endif

@@ -270,11 +270,11 @@ public:
{
if (const double sampleRate = getSampleRate())
if (sampleRate > 0.0)
plugin.setSampleRate(sampleRate);
plugin.setSampleRate(sampleRate, true);

if (const int samplesPerBlock = getBlockSize())
if (samplesPerBlock > 0)
plugin.setBufferSize(static_cast<uint32_t>(samplesPerBlock));
plugin.setBufferSize(static_cast<uint32_t>(samplesPerBlock), true);

if (parameterCount != 0)
{
@@ -313,8 +313,8 @@ protected:
DISTRHO_SAFE_ASSERT_RETURN(samplesPerBlock > 0,);

plugin.deactivateIfNeeded();
plugin.setSampleRate(sampleRate);
plugin.setBufferSize(static_cast<uint32_t>(samplesPerBlock));
plugin.setSampleRate(sampleRate, true);
plugin.setBufferSize(static_cast<uint32_t>(samplesPerBlock), true);
plugin.activate();
}



+ 0
- 1
lv2export/Makefile View File

@@ -59,7 +59,6 @@ ifeq ($(WINDOWS),true)
BASE_FLAGS += -D_USE_MATH_DEFINES
BASE_FLAGS += -DWIN32_LEAN_AND_MEAN
BASE_FLAGS += -I../include/mingw-compat
BASE_FLAGS += -I../include/mingw-std-threads
endif

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


+ 1
- 19
lv2export/export.cpp View File

@@ -15,25 +15,7 @@
* For a full copy of the GNU General Public License see the LICENSE file.
*/

#ifndef PLUGIN_BRAND
# error PLUGIN_BRAND undefined
#endif

#ifndef PLUGIN_LABEL
# error PLUGIN_LABEL undefined
#endif

#ifndef PLUGIN_MODEL
# error PLUGIN_MODEL undefined
#endif

#ifndef PLUGIN_CV_INPUTS
# error PLUGIN_CV_INPUTS undefined
#endif

#ifndef PLUGIN_CV_OUTPUTS
# error PLUGIN_CV_OUTPUTS undefined
#endif
#include "lv2plugin.hpp"

#include <cstdio>



+ 4
- 27
lv2export/lv2plugin.cpp View File

@@ -15,26 +15,7 @@
* For a full copy of the GNU General Public License see the LICENSE file.
*/

#ifndef PLUGIN_MODEL
# error PLUGIN_MODEL undefined
#endif

#ifndef PLUGIN_CV_INPUTS
# error PLUGIN_CV_INPUTS undefined
#endif

#ifndef PLUGIN_CV_OUTPUTS
# error PLUGIN_CV_OUTPUTS undefined
#endif

enum PortType {
Audio = 0,
Bi = 1,
Uni = 2,
};

static constexpr const int kCvInputs[] = PLUGIN_CV_INPUTS;
static constexpr const int kCvOutputs[] = PLUGIN_CV_OUTPUTS;
#include "lv2plugin.hpp"

#include "src/lv2/buf-size.h"
#include "src/lv2/options.h"
@@ -185,21 +166,19 @@ static LV2_Handle lv2_instantiate(const LV2_Descriptor*, double sampleRate, cons

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

#define instancePtr ((PluginLv2*)instance)

static void lv2_connect_port(LV2_Handle instance, uint32_t port, void* dataLocation)
{
instancePtr->lv2_connect_port(port, dataLocation);
static_cast<PluginLv2*>(instance)->lv2_connect_port(port, dataLocation);
}

static void lv2_run(LV2_Handle instance, uint32_t sampleCount)
{
instancePtr->lv2_run(sampleCount);
static_cast<PluginLv2*>(instance)->lv2_run(sampleCount);
}

static void lv2_cleanup(LV2_Handle instance)
{
delete instancePtr;
delete static_cast<PluginLv2*>(instance);
}

// -----------------------------------------------------------------------
@@ -209,8 +188,6 @@ static const void* lv2_extension_data(const char* uri)
return nullptr;
}

#undef instancePtr

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

static const LV2_Descriptor sLv2Descriptor = {


include/mingw-compat/stdio.h → lv2export/lv2plugin.hpp View File

@@ -1,6 +1,6 @@
/*
* DISTRHO Cardinal Plugin
* Copyright (C) 2021 Filipe Coelho <falktx@falktx.com>
* Copyright (C) 2021-2022 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
@@ -17,19 +17,31 @@

#pragma once

/* On mingw stdio functions like printf are not inline, and thus get defined every time they are used.
* We go through a few steps to ensure unique symbol names.
*/
#ifdef STDIO_OVERRIDE
#ifndef PLUGIN_BRAND
# error PLUGIN_BRAND undefined
#endif

#ifndef PLUGIN_LABEL
# error PLUGIN_LABEL undefined
#endif

#ifndef PLUGIN_MODEL
# error PLUGIN_MODEL undefined
#endif

// helper macros
# define STDIO_OVERRIDE_HELPER(NS, SEP, FN) NS ## SEP ## FN
# define STDIO_OVERRIDE_MACRO(NS, FN) STDIO_OVERRIDE_HELPER(NS, _, FN)
#ifndef PLUGIN_CV_INPUTS
# error PLUGIN_CV_INPUTS undefined
#endif

// prefix the needed stdio functions
# define printf STDIO_OVERRIDE_MACRO(STDIO_OVERRIDE, printf)
#ifndef PLUGIN_CV_OUTPUTS
# error PLUGIN_CV_OUTPUTS undefined
#endif

#endif // STDIO_OVERRIDE
enum PortType {
Audio = 0,
Bi = 1,
Uni = 2,
};

// now just include the real stdio.h
#include_next <stdio.h>
static constexpr const PortType kCvInputs[] = PLUGIN_CV_INPUTS;
static constexpr const PortType kCvOutputs[] = PLUGIN_CV_OUTPUTS;

+ 2
- 2
lv2export/plugins/aubileinstruments-macro-osc-2.cpp View File

@@ -55,8 +55,8 @@
#define PLUGIN_BRAND "AudibleInstruments"
#define PLUGIN_LABEL "Macro Osc 2"
#define PLUGIN_MODEL modelPlaits
#define PLUGIN_CV_INPUTS {1,1,1,1,1,1,1,1}
#define PLUGIN_CV_OUTPUTS {0,0}
#define PLUGIN_CV_INPUTS {Bi,Bi,Bi,Bi,Bi,Bi,Bi,Bi}
#define PLUGIN_CV_OUTPUTS {Audio,Audio}
#define PLUGIN_LV2_CATEGORY "lv2:GeneratorPlugin"

#include "lv2plugin.cpp"


+ 2
- 2
lv2export/plugins/aubileinstruments-macro-osc.cpp View File

@@ -35,8 +35,8 @@
#define PLUGIN_BRAND "AudibleInstruments"
#define PLUGIN_LABEL "Macro Osc"
#define PLUGIN_MODEL modelBraids
#define PLUGIN_CV_INPUTS {1,1,1,1,1}
#define PLUGIN_CV_OUTPUTS {0}
#define PLUGIN_CV_INPUTS {Bi,Bi,Bi,Bi,Bi}
#define PLUGIN_CV_OUTPUTS {Audio}
#define PLUGIN_LV2_CATEGORY "lv2:GeneratorPlugin"

#include "lv2plugin.cpp"


+ 2
- 2
lv2export/plugins/msm-phaser.cpp View File

@@ -20,8 +20,8 @@
#define PLUGIN_BRAND "MSM"
#define PLUGIN_LABEL "Phaser"
#define PLUGIN_MODEL modelPhaserModule
#define PLUGIN_CV_INPUTS {1,1,1,0}
#define PLUGIN_CV_OUTPUTS {0}
#define PLUGIN_CV_INPUTS {Bi,Bi,Bi,Audio}
#define PLUGIN_CV_OUTPUTS {Audio}
#define PLUGIN_LV2_CATEGORY "lv2:DistortionPlugin"

#include "lv2plugin.cpp"


+ 2
- 2
lv2export/plugins/rackwindows-mv.cpp View File

@@ -20,8 +20,8 @@
#define PLUGIN_BRAND "Rackwindows"
#define PLUGIN_LABEL "MV"
#define PLUGIN_MODEL modelMv
#define PLUGIN_CV_INPUTS {1,1,1,1,0,0}
#define PLUGIN_CV_OUTPUTS {0,0}
#define PLUGIN_CV_INPUTS {Bi,Bi,Bi,Bi,Audio,Audio}
#define PLUGIN_CV_OUTPUTS {Audio,Audio}
#define PLUGIN_LV2_CATEGORY "lv2:ReverbPlugin"

#include "lv2plugin.cpp"


+ 2
- 2
lv2export/plugins/rackwindows-vibrato.cpp View File

@@ -20,8 +20,8 @@
#define PLUGIN_BRAND "Rackwindows"
#define PLUGIN_LABEL "Vibrato"
#define PLUGIN_MODEL modelVibrato
#define PLUGIN_CV_INPUTS {1,1,1,1,1,0}
#define PLUGIN_CV_OUTPUTS {1,0,1}
#define PLUGIN_CV_INPUTS {Bi,Bi,Bi,Bi,Bi,Audio}
#define PLUGIN_CV_OUTPUTS {Bi,Audio,Bi}
#define PLUGIN_LV2_CATEGORY "lv2:DynamicsPlugin"

#include "lv2plugin.cpp"


+ 2
- 2
lv2export/plugins/valleyaudio-plateau.cpp View File

@@ -23,8 +23,8 @@
#define PLUGIN_BRAND "Valley Audio"
#define PLUGIN_LABEL "Plateau"
#define PLUGIN_MODEL modelPlateau
#define PLUGIN_CV_INPUTS {0,0,1,1,1,1,1,1,1,1,1,1,1,1,1,1,1}
#define PLUGIN_CV_OUTPUTS {0,0}
#define PLUGIN_CV_INPUTS {Audio,Audio,Bi,Bi,Bi,Bi,Bi,Bi,Bi,Bi,Bi,Bi,Bi,Bi,Bi,Bi,Bi}
#define PLUGIN_CV_OUTPUTS {Audio,Audio}
#define PLUGIN_LV2_CATEGORY "lv2:ReverbPlugin"

#include "lv2plugin.cpp"


+ 6
- 24
patches/examples/DRMR_-_Interverb.vcv View File

@@ -1,6 +1,5 @@
{
"version": "2.0",
"zoom": 1.0,
"version": "2.1.2",
"modules": [
{
"id": 1184757612963547,
@@ -462,27 +461,6 @@
0
]
},
{
"id": 8996849652715896,
"plugin": "Cardinal",
"model": "Carla",
"version": "2.0",
"params": [
{
"value": 1.0,
"id": 0
},
{
"value": 1.0,
"id": 1
}
],
"data": "<?xml version='1.0' encoding='UTF-8'?>\n<!DOCTYPE CARLA-PROJECT>\n<CARLA-PROJECT VERSION='2.4'>\n <EngineSettings>\n <ForceStereo>false</ForceStereo>\n <PreferPluginBridges>false</PreferPluginBridges>\n <PreferUiBridges>false</PreferUiBridges>\n <UIsAlwaysOnTop>true</UIsAlwaysOnTop>\n <MaxParameters>200</MaxParameters>\n <UIBridgesTimeout>4000</UIBridgesTimeout>\n <LADSPA_PATH></LADSPA_PATH>\n <DSSI_PATH></DSSI_PATH>\n <LV2_PATH></LV2_PATH>\n <VST2_PATH></VST2_PATH>\n <VST3_PATH></VST3_PATH>\n <SF2_PATH></SF2_PATH>\n <SFZ_PATH></SFZ_PATH>\n <JSFX_PATH></JSFX_PATH>\n </EngineSettings>\n\n <Patchbay>\n </Patchbay>\n</CARLA-PROJECT>\n",
"pos": [
123,
1
]
},
{
"id": 644714212872810,
"plugin": "Cardinal",
@@ -492,7 +470,7 @@
"data": {
"filepath": "",
"lang": "None",
"etext": " \n ^ ^ ,_, \n (O,O) (.,.) \n ( ) ( ) \n--------\"-\"---dwb--\"-\"---dwb- \n\nversatile 4 voice polyphonic synth with a bit\nof reverb\n\nParam1: pulse width modulation\nParam2: filter frequency\nParam3: filter resonance\n\n\n /^--^\\ /^--^\\ /^--^\\ \n \\____/ \\____/ \\____/ \n / \\ / \\ / \\ \n | | | | | | \n \\__ __/ \\__ __/ \\__ __/ \n|^|^|^|^\\ \\^|^|^|^/ /^|^|^|^|^\\ \\^|^|^|^|^|^|^|^|^|\n| | | | |\\ \\| | |/ /| | | | | |\\ \\| | | | | | | | |\n#########/ /#####\\ \\###########/ /#################\n| | | | |\\/ | | | \\/| | | | | |\\/ | | | | | | | | |\n|_|_|_|_|_|_|_|_|_|_|_|_|_|_|_|_|_|_|_|_|_|_|_|_|_|\n\n\n\n\n\n\n",
"etext": " \n ^ ^ ,_, \n (O,O) (.,.) \n ( ) ( ) \n--------\"-\"---dwb--\"-\"---dwb- \n\nversatile 4 voice polyphonic synth with a bit\nof reverb\n\nParam1: pulse width modulation\nParam2: filter frequency\nParam3: filter resonance\n\n\n /^--^\\ /^--^\\ /^--^\\ \n \\____/ \\____/ \\____/ \n / \\ / \\ / \\ \n | | | | | | \n \\__ __/ \\__ __/ \\__ __/ \n|^|^|^|^\\ \\^|^|^|^/ /^|^|^|^|^\\ \\^|^|^|^|^|^|^|^|^|\n| | | | |\\ \\| | |/ /| | | | | |\\ \\| | | | | | | | |\n#########/ /#####\\ \\###########/ /#################\n| | | | |\\/ | | | \\/| | | | | |\\/ | | | | | | | | |\n|_|_|_|_|_|_|_|_|_|_|_|_|_|_|_|_|_|_|_|_|_|_|_|_|_|\n\n\n\n\n\n\n\n",
"width": 27
},
"pos": [
@@ -527,6 +505,7 @@
"version": "2.0",
"params": [],
"data": {
"pwRange": 0.0,
"smooth": true,
"channels": 4,
"polyMode": 0,
@@ -546,6 +525,9 @@
"model": "HostParameters",
"version": "2.0",
"params": [],
"data": {
"smooth": true
},
"pos": [
32,
2


+ 6384
- 0
patches/examples/JTB_-_Waves.vcv
File diff suppressed because it is too large
View File


+ 711
- 0
patches/examples/SpotlightKid_-_Classic-Polysynth.vcv View File

@@ -0,0 +1,711 @@
{
"version": "2.1.2",
"zoom": 1.0,
"modules": [
{
"id": 5726895899473528,
"plugin": "Fundamental",
"model": "ADSR",
"version": "2.0",
"params": [
{
"value": 0.0,
"id": 0
},
{
"value": 0.73012268543243408,
"id": 1
},
{
"value": 0.73614501953125,
"id": 2
},
{
"value": 0.64457994699478149,
"id": 3
},
{
"value": 0.0,
"id": 4
},
{
"value": 0.0,
"id": 5
},
{
"value": 0.0,
"id": 6
},
{
"value": 0.0,
"id": 7
},
{
"value": 0.0,
"id": 8
}
],
"leftModuleId": 5337037007035013,
"rightModuleId": 4828178296911509,
"pos": [
58,
0
]
},
{
"id": 4828178296911509,
"plugin": "Fundamental",
"model": "VCA-1",
"version": "2.0",
"params": [
{
"value": 1.0,
"id": 0
},
{
"value": 1.0,
"id": 1
}
],
"leftModuleId": 5726895899473528,
"rightModuleId": 6408981600715695,
"pos": [
67,
0
]
},
{
"id": 5337037007035013,
"plugin": "Fundamental",
"model": "ADSR",
"version": "2.0",
"params": [
{
"value": 0.0,
"id": 0
},
{
"value": 0.69156646728515625,
"id": 1
},
{
"value": 0.0,
"id": 2
},
{
"value": 0.65542322397232056,
"id": 3
},
{
"value": 0.0,
"id": 4
},
{
"value": 0.0,
"id": 5
},
{
"value": 0.0,
"id": 6
},
{
"value": 0.0,
"id": 7
},
{
"value": 0.0,
"id": 8
}
],
"leftModuleId": 8662611283913679,
"rightModuleId": 5726895899473528,
"pos": [
49,
0
]
},
{
"id": 5012071172439093,
"plugin": "Bogaudio",
"model": "Bogaudio-VCO",
"version": "2.0",
"params": [
{
"value": 0.0,
"id": 0
},
{
"value": -0.10602404922246933,
"id": 1
},
{
"value": 0.0,
"id": 2
},
{
"value": -0.66505992412567139,
"id": 3
},
{
"value": 0.0,
"id": 4
},
{
"value": 1.0,
"id": 5
},
{
"value": 0.0,
"id": 6
}
],
"leftModuleId": 7829403555464046,
"rightModuleId": 3498834829604531,
"data": {
"poly_input": 0,
"dc_correction": true
},
"pos": [
9,
0
]
},
{
"id": 3498834829604531,
"plugin": "Bogaudio",
"model": "Bogaudio-VCO",
"version": "2.0",
"params": [
{
"value": 0.0,
"id": 0
},
{
"value": 0.10602407157421112,
"id": 1
},
{
"value": 0.0,
"id": 2
},
{
"value": 0.0,
"id": 3
},
{
"value": 0.0,
"id": 4
},
{
"value": 1.0,
"id": 5
},
{
"value": 0.0,
"id": 6
}
],
"leftModuleId": 5012071172439093,
"rightModuleId": 6599230938402504,
"data": {
"poly_input": 0,
"dc_correction": true
},
"pos": [
19,
0
]
},
{
"id": 6408981600715695,
"plugin": "Bogaudio",
"model": "Bogaudio-LFO",
"version": "2.0",
"params": [
{
"value": 1.4879528284072876,
"id": 0
},
{
"value": 0.0,
"id": 1
},
{
"value": 0.0,
"id": 2
},
{
"value": 0.0,
"id": 3
},
{
"value": 0.0,
"id": 4
},
{
"value": 0.5,
"id": 5
},
{
"value": 0.0,
"id": 6
}
],
"leftModuleId": 4828178296911509,
"rightModuleId": 1204823109328701,
"data": {
"offset_cv_to_smoothing": false
},
"pos": [
70,
0
]
},
{
"id": 8662611283913679,
"plugin": "Bogaudio",
"model": "Bogaudio-VCF",
"version": "2.0",
"params": [
{
"value": 0.17951798439025879,
"id": 0
},
{
"value": 0.27710825204849243,
"id": 1
},
{
"value": 0.0,
"id": 2
},
{
"value": 0.0,
"id": 3
},
{
"value": 0.0,
"id": 4
},
{
"value": 0.33428090810775757,
"id": 5
}
],
"leftModuleId": 6599230938402504,
"rightModuleId": 5337037007035013,
"data": {
"bandwidthMode": "pitched"
},
"pos": [
39,
0
]
},
{
"id": 1204823109328701,
"plugin": "Fundamental",
"model": "8vert",
"version": "2.0",
"params": [
{
"value": 0.16385534405708313,
"id": 0
},
{
"value": 0.099999845027923584,
"id": 1
},
{
"value": 0.0,
"id": 2
},
{
"value": 0.0,
"id": 3
},
{
"value": 0.0,
"id": 4
},
{
"value": 0.0,
"id": 5
},
{
"value": 0.0,
"id": 6
},
{
"value": 0.0,
"id": 7
}
],
"leftModuleId": 6408981600715695,
"pos": [
80,
0
]
},
{
"id": 6599230938402504,
"plugin": "Bogaudio",
"model": "Bogaudio-VCM",
"version": "2.0",
"params": [
{
"value": 0.0,
"id": 0
},
{
"value": 0.89999997615814209,
"id": 1
},
{
"value": 0.0,
"id": 2
},
{
"value": 0.89999997615814209,
"id": 3
},
{
"value": 0.80000001192092896,
"id": 4
},
{
"value": 0.0,
"id": 5
}
],
"leftModuleId": 3498834829604531,
"rightModuleId": 8662611283913679,
"data": {
"disableOutputLimit": false
},
"pos": [
29,
0
]
},
{
"id": 7829403555464046,
"plugin": "Bogaudio",
"model": "Bogaudio-Matrix44",
"version": "2.0",
"params": [
{
"value": 1.0,
"id": 0
},
{
"value": 0.070000037550926208,
"id": 1
},
{
"value": 0.035000000149011612,
"id": 2
},
{
"value": 0.0,
"id": 3
},
{
"value": 1.0,
"id": 4
},
{
"value": -0.069999769330024719,
"id": 5
},
{
"value": 0.035000000149011612,
"id": 6
},
{
"value": 0.0,
"id": 7
},
{
"value": 0.0,
"id": 8
},
{
"value": 0.0,
"id": 9
},
{
"value": 0.0,
"id": 10
},
{
"value": 0.0,
"id": 11
},
{
"value": 0.0,
"id": 12
},
{
"value": 0.0,
"id": 13
},
{
"value": 0.0,
"id": 14
},
{
"value": 0.0,
"id": 15
}
],
"rightModuleId": 5012071172439093,
"data": {
"clipping_mode": 0,
"input_gain_db": 0.0,
"sum": true,
"indicator_knobs": true,
"unipolar": false
},
"pos": [
-1,
0
]
},
{
"id": 2610715620592544,
"plugin": "Cardinal",
"model": "TextEditor",
"version": "2.0",
"params": [],
"data": {
"filepath": "",
"lang": "None",
"etext": "A classic polyphonic 2-oscillator synthesizer\n---------------------------------------------\n\n* 2 VCOs with blendable sawtooth and pulse waves\n* 1 multi-mode filter\n* 1 filter envelope\n* 1 VCA envelope\n* 1 multi-waveform LFO\n\nNotes:\n\n* The LFO is patched to oscillator pitch by default.\n The amount can be controlled via the 2A and 2B level\n knobs of the \"Matrix44\" mixer module.\n* You can control additional destinations with the LFO by \n patching its output(s) into the \"Matrix44\" module's input \n (optionally via the \"8Vert\" attenuator module) and\n then the outputs of the \"Matrix44\" module into the \n destinations. Then use its corresponding level knobs to \n control the amount.\n* The pitch bend amount can be controlled via the 3A and 3B\n level knobs of the \"Matrix44\" module (3.5% is roughly 2\n semitones).\n* The number of polyphonic voices can be set via the \n context menu of the \"Cardinal Host MIDI\" module.\n\n\n\n\n\n\n",
"width": 30
},
"pos": [
45,
1
]
},
{
"id": 1,
"plugin": "Cardinal",
"model": "HostAudio2",
"version": "2.0",
"params": [
{
"value": 0.70632630586624146,
"id": 0
}
],
"data": {
"dcFilter": true
},
"pos": [
80,
1
]
},
{
"id": 2,
"plugin": "Cardinal",
"model": "HostMIDI",
"version": "2.0",
"params": [],
"rightModuleId": 4,
"data": {
"pwRange": 0.0,
"smooth": false,
"channels": 6,
"polyMode": 0,
"lastPitch": 8192,
"lastMod": 0,
"inputChannel": 0,
"outputChannel": 0
},
"pos": [
-1,
1
]
},
{
"id": 4,
"plugin": "Cardinal",
"model": "HostParameters",
"version": "2.0",
"params": [],
"leftModuleId": 2,
"data": {
"smooth": true
},
"pos": [
8,
1
]
}
],
"cables": [
{
"id": 5155876120487880,
"outputModuleId": 2,
"outputId": 1,
"inputModuleId": 5726895899473528,
"inputId": 4,
"color": "#ff9352"
},
{
"id": 781753834216137,
"outputModuleId": 2,
"outputId": 6,
"inputModuleId": 5726895899473528,
"inputId": 5,
"color": "#ffd452"
},
{
"id": 3464471860196875,
"outputModuleId": 5726895899473528,
"outputId": 0,
"inputModuleId": 4828178296911509,
"inputId": 0,
"color": "#e8ff52"
},
{
"id": 3735627013913285,
"outputModuleId": 2,
"outputId": 1,
"inputModuleId": 5337037007035013,
"inputId": 4,
"color": "#ff9352"
},
{
"id": 580842343744148,
"outputModuleId": 2,
"outputId": 6,
"inputModuleId": 5337037007035013,
"inputId": 5,
"color": "#ffd452"
},
{
"id": 3568029120047108,
"outputModuleId": 8662611283913679,
"outputId": 0,
"inputModuleId": 4828178296911509,
"inputId": 1,
"color": "#ff5252"
},
{
"id": 498514594501880,
"outputModuleId": 5337037007035013,
"outputId": 0,
"inputModuleId": 8662611283913679,
"inputId": 0,
"color": "#a8ff52"
},
{
"id": 1797497447138497,
"outputModuleId": 6408981600715695,
"outputId": 3,
"inputModuleId": 1204823109328701,
"inputId": 0,
"color": "#6752ff"
},
{
"id": 4517203320689158,
"outputModuleId": 6408981600715695,
"outputId": 3,
"inputModuleId": 1204823109328701,
"inputId": 1,
"color": "#e952ff"
},
{
"id": 3320898588984728,
"outputModuleId": 4828178296911509,
"outputId": 0,
"inputModuleId": 1,
"inputId": 0,
"color": "#ff9352"
},
{
"id": 6368912553945733,
"outputModuleId": 5012071172439093,
"outputId": 0,
"inputModuleId": 6599230938402504,
"inputId": 0,
"color": "#ffd452"
},
{
"id": 7452422491828867,
"outputModuleId": 5012071172439093,
"outputId": 1,
"inputModuleId": 6599230938402504,
"inputId": 2,
"color": "#527dff"
},
{
"id": 8322447986534562,
"outputModuleId": 3498834829604531,
"outputId": 0,
"inputModuleId": 6599230938402504,
"inputId": 4,
"color": "#67ff52"
},
{
"id": 7931051349285735,
"outputModuleId": 3498834829604531,
"outputId": 1,
"inputModuleId": 6599230938402504,
"inputId": 6,
"color": "#52ffff"
},
{
"id": 5415548314308516,
"outputModuleId": 6599230938402504,
"outputId": 0,
"inputModuleId": 8662611283913679,
"inputId": 3,
"color": "#e8ff52"
},
{
"id": 8251957244621037,
"outputModuleId": 2,
"outputId": 0,
"inputModuleId": 7829403555464046,
"inputId": 0,
"color": "#52ff7d"
},
{
"id": 696754494174847,
"outputModuleId": 1204823109328701,
"outputId": 1,
"inputModuleId": 7829403555464046,
"inputId": 1,
"color": "#527dff"
},
{
"id": 8414987939373829,
"outputModuleId": 7829403555464046,
"outputId": 0,
"inputModuleId": 5012071172439093,
"inputId": 0,
"color": "#52ffff"
},
{
"id": 3908893753031146,
"outputModuleId": 7829403555464046,
"outputId": 1,
"inputModuleId": 3498834829604531,
"inputId": 0,
"color": "#a852ff"
},
{
"id": 5892222261492300,
"outputModuleId": 2,
"outputId": 4,
"inputModuleId": 7829403555464046,
"inputId": 2,
"color": "#e952ff"
}
]
}

+ 858
- 0
patches/examples/falkTX_-_Divide-no-Conquer.vcv View File

@@ -0,0 +1,858 @@
{
"version": "2.1.2",
"zoom": 1.0,
"modules": [
{
"id": 2323510085504344,
"plugin": "Mog",
"model": "Network",
"version": "2.0",
"params": [
{
"value": 0.5,
"id": 0
},
{
"value": 0.5,
"id": 1
},
{
"value": 0.5,
"id": 2
},
{
"value": 0.5,
"id": 3
},
{
"value": 0.5,
"id": 4
},
{
"value": 0.5,
"id": 5
},
{
"value": 0.5,
"id": 6
},
{
"value": 0.5,
"id": 7
},
{
"value": 0.5,
"id": 8
},
{
"value": 0.5,
"id": 9
},
{
"value": 0.5,
"id": 10
},
{
"value": 0.5,
"id": 11
},
{
"value": 0.5,
"id": 12
},
{
"value": 0.5,
"id": 13
},
{
"value": 0.5,
"id": 14
},
{
"value": 0.5,
"id": 15
},
{
"value": 0.0,
"id": 16
},
{
"value": 0.0,
"id": 17
},
{
"value": 0.40000000596046448,
"id": 18
},
{
"value": 1.0,
"id": 19
},
{
"value": 0.0,
"id": 20
}
],
"data": {
"channels": 16,
"polyMode": 1,
"nodeStates": [
-1,
-1,
-1,
-1,
-1,
-1,
-1,
0,
-2,
-1,
-1,
-1,
-2,
0,
-2,
-1
]
},
"pos": [
5,
0
]
},
{
"id": 7733409763520287,
"plugin": "Fundamental",
"model": "LFO",
"version": "2.0",
"params": [
{
"value": 1.0,
"id": 0
},
{
"value": 0.0,
"id": 1
},
{
"value": 2.1946320533752441,
"id": 2
},
{
"value": 0.0,
"id": 3
},
{
"value": 0.0,
"id": 4
},
{
"value": 0.5,
"id": 5
},
{
"value": 0.0,
"id": 6
}
],
"pos": [
-5,
-1
]
},
{
"id": 7910322281435707,
"plugin": "GoodSheperd",
"model": "SEQ3st",
"version": "2.0",
"params": [
{
"value": 1.2771106958389282,
"id": 0
},
{
"value": 0.0,
"id": 1
},
{
"value": 0.0,
"id": 2
},
{
"value": 8.0,
"id": 3
},
{
"value": 0.33734941482543945,
"id": 4
},
{
"value": 2.1566267013549805,
"id": 5
},
{
"value": 1.3012033700942993,
"id": 6
},
{
"value": 1.8674684762954712,
"id": 7
},
{
"value": 2.4819269180297852,
"id": 8
},
{
"value": 1.9036139249801636,
"id": 9
},
{
"value": 2.1807231903076172,
"id": 10
},
{
"value": 1.493976354598999,
"id": 11
},
{
"value": 1.3975902795791626,
"id": 12
},
{
"value": 1.4337348937988281,
"id": 13
},
{
"value": 1.9277111291885376,
"id": 14
},
{
"value": 1.9277104139328003,
"id": 15
},
{
"value": 0.74698799848556519,
"id": 16
},
{
"value": 1.3614462614059448,
"id": 17
},
{
"value": 0.45783132314682007,
"id": 18
},
{
"value": 0.98795127868652344,
"id": 19
},
{
"value": 0.1686750054359436,
"id": 20
},
{
"value": 1.0782999992370605,
"id": 21
},
{
"value": 0.65060001611709595,
"id": 22
},
{
"value": 0.9337499737739563,
"id": 23
},
{
"value": 1.2409499883651733,
"id": 24
},
{
"value": 0.95179998874664307,
"id": 25
},
{
"value": 1.0903500318527222,
"id": 26
},
{
"value": 0.74699997901916504,
"id": 27
},
{
"value": 0.0,
"id": 28
},
{
"value": 0.0,
"id": 29
},
{
"value": 0.0,
"id": 30
},
{
"value": 0.0,
"id": 31
},
{
"value": 0.0,
"id": 32
},
{
"value": 0.0,
"id": 33
},
{
"value": 0.0,
"id": 34
},
{
"value": 0.0,
"id": 35
},
{
"value": 0.0,
"id": 36
}
],
"rightModuleId": 7124670414167707,
"data": {
"running": true,
"gates": [
1,
1,
1,
1,
1,
1,
1,
1
]
},
"pos": [
5,
-1
]
},
{
"id": 6113641652229320,
"plugin": "Fundamental",
"model": "Quantizer",
"version": "2.0",
"params": [
{
"value": 0.0,
"id": 0
}
],
"leftModuleId": 7124670414167707,
"data": {
"enabledNotes": [
true,
false,
true,
false,
true,
false,
false,
true,
false,
true,
false,
false
]
},
"pos": [
44,
-1
]
},
{
"id": 6436949913364135,
"plugin": "Befaco",
"model": "EvenVCO",
"version": "2.0",
"params": [
{
"value": -5.0,
"id": 0
},
{
"value": 0.0,
"id": 1
},
{
"value": 0.0,
"id": 2
}
],
"pos": [
53,
-1
]
},
{
"id": 7124670414167707,
"plugin": "Extratone",
"model": "Ichneumonid",
"version": "2.0",
"params": [
{
"value": 0.0,
"id": 0
},
{
"value": 0.0,
"id": 1
},
{
"value": 0.0,
"id": 2
},
{
"value": 0.0,
"id": 3
},
{
"value": 0.0,
"id": 4
},
{
"value": 0.0,
"id": 5
},
{
"value": 0.0,
"id": 6
},
{
"value": 1.0,
"id": 7
},
{
"value": 1.0,
"id": 8
},
{
"value": 1.0,
"id": 9
},
{
"value": 1.0,
"id": 10
},
{
"value": 1.0,
"id": 11
},
{
"value": 1.0,
"id": 12
},
{
"value": 1.0,
"id": 13
},
{
"value": 1.0,
"id": 14
},
{
"value": 1.0,
"id": 15
}
],
"leftModuleId": 7910322281435707,
"rightModuleId": 6113641652229320,
"pos": [
32,
-1
]
},
{
"id": 6704396017183286,
"plugin": "Bogaudio",
"model": "Bogaudio-Unison",
"version": "2.0",
"params": [
{
"value": 16.0,
"id": 0
},
{
"value": 30.662649154663086,
"id": 1
}
],
"data": {},
"pos": [
49,
-1
]
},
{
"id": 5274645123493261,
"plugin": "AudibleInstruments",
"model": "Plaits",
"version": "2.0",
"params": [
{
"value": 0.0,
"id": 0
},
{
"value": 0.0,
"id": 1
},
{
"value": -2.0,
"id": 2
},
{
"value": 0.5,
"id": 3
},
{
"value": 0.5,
"id": 4
},
{
"value": 0.5,
"id": 5
},
{
"value": 0.0,
"id": 6
},
{
"value": 0.0,
"id": 7
},
{
"value": 0.0,
"id": 8
},
{
"value": 0.5,
"id": 9
},
{
"value": 0.5,
"id": 10
}
],
"leftModuleId": 3982223550835589,
"rightModuleId": 3927208667084646,
"data": {
"lowCpu": true,
"model": 14
},
"pos": [
34,
0
]
},
{
"id": 3927208667084646,
"plugin": "AudibleInstruments",
"model": "Plaits",
"version": "2.0",
"params": [
{
"value": 0.0,
"id": 0
},
{
"value": 0.0,
"id": 1
},
{
"value": -1.0,
"id": 2
},
{
"value": 0.5,
"id": 3
},
{
"value": 0.75,
"id": 4
},
{
"value": 0.5,
"id": 5
},
{
"value": 0.0,
"id": 6
},
{
"value": 0.0,
"id": 7
},
{
"value": 0.0,
"id": 8
},
{
"value": 0.5,
"id": 9
},
{
"value": 0.5,
"id": 10
}
],
"leftModuleId": 5274645123493261,
"data": {
"lowCpu": true,
"model": 10
},
"pos": [
46,
0
]
},
{
"id": 3982223550835589,
"plugin": "MockbaModular",
"model": "Dividah",
"version": "2.0",
"params": [],
"rightModuleId": 5274645123493261,
"pos": [
32,
0
]
},
{
"id": 3793316304034300,
"plugin": "Cardinal",
"model": "HostAudio2",
"version": "2.0",
"params": [
{
"value": 0.31600001454353333,
"id": 0
}
],
"data": {
"dcFilter": true
},
"pos": [
62,
-1
]
},
{
"id": 4515410204981580,
"plugin": "Cardinal",
"model": "HostAudio2",
"version": "2.0",
"params": [
{
"value": 1.42400062084198,
"id": 0
}
],
"leftModuleId": 4385899070319166,
"data": {
"dcFilter": true
},
"pos": [
67,
0
]
},
{
"id": 4385899070319166,
"plugin": "Cardinal",
"model": "HostAudio2",
"version": "2.0",
"params": [
{
"value": 0.8400002121925354,
"id": 0
}
],
"rightModuleId": 4515410204981580,
"data": {
"dcFilter": true
},
"pos": [
59,
0
]
}
],
"cables": [
{
"id": 8073390375565190,
"outputModuleId": 2323510085504344,
"outputId": 1,
"inputModuleId": 2323510085504344,
"inputId": 9,
"color": "#ffd452"
},
{
"id": 8282467367250825,
"outputModuleId": 7733409763520287,
"outputId": 3,
"inputModuleId": 2323510085504344,
"inputId": 0,
"color": "#a8ff52"
},
{
"id": 7741525453916855,
"outputModuleId": 7733409763520287,
"outputId": 3,
"inputModuleId": 7910322281435707,
"inputId": 1,
"color": "#67ff52"
},
{
"id": 7343310319365506,
"outputModuleId": 7910322281435707,
"outputId": 1,
"inputModuleId": 7124670414167707,
"inputId": 8,
"color": "#527dff"
},
{
"id": 8663072108782081,
"outputModuleId": 7910322281435707,
"outputId": 2,
"inputModuleId": 7124670414167707,
"inputId": 9,
"color": "#ff5293"
},
{
"id": 2408554084144896,
"outputModuleId": 7124670414167707,
"outputId": 1,
"inputModuleId": 6113641652229320,
"inputId": 0,
"color": "#ff5252"
},
{
"id": 1993175531751407,
"outputModuleId": 2323510085504344,
"outputId": 40,
"inputModuleId": 2323510085504344,
"inputId": 22,
"color": "#a8ff52"
},
{
"id": 3675645084235896,
"outputModuleId": 2323510085504344,
"outputId": 60,
"inputModuleId": 7124670414167707,
"inputId": 4,
"color": "#6752ff"
},
{
"id": 914539014511784,
"outputModuleId": 2323510085504344,
"outputId": 28,
"inputModuleId": 7124670414167707,
"inputId": 5,
"color": "#a852ff"
},
{
"id": 4466427789626097,
"outputModuleId": 6704396017183286,
"outputId": 0,
"inputModuleId": 6436949913364135,
"inputId": 1,
"color": "#52beff"
},
{
"id": 6032249062735731,
"outputModuleId": 6704396017183286,
"outputId": 1,
"inputModuleId": 6436949913364135,
"inputId": 0,
"color": "#527dff"
},
{
"id": 5205186222022677,
"outputModuleId": 6436949913364135,
"outputId": 2,
"inputModuleId": 3793316304034300,
"inputId": 0,
"color": "#a852ff"
},
{
"id": 205800917378687,
"outputModuleId": 2323510085504344,
"outputId": 46,
"inputModuleId": 2323510085504344,
"inputId": 31,
"color": "#ffd452"
},
{
"id": 5650060513024868,
"outputModuleId": 2323510085504344,
"outputId": 16,
"inputModuleId": 2323510085504344,
"inputId": 15,
"color": "#67ff52"
},
{
"id": 212470725194084,
"outputModuleId": 3927208667084646,
"outputId": 0,
"inputModuleId": 4515410204981580,
"inputId": 0,
"color": "#52ffff"
},
{
"id": 793863606792629,
"outputModuleId": 5274645123493261,
"outputId": 0,
"inputModuleId": 4385899070319166,
"inputId": 0,
"color": "#52ffff"
},
{
"id": 940323606941669,
"outputModuleId": 7733409763520287,
"outputId": 3,
"inputModuleId": 3982223550835589,
"inputId": 0,
"color": "#67ff52"
},
{
"id": 3055152764376614,
"outputModuleId": 3982223550835589,
"outputId": 0,
"inputModuleId": 3927208667084646,
"inputId": 5,
"color": "#52ffff"
},
{
"id": 5223449680888454,
"outputModuleId": 3982223550835589,
"outputId": 1,
"inputModuleId": 5274645123493261,
"inputId": 5,
"color": "#52ffff"
},
{
"id": 6071685052548665,
"outputModuleId": 6113641652229320,
"outputId": 0,
"inputModuleId": 6704396017183286,
"inputId": 1,
"color": "#527dff"
},
{
"id": 1592690071120657,
"outputModuleId": 2323510085504344,
"outputId": 16,
"inputModuleId": 2323510085504344,
"inputId": 20,
"color": "#ff9352"
}
]
}

+ 0
- 2299
patches/mini/JTB_-_Proof-Of-Concept.vcv
File diff suppressed because it is too large
View File


+ 622
- 0
patches/mini/falkTX_-_Moogy.vcv View File

@@ -0,0 +1,622 @@
{
"version": "2.1.2",
"zoom": 1.0,
"gridOffset": [
-7,
-0.05
],
"modules": [
{
"id": 7797650034473482,
"plugin": "Cardinal",
"model": "TextEditor",
"version": "2.0",
"params": [],
"leftModuleId": 7219430607288126,
"data": {
"filepath": "",
"lang": "None",
"etext": "\n\nThis section spreads\n\nthe unison sound\n\nacross 4 stereo outs\n\n\n\n\n\n",
"width": 14
},
"pos": [
31,
1
]
},
{
"id": 8869926954268675,
"plugin": "Bogaudio",
"model": "Bogaudio-Unison",
"version": "2.0",
"params": [
{
"value": 8.0,
"id": 0
},
{
"value": 4.7590360641479492,
"id": 1
}
],
"data": {},
"pos": [
4,
0
]
},
{
"id": 5726895899473528,
"plugin": "Fundamental",
"model": "ADSR",
"version": "2.0",
"params": [
{
"value": 0.28500017523765564,
"id": 0
},
{
"value": 0.50499969720840454,
"id": 1
},
{
"value": 0.49999982118606567,
"id": 2
},
{
"value": 0.5,
"id": 3
},
{
"value": 0.0,
"id": 4
},
{
"value": 0.0,
"id": 5
},
{
"value": 0.0,
"id": 6
},
{
"value": 0.0,
"id": 7
},
{
"value": 0.0,
"id": 8
}
],
"pos": [
8,
0
]
},
{
"id": 4655444792904207,
"plugin": "MockbaModular",
"model": "CZOsc",
"version": "2.0",
"params": [
{
"value": 7.0,
"id": 0
},
{
"value": 0.0,
"id": 1
},
{
"value": 0.0,
"id": 2
},
{
"value": 0.0,
"id": 3
},
{
"value": 0.0,
"id": 4
}
],
"leftModuleId": 1312836734148177,
"pos": [
21,
0
]
},
{
"id": 1416017514237263,
"plugin": "MockbaModular",
"model": "Filtah",
"version": "2.0",
"params": [
{
"value": 0.0,
"id": 0
},
{
"value": 79.999984741210938,
"id": 1
},
{
"value": 1.348394960132282e-7,
"id": 2
},
{
"value": 0.0,
"id": 3
}
],
"leftModuleId": 1223772688968402,
"pos": [
27,
0
]
},
{
"id": 1312836734148177,
"plugin": "MockbaModular",
"model": "MaugOsc",
"version": "2.0",
"params": [
{
"value": 1.0,
"id": 0
},
{
"value": 0.0,
"id": 1
},
{
"value": 0.0,
"id": 2
},
{
"value": 0.0,
"id": 3
}
],
"rightModuleId": 4655444792904207,
"pos": [
19,
0
]
},
{
"id": 1223772688968402,
"plugin": "MockbaModular",
"model": "Filtah",
"version": "2.0",
"params": [
{
"value": 0.0,
"id": 0
},
{
"value": 79.999984741210938,
"id": 1
},
{
"value": 1.348394960132282e-7,
"id": 2
},
{
"value": 0.0,
"id": 3
}
],
"rightModuleId": 1416017514237263,
"pos": [
25,
0
]
},
{
"id": 4038801811482009,
"plugin": "MockbaModular",
"model": "Mixah",
"version": "2.0",
"params": [
{
"value": 0.55000019073486328,
"id": 0
},
{
"value": 0.0,
"id": 1
}
],
"pos": [
31,
0
]
},
{
"id": 7219430607288126,
"plugin": "Fundamental",
"model": "Split",
"version": "2.0",
"params": [],
"leftModuleId": 1,
"rightModuleId": 7797650034473482,
"pos": [
26,
1
]
},
{
"id": 1079059256177472,
"plugin": "Cardinal",
"model": "TextEditor",
"version": "2.0",
"params": [],
"leftModuleId": 32755851899487,
"data": {
"filepath": "",
"lang": "None",
"etext": "\n\n1 - LP Filter\n2 - Resonance\n3 - OSC 1 <> 2\n4 - Attack\n5 - Decay\n6 - Sustain\n\n\n\n\n",
"width": 11
},
"pos": [
48,
0
]
},
{
"id": 1,
"plugin": "Cardinal",
"model": "HostAudio2",
"version": "2.0",
"params": [
{
"value": 0.66632837057113647,
"id": 0
}
],
"leftModuleId": 3932369330543212,
"rightModuleId": 7219430607288126,
"data": {
"dcFilter": true
},
"pos": [
18,
1
]
},
{
"id": 2,
"plugin": "Cardinal",
"model": "HostMIDI",
"version": "2.0",
"params": [],
"data": {
"pwRange": 0.0,
"smooth": false,
"channels": 1,
"polyMode": 0,
"lastPitch": 8192,
"lastMod": 0,
"inputChannel": 0,
"outputChannel": 0
},
"pos": [
-6,
0
]
},
{
"id": 3932369330543212,
"plugin": "Cardinal",
"model": "HostAudio2",
"version": "2.0",
"params": [
{
"value": 0.66632837057113647,
"id": 0
}
],
"leftModuleId": 1952123403145454,
"rightModuleId": 1,
"data": {
"dcFilter": true
},
"pos": [
10,
1
]
},
{
"id": 1952123403145454,
"plugin": "Cardinal",
"model": "HostAudio2",
"version": "2.0",
"params": [
{
"value": 0.66632837057113647,
"id": 0
}
],
"leftModuleId": 3890811893602150,
"rightModuleId": 3932369330543212,
"data": {
"dcFilter": true
},
"pos": [
2,
1
]
},
{
"id": 3890811893602150,
"plugin": "Cardinal",
"model": "HostAudio2",
"version": "2.0",
"params": [
{
"value": 0.66632837057113647,
"id": 0
}
],
"rightModuleId": 1952123403145454,
"data": {
"dcFilter": true
},
"pos": [
-6,
1
]
},
{
"id": 32755851899487,
"plugin": "Cardinal",
"model": "HostParametersMap",
"version": "2.0",
"params": [],
"rightModuleId": 1079059256177472,
"data": {
"maps": [
{
"hostParamId": 0,
"inverted": false,
"smooth": true,
"moduleId": 1223772688968402,
"paramId": 1
},
{
"hostParamId": 0,
"inverted": false,
"smooth": true,
"moduleId": 1416017514237263,
"paramId": 1
},
{
"hostParamId": 1,
"inverted": false,
"smooth": true,
"moduleId": 1223772688968402,
"paramId": 2
},
{
"hostParamId": 1,
"inverted": false,
"smooth": true,
"moduleId": 1416017514237263,
"paramId": 2
},
{
"hostParamId": 2,
"inverted": false,
"smooth": true,
"moduleId": 4038801811482009,
"paramId": 0
},
{
"hostParamId": 3,
"inverted": false,
"smooth": true,
"moduleId": 5726895899473528,
"paramId": 0
},
{
"hostParamId": 4,
"inverted": false,
"smooth": true,
"moduleId": 5726895899473528,
"paramId": 1
},
{
"hostParamId": 5,
"inverted": false,
"smooth": true,
"moduleId": 5726895899473528,
"paramId": 2
}
]
},
"pos": [
37,
0
]
}
],
"cables": [
{
"id": 8182356705718260,
"outputModuleId": 1312836734148177,
"outputId": 0,
"inputModuleId": 1223772688968402,
"inputId": 2,
"color": "#a8ff52"
},
{
"id": 5472993478872985,
"outputModuleId": 5726895899473528,
"outputId": 0,
"inputModuleId": 1223772688968402,
"inputId": 0,
"color": "#e8ff52"
},
{
"id": 5127890094838131,
"outputModuleId": 2,
"outputId": 1,
"inputModuleId": 8869926954268675,
"inputId": 2,
"color": "#ff5252"
},
{
"id": 4024923731736886,
"outputModuleId": 2,
"outputId": 0,
"inputModuleId": 8869926954268675,
"inputId": 1,
"color": "#ff5252"
},
{
"id": 2334907509933159,
"outputModuleId": 8869926954268675,
"outputId": 0,
"inputModuleId": 1312836734148177,
"inputId": 0,
"color": "#ff5252"
},
{
"id": 3002878830249735,
"outputModuleId": 8869926954268675,
"outputId": 1,
"inputModuleId": 5726895899473528,
"inputId": 4,
"color": "#ff5252"
},
{
"id": 3630780656969299,
"outputModuleId": 7219430607288126,
"outputId": 0,
"inputModuleId": 1,
"inputId": 0,
"color": "#e952ff"
},
{
"id": 2252461163745874,
"outputModuleId": 7219430607288126,
"outputId": 2,
"inputModuleId": 1,
"inputId": 1,
"color": "#e952ff"
},
{
"id": 285917638623769,
"outputModuleId": 7219430607288126,
"outputId": 3,
"inputModuleId": 3932369330543212,
"inputId": 1,
"color": "#e952ff"
},
{
"id": 8064030762561300,
"outputModuleId": 7219430607288126,
"outputId": 7,
"inputModuleId": 3890811893602150,
"inputId": 1,
"color": "#e952ff"
},
{
"id": 5150351568049518,
"outputModuleId": 7219430607288126,
"outputId": 5,
"inputModuleId": 1952123403145454,
"inputId": 1,
"color": "#e952ff"
},
{
"id": 1530942990840499,
"outputModuleId": 7219430607288126,
"outputId": 6,
"inputModuleId": 3890811893602150,
"inputId": 0,
"color": "#e952ff"
},
{
"id": 6358946006960973,
"outputModuleId": 7219430607288126,
"outputId": 4,
"inputModuleId": 1952123403145454,
"inputId": 0,
"color": "#e952ff"
},
{
"id": 6965224767727040,
"outputModuleId": 7219430607288126,
"outputId": 1,
"inputModuleId": 3932369330543212,
"inputId": 0,
"color": "#e952ff"
},
{
"id": 5380295368493604,
"outputModuleId": 4655444792904207,
"outputId": 0,
"inputModuleId": 1416017514237263,
"inputId": 2,
"color": "#a8ff52"
},
{
"id": 2435962983629702,
"outputModuleId": 1223772688968402,
"outputId": 0,
"inputModuleId": 4038801811482009,
"inputId": 2,
"color": "#e952ff"
},
{
"id": 8984394551942722,
"outputModuleId": 1416017514237263,
"outputId": 0,
"inputModuleId": 4038801811482009,
"inputId": 3,
"color": "#e952ff"
},
{
"id": 8445580184820759,
"outputModuleId": 5726895899473528,
"outputId": 0,
"inputModuleId": 1416017514237263,
"inputId": 0,
"color": "#e8ff52"
},
{
"id": 7727190565279635,
"outputModuleId": 8869926954268675,
"outputId": 0,
"inputModuleId": 4655444792904207,
"inputId": 0,
"color": "#ff5252"
},
{
"id": 6359733527436216,
"outputModuleId": 5726895899473528,
"outputId": 0,
"inputModuleId": 4038801811482009,
"inputId": 1,
"color": "#e8ff52"
},
{
"id": 8765471407154125,
"outputModuleId": 2,
"outputId": 6,
"inputModuleId": 5726895899473528,
"inputId": 5,
"color": "#ff9352"
},
{
"id": 8605661946106678,
"outputModuleId": 4038801811482009,
"outputId": 0,
"inputModuleId": 7219430607288126,
"inputId": 0,
"color": "#e952ff"
}
]
}

+ 971
- 0
patches/mini/falkTX_-_Saw_For_One.vcv View File

@@ -0,0 +1,971 @@
{
"version": "2.1.2",
"zoom": 1.0,
"gridOffset": [
-3.8666665554046631,
-0.33421051502227783
],
"modules": [
{
"id": 3530479703931215,
"plugin": "Fundamental",
"model": "LFO",
"version": "2.0",
"params": [
{
"value": 1.0,
"id": 0
},
{
"value": 0.0,
"id": 1
},
{
"value": -0.99517768621444702,
"id": 2
},
{
"value": 0.0,
"id": 3
},
{
"value": 0.0,
"id": 4
},
{
"value": 0.5,
"id": 5
},
{
"value": 0.0,
"id": 6
}
],
"pos": [
0,
-1
]
},
{
"id": 2617521628379532,
"plugin": "Fundamental",
"model": "ADSR",
"version": "2.0",
"params": [
{
"value": 0.2975899875164032,
"id": 0
},
{
"value": 0.53734946250915527,
"id": 1
},
{
"value": 0.31204831600189209,
"id": 2
},
{
"value": 0.5,
"id": 3
},
{
"value": 0.0,
"id": 4
},
{
"value": 0.0,
"id": 5
},
{
"value": 0.0,
"id": 6
},
{
"value": 0.0,
"id": 7
},
{
"value": 0.0,
"id": 8
}
],
"rightModuleId": 6351707277679558,
"pos": [
44,
0
]
},
{
"id": 8914754292241465,
"plugin": "SurgeXTRack",
"model": "SurgeXTOSCSine",
"version": "2.0",
"params": [
{
"value": 0.0,
"id": 0
},
{
"value": 0.44499999284744263,
"id": 1
},
{
"value": 0.60414284467697144,
"id": 2
},
{
"value": 0.99500000476837158,
"id": 3
},
{
"value": 0.0,
"id": 4
},
{
"value": 1.0,
"id": 5
},
{
"value": 0.11999999731779099,
"id": 6
},
{
"value": 0.1276666522026062,
"id": 7
},
{
"value": 0.0,
"id": 8
},
{
"value": 0.0,
"id": 9
},
{
"value": 0.0,
"id": 10
},
{
"value": 0.0,
"id": 11
},
{
"value": 0.0,
"id": 12
},
{
"value": 0.0,
"id": 13
},
{
"value": 0.0,
"id": 14
},
{
"value": 0.0,
"id": 15
},
{
"value": -0.14399991929531097,
"id": 16
},
{
"value": 0.0,
"id": 17
},
{
"value": 0.0,
"id": 18
},
{
"value": 0.0,
"id": 19
},
{
"value": 0.0,
"id": 20
},
{
"value": 0.0,
"id": 21
},
{
"value": 0.0,
"id": 22
},
{
"value": 0.0,
"id": 23
},
{
"value": 0.0,
"id": 24
},
{
"value": 0.0,
"id": 25
},
{
"value": 0.0,
"id": 26
},
{
"value": 0.0,
"id": 27
},
{
"value": 0.0,
"id": 28
},
{
"value": 0.0,
"id": 29
},
{
"value": 0.0,
"id": 30
},
{
"value": 0.0,
"id": 31
},
{
"value": 0.0,
"id": 32
},
{
"value": 0.061999920755624771,
"id": 33
},
{
"value": 0.0,
"id": 34
},
{
"value": 0.0,
"id": 35
},
{
"value": 0.0,
"id": 36
},
{
"value": 0.0,
"id": 37
},
{
"value": 0.0,
"id": 38
},
{
"value": 0.0,
"id": 39
},
{
"value": 0.0,
"id": 40
},
{
"value": 0.0,
"id": 41
},
{
"value": 0.0,
"id": 42
},
{
"value": 0.0,
"id": 43
},
{
"value": 0.0,
"id": 44
},
{
"value": 0.0,
"id": 45
},
{
"value": 0.0,
"id": 46
},
{
"value": 0.0,
"id": 47
},
{
"value": 1.0,
"id": 48
},
{
"value": 0.078000001609325409,
"id": 49
},
{
"value": 1.0,
"id": 50
}
],
"leftModuleId": 287325898511014,
"rightModuleId": 6895418575305544,
"data": {
"xtshared": {
"streamingVersion": 1,
"buildInfo": "os:linux pluggit:Cardinal surgegit:Cardinal buildtime=Feb 19 2023 23:43:29",
"isCoupledToGlobalStyle": true,
"localStyle": 10001,
"localDisplayRegionColor": 900001,
"localModulationColor": 900005,
"localControlValueColor": 900001,
"localPowerButtonColor": 900003
},
"modulespecific": {
"halfbandM": 6,
"halfbandSteep": true,
"doDCBlock": true
}
},
"pos": [
22,
0
]
},
{
"id": 287325898511014,
"plugin": "SurgeXTRack",
"model": "SurgeXTOSCModern",
"version": "2.0",
"params": [
{
"value": 0.0,
"id": 0
},
{
"value": 1.0,
"id": 1
},
{
"value": 0.32114300131797791,
"id": 2
},
{
"value": 0.8151429295539856,
"id": 3
},
{
"value": 0.5,
"id": 4
},
{
"value": 0.0,
"id": 5
},
{
"value": 0.11999999731779099,
"id": 6
},
{
"value": 0.13699999451637268,
"id": 7
},
{
"value": 0.0,
"id": 8
},
{
"value": 0.0,
"id": 9
},
{
"value": 0.0,
"id": 10
},
{
"value": 0.0,
"id": 11
},
{
"value": 0.0,
"id": 12
},
{
"value": -1.0,
"id": 13
},
{
"value": 0.0,
"id": 14
},
{
"value": 0.0,
"id": 15
},
{
"value": 0.16599999368190765,
"id": 16
},
{
"value": 0.0,
"id": 17
},
{
"value": 0.0,
"id": 18
},
{
"value": 0.0,
"id": 19
},
{
"value": -0.28200000524520874,
"id": 20
},
{
"value": 0.0,
"id": 21
},
{
"value": 0.0,
"id": 22
},
{
"value": 0.0,
"id": 23
},
{
"value": 0.0,
"id": 24
},
{
"value": 0.0,
"id": 25
},
{
"value": 0.0,
"id": 26
},
{
"value": 0.0,
"id": 27
},
{
"value": 0.0,
"id": 28
},
{
"value": 0.0,
"id": 29
},
{
"value": 0.0,
"id": 30
},
{
"value": 0.0,
"id": 31
},
{
"value": 0.0,
"id": 32
},
{
"value": 0.0,
"id": 33
},
{
"value": 0.0,
"id": 34
},
{
"value": 0.0,
"id": 35
},
{
"value": 0.0,
"id": 36
},
{
"value": 0.0,
"id": 37
},
{
"value": 0.0,
"id": 38
},
{
"value": 0.0,
"id": 39
},
{
"value": 0.0,
"id": 40
},
{
"value": 0.0,
"id": 41
},
{
"value": 0.0,
"id": 42
},
{
"value": 0.0,
"id": 43
},
{
"value": 0.0,
"id": 44
},
{
"value": 0.0,
"id": 45
},
{
"value": 0.0,
"id": 46
},
{
"value": 0.0,
"id": 47
},
{
"value": 1.0,
"id": 48
},
{
"value": 0.066999994218349457,
"id": 49
},
{
"value": 1.0,
"id": 50
}
],
"rightModuleId": 8914754292241465,
"data": {
"xtshared": {
"streamingVersion": 1,
"buildInfo": "os:linux pluggit:Cardinal surgegit:Cardinal buildtime=Feb 19 2023 23:43:29",
"isCoupledToGlobalStyle": true,
"localStyle": 10001,
"localDisplayRegionColor": 900001,
"localModulationColor": 900005,
"localControlValueColor": 900001,
"localPowerButtonColor": 900003
},
"modulespecific": {
"halfbandM": 6,
"halfbandSteep": true,
"doDCBlock": true
}
},
"pos": [
10,
0
]
},
{
"id": 6895418575305544,
"plugin": "AriaSalvatrice",
"model": "Swerge",
"version": "2.0",
"params": [
{
"value": 0.0,
"id": 0
}
],
"leftModuleId": 8914754292241465,
"rightModuleId": 6420065476624550,
"pos": [
34,
0
]
},
{
"id": 702164998788601,
"plugin": "Fundamental",
"model": "Sum",
"version": "2.0",
"params": [
{
"value": 1.0,
"id": 0
}
],
"leftModuleId": 6420065476624550,
"pos": [
40,
0
]
},
{
"id": 6420065476624550,
"plugin": "Fundamental",
"model": "Sum",
"version": "2.0",
"params": [
{
"value": 1.0,
"id": 0
}
],
"leftModuleId": 6895418575305544,
"rightModuleId": 702164998788601,
"pos": [
37,
0
]
},
{
"id": 6351707277679558,
"plugin": "SurgeXTRack",
"model": "SurgeXTWaveshaper",
"version": "2.0",
"params": [
{
"value": -8.6468648910522461,
"id": 0
},
{
"value": 0.0,
"id": 1
},
{
"value": 0.0,
"id": 2
},
{
"value": -60.0,
"id": 3
},
{
"value": 70.0,
"id": 4
},
{
"value": 0.12800015509128571,
"id": 5
},
{
"value": 0.0,
"id": 6
},
{
"value": 0.0,
"id": 7
},
{
"value": 0.0,
"id": 8
},
{
"value": 0.0,
"id": 9
},
{
"value": 0.21600000560283661,
"id": 10
},
{
"value": 0.0,
"id": 11
},
{
"value": 0.0,
"id": 12
},
{
"value": 0.50200003385543823,
"id": 13
},
{
"value": 0.0,
"id": 14
},
{
"value": 0.0,
"id": 15
},
{
"value": 0.0,
"id": 16
},
{
"value": 0.0,
"id": 17
},
{
"value": 0.0,
"id": 18
},
{
"value": 0.0,
"id": 19
},
{
"value": 0.0,
"id": 20
},
{
"value": 0.0,
"id": 21
},
{
"value": 0.0,
"id": 22
},
{
"value": 0.0,
"id": 23
},
{
"value": 0.0,
"id": 24
},
{
"value": 15.0,
"id": 25
},
{
"value": 0.0,
"id": 26
},
{
"value": 0.0,
"id": 27
}
],
"leftModuleId": 2617521628379532,
"data": {
"xtshared": {
"streamingVersion": 1,
"buildInfo": "os:linux pluggit:Cardinal surgegit:Cardinal buildtime=Feb 19 2023 23:43:29",
"isCoupledToGlobalStyle": true,
"localStyle": 10001,
"localDisplayRegionColor": 900001,
"localModulationColor": 900005,
"localControlValueColor": 900001,
"localPowerButtonColor": 900003
},
"modulespecific": {
"doDCBlock": false
}
},
"pos": [
53,
0
]
},
{
"id": 1,
"plugin": "Cardinal",
"model": "HostAudio2",
"version": "2.0",
"params": [
{
"value": 0.45032820105552673,
"id": 0
}
],
"data": {
"dcFilter": true
},
"pos": [
66,
0
]
},
{
"id": 2,
"plugin": "Cardinal",
"model": "HostMIDI",
"version": "2.0",
"params": [],
"data": {
"pwRange": 0.0,
"smooth": false,
"channels": 1,
"polyMode": 0,
"lastPitch": 8192,
"lastMod": 0,
"inputChannel": 0,
"outputChannel": 0
},
"pos": [
0,
0
]
}
],
"cables": [
{
"id": 7078442804356951,
"outputModuleId": 2,
"outputId": 0,
"inputModuleId": 287325898511014,
"inputId": 0,
"color": "#52beff"
},
{
"id": 2637993111379757,
"outputModuleId": 2,
"outputId": 0,
"inputModuleId": 8914754292241465,
"inputId": 0,
"color": "#52beff"
},
{
"id": 7645122439500280,
"outputModuleId": 2,
"outputId": 6,
"inputModuleId": 287325898511014,
"inputId": 1,
"color": "#527dff"
},
{
"id": 456636951896817,
"outputModuleId": 2,
"outputId": 6,
"inputModuleId": 8914754292241465,
"inputId": 1,
"color": "#527dff"
},
{
"id": 4908672560602015,
"outputModuleId": 2,
"outputId": 1,
"inputModuleId": 2617521628379532,
"inputId": 4,
"color": "#a852ff"
},
{
"id": 3911345250761309,
"outputModuleId": 2,
"outputId": 6,
"inputModuleId": 2617521628379532,
"inputId": 5,
"color": "#527dff"
},
{
"id": 1721551606636812,
"outputModuleId": 6351707277679558,
"outputId": 0,
"inputModuleId": 1,
"inputId": 0,
"color": "#ff5252"
},
{
"id": 8567652559342014,
"outputModuleId": 6351707277679558,
"outputId": 1,
"inputModuleId": 1,
"inputId": 1,
"color": "#ff5252"
},
{
"id": 7051140988441255,
"outputModuleId": 287325898511014,
"outputId": 1,
"inputModuleId": 6895418575305544,
"inputId": 4,
"color": "#ff5252"
},
{
"id": 780441311761289,
"outputModuleId": 8914754292241465,
"outputId": 0,
"inputModuleId": 6895418575305544,
"inputId": 1,
"color": "#ff5252"
},
{
"id": 2400958554319452,
"outputModuleId": 8914754292241465,
"outputId": 1,
"inputModuleId": 6895418575305544,
"inputId": 5,
"color": "#ff5252"
},
{
"id": 5935487313164681,
"outputModuleId": 287325898511014,
"outputId": 0,
"inputModuleId": 6895418575305544,
"inputId": 0,
"color": "#ff5252"
},
{
"id": 7922595614504923,
"outputModuleId": 6895418575305544,
"outputId": 0,
"inputModuleId": 6420065476624550,
"inputId": 0,
"color": "#ff5252"
},
{
"id": 5223439046078660,
"outputModuleId": 6420065476624550,
"outputId": 0,
"inputModuleId": 6351707277679558,
"inputId": 0,
"color": "#ff5252"
},
{
"id": 1550005732923321,
"outputModuleId": 6895418575305544,
"outputId": 1,
"inputModuleId": 702164998788601,
"inputId": 0,
"color": "#ff5252"
},
{
"id": 3466384847513146,
"outputModuleId": 702164998788601,
"outputId": 0,
"inputModuleId": 6351707277679558,
"inputId": 1,
"color": "#ff5252"
},
{
"id": 6350073656502047,
"outputModuleId": 2617521628379532,
"outputId": 0,
"inputModuleId": 287325898511014,
"inputId": 2,
"color": "#a852ff"
},
{
"id": 4319366098337873,
"outputModuleId": 2617521628379532,
"outputId": 0,
"inputModuleId": 8914754292241465,
"inputId": 2,
"color": "#a852ff"
},
{
"id": 960118561480436,
"outputModuleId": 2617521628379532,
"outputId": 0,
"inputModuleId": 6351707277679558,
"inputId": 2,
"color": "#a852ff"
},
{
"id": 6295963384449957,
"outputModuleId": 3530479703931215,
"outputId": 0,
"inputModuleId": 287325898511014,
"inputId": 3,
"color": "#ff5293"
},
{
"id": 5112615215271363,
"outputModuleId": 3530479703931215,
"outputId": 1,
"inputModuleId": 6351707277679558,
"inputId": 3,
"color": "#ff5293"
}
]
}

patches/init/fx.vcv → patches/templates/fx.vcv View File


patches/init/main.vcv → patches/templates/main.vcv View File


+ 283
- 0
patches/templates/mini.vcv View File

@@ -0,0 +1,283 @@
{
"version": "2.1.1",
"zoom": 1.0,
"modules": [
{
"id": 8712245256622475,
"plugin": "Cardinal",
"model": "TextEditor",
"version": "2.0",
"params": [],
"leftModuleId": 1202678850202654,
"data": {
"filepath": "",
"lang": "None",
"etext": "Welcome to Cardinal!\n\nThis is the mini variant\nIt has 2 audio ports, 5 CV ports, plus MIDI\n\nThe most relevant modules for host\nintegration are in this default patch\n\nA basic VCO + ADSR + VCA is\nthe default patch\n\nHave fun!\n\n",
"width": 23
},
"pos": [
58,
0
]
},
{
"id": 5726895899473528,
"plugin": "Fundamental",
"model": "ADSR",
"version": "2.0",
"params": [
{
"value": 0.5,
"id": 0
},
{
"value": 0.5,
"id": 1
},
{
"value": 0.5,
"id": 2
},
{
"value": 0.5,
"id": 3
},
{
"value": 0.0,
"id": 4
},
{
"value": 0.0,
"id": 5
},
{
"value": 0.0,
"id": 6
},
{
"value": 0.0,
"id": 7
},
{
"value": 0.0,
"id": 8
}
],
"leftModuleId": 8601159184541723,
"rightModuleId": 4828178296911509,
"pos": [
18,
0
]
},
{
"id": 4828178296911509,
"plugin": "Fundamental",
"model": "VCA-1",
"version": "2.0",
"params": [
{
"value": 1.0,
"id": 0
},
{
"value": 1.0,
"id": 1
}
],
"leftModuleId": 5726895899473528,
"rightModuleId": 1,
"pos": [
27,
0
]
},
{
"id": 8601159184541723,
"plugin": "Fundamental",
"model": "VCO",
"version": "2.0",
"params": [
{
"value": 0.0,
"id": 0
},
{
"value": 1.0,
"id": 1
},
{
"value": 0.0,
"id": 2
},
{
"value": 0.0,
"id": 3
},
{
"value": 0.0,
"id": 4
},
{
"value": 0.5,
"id": 5
},
{
"value": 0.0,
"id": 6
},
{
"value": 0.0,
"id": 7
}
],
"leftModuleId": 2,
"rightModuleId": 5726895899473528,
"pos": [
9,
0
]
},
{
"id": 1,
"plugin": "Cardinal",
"model": "HostAudio2",
"version": "2.0",
"params": [
{
"value": 0.79432821273803711,
"id": 0
}
],
"leftModuleId": 4828178296911509,
"rightModuleId": 4,
"data": {
"dcFilter": true
},
"pos": [
30,
0
]
},
{
"id": 2,
"plugin": "Cardinal",
"model": "HostMIDI",
"version": "2.0",
"params": [],
"rightModuleId": 8601159184541723,
"data": {
"pwRange": 0.0,
"smooth": false,
"channels": 1,
"polyMode": 0,
"lastPitch": 8192,
"lastMod": 0,
"inputChannel": 0,
"outputChannel": 0
},
"pos": [
0,
0
]
},
{
"id": 4,
"plugin": "Cardinal",
"model": "HostParameters",
"version": "2.0",
"params": [],
"leftModuleId": 1,
"rightModuleId": 1202678850202654,
"data": {
"smooth": true
},
"pos": [
38,
0
]
},
{
"id": 1202678850202654,
"plugin": "Cardinal",
"model": "HostParametersMap",
"version": "2.0",
"params": [],
"leftModuleId": 4,
"rightModuleId": 8712245256622475,
"data": {
"maps": [
{
"hostParamId": 255,
"inverted": false,
"smooth": true,
"moduleId": -1,
"paramId": 0
}
]
},
"pos": [
47,
0
]
}
],
"cables": [
{
"id": 5155876120487880,
"outputModuleId": 2,
"outputId": 1,
"inputModuleId": 5726895899473528,
"inputId": 4,
"color": "#ff9352"
},
{
"id": 781753834216137,
"outputModuleId": 2,
"outputId": 6,
"inputModuleId": 5726895899473528,
"inputId": 5,
"color": "#ffd452"
},
{
"id": 3464471860196875,
"outputModuleId": 5726895899473528,
"outputId": 0,
"inputModuleId": 4828178296911509,
"inputId": 0,
"color": "#e8ff52"
},
{
"id": 739552540616113,
"outputModuleId": 4828178296911509,
"outputId": 0,
"inputModuleId": 1,
"inputId": 0,
"color": "#52beff"
},
{
"id": 6701970185765111,
"outputModuleId": 2,
"outputId": 0,
"inputModuleId": 8601159184541723,
"inputId": 0,
"color": "#ff5252"
},
{
"id": 6959800657121782,
"outputModuleId": 2,
"outputId": 2,
"inputModuleId": 8601159184541723,
"inputId": 1,
"color": "#52ff7d"
},
{
"id": 1598271319373837,
"outputModuleId": 8601159184541723,
"outputId": 0,
"inputModuleId": 4828178296911509,
"inputId": 1,
"color": "#a8ff52"
}
]
}

patches/init/native.vcv → patches/templates/native.vcv View File


patches/init/synth.vcv → patches/templates/synth.vcv View File


BIN
patches/touchosc/24-direct-fader-params.tosc View File


+ 29
- 14
patches/welcome-wasm-mini.vcv View File

@@ -1,6 +1,5 @@
{
"version": "2.1.2",
"unsaved": true,
"version": "2.1.1",
"zoom": 1.0,
"modules": [
{
@@ -9,15 +8,15 @@
"model": "TextEditor",
"version": "2.0",
"params": [],
"leftModuleId": 799138358763949,
"leftModuleId": 1202678850202654,
"data": {
"filepath": "",
"lang": "None",
"etext": "Welcome to Cardinal!\n\nThis is the Web/Wasm variant\nIt has 2 audio outputs, enabled by default.\nUse Engine menu to enable input and/or MIDI.\n\nA basic VCO + ADSR + VCA is the default patch\n\n",
"width": 23
"etext": "Welcome to Cardinal!\n\nThis is the mini variant\nIt has 2 audio outputs, with optional audio input and MIDI (enabled via Engine menu)\n\nA basic VCO + ADSR + VCA is the default patch\n\nHave fun!\n\n",
"width": 19
},
"pos": [
49,
58,
0
]
},
@@ -151,7 +150,7 @@
}
],
"leftModuleId": 4828178296911509,
"rightModuleId": 799138358763949,
"rightModuleId": 4,
"data": {
"dcFilter": true
},
@@ -183,26 +182,42 @@
]
},
{
"id": 799138358763949,
"id": 4,
"plugin": "Cardinal",
"model": "HostMIDIMap",
"model": "HostParameters",
"version": "2.0",
"params": [],
"leftModuleId": 1,
"rightModuleId": 1202678850202654,
"data": {
"smooth": true
},
"pos": [
38,
0
]
},
{
"id": 1202678850202654,
"plugin": "Cardinal",
"model": "HostParametersMap",
"version": "2.0",
"params": [],
"leftModuleId": 4,
"rightModuleId": 8712245256622475,
"data": {
"maps": [
{
"cc": -1,
"hostParamId": 255,
"inverted": false,
"smooth": true,
"moduleId": -1,
"paramId": 0
}
],
"smooth": true,
"channel": 0
]
},
"pos": [
38,
47,
0
]
}


+ 136
- 1064
patches/welcome-wasm.vcv
File diff suppressed because it is too large
View File


+ 1
- 1
plugins/AS

@@ -1 +1 @@
Subproject commit 93aa1d0bbb2550bf05998e331e603e87425aeb91
Subproject commit b5fdb76c79688207e56bd5b07b01e9c63a102797

+ 1
- 1
plugins/AnimatedCircuits

@@ -1 +1 @@
Subproject commit 76c2912fd6ebdd7c3e33fca88096bea9c67209a1
Subproject commit bf78cd8ed22970fe9dc5ebff8e3907898904c747

+ 1
- 1
plugins/ArableInstruments

@@ -1 +1 @@
Subproject commit 890448f087e3ab47eac391f9bcfe03f7bbd2123e
Subproject commit a2de62d0c3b9f764ce6b42441366788d1e52bfcc

+ 1
- 1
plugins/AudibleInstruments

@@ -1 +1 @@
Subproject commit 2a19bb25c0da725756390ad96dca55632800c74d
Subproject commit 1f279a02d955667341d08f74ddf2054d10e82c65

+ 1
- 1
plugins/BaconPlugs

@@ -1 +1 @@
Subproject commit adf84fc00a953f8e8a1b378531a08ee68b9a68d7
Subproject commit a86d5081d12a72ae0d0c775c61813b695cde8a9c

+ 1
- 1
plugins/Befaco

@@ -1 +1 @@
Subproject commit dcd9a59ea785d7efebd39ea5564823c72f2fdddf
Subproject commit fcf9b564017d8eee63504771a3006bea81749ff8

+ 1
- 1
plugins/Bidoo

@@ -1 +1 @@
Subproject commit 97f61b3616a6e0935ac84f02b1e35734413c6b34
Subproject commit 8610d4c86740d9d67ebfa4ded70279df7aeb95be

+ 2
- 3
plugins/BidooDark/plugin.cpp View File

@@ -1,5 +1,4 @@
#include "../Bidoo/src/plugin.hpp"
#undef ModuleWidget

void InstantiateExpanderItem::onAction(const event::Action &e) {
engine::Module* module = model->createModule();
@@ -16,7 +15,7 @@ void InstantiateExpanderItem::onAction(const event::Action &e) {
}

json_t* BidooModule::dataToJson() {
return nullptr;
return json_object();
}

void BidooModule::dataFromJson(json_t*) {
@@ -36,5 +35,5 @@ void BidooWidget::prepareThemes(const std::string& filename) {
}

void BidooWidget::step() {
CardinalModuleWidget::step();
ModuleWidget::step();
}

+ 10
- 0
plugins/Cardinal/plugin.json View File

@@ -117,6 +117,16 @@
"Visual"
]
},
{
"slug": "AIDA-X",
"name": "AIDA-X",
"description": "Amp Model Player leveraging AI",
"manualUrl": "https://github.com/DISTRHO/Cardinal/blob/main/docs/CARDINAL-MODULES.md#aidax",
"tags": [
"Distortion",
"Effect"
]
},
{
"slug": "Blank",
"name": "Blank",


+ 130
- 0
plugins/Cardinal/res/AIDA-X.svg View File

@@ -0,0 +1,130 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<!-- Created with Inkscape (http://www.inkscape.org/) -->

<svg
width="116.84mm"
height="128.5mm"
viewBox="0 0 116.84 128.5"
version="1.1"
id="svg4620"
sodipodi:docname="AIDA-X.svg"
inkscape:version="1.1.2 (0a00cf5339, 2022-02-04)"
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
xmlns="http://www.w3.org/2000/svg"
xmlns:svg="http://www.w3.org/2000/svg"
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
xmlns:cc="http://creativecommons.org/ns#"
xmlns:dc="http://purl.org/dc/elements/1.1/">
<sodipodi:namedview
id="namedview40"
pagecolor="#ffffff"
bordercolor="#666666"
borderopacity="1.0"
inkscape:pageshadow="2"
inkscape:pageopacity="0.0"
inkscape:pagecheckerboard="0"
inkscape:document-units="mm"
showgrid="false"
inkscape:zoom="1.3260052"
inkscape:cx="220.96444"
inkscape:cy="302.78916"
inkscape:window-width="2560"
inkscape:window-height="1367"
inkscape:window-x="0"
inkscape:window-y="0"
inkscape:window-maximized="1"
inkscape:current-layer="svg4620" />
<defs
id="defs4614">
<style
id="style6"
type="text/css">
.str0 {stroke:#565656;stroke-width:0.0966867}
.str1 {stroke:#4F4F4F;stroke-width:0.193345}
.fil0 {fill:none}
.fil2 {fill:#2B2A29}
.fil1 {fill:#6B6B6B}
</style>
<clipPath
clipPathUnits="userSpaceOnUse"
id="clipPath847">
<g
id="use849">
<g
transform="matrix(6.342689,0,0,6.342689,5.4472535,175.6457)"
id="g865"
style="fill-rule:evenodd">
<g
id="g863"
transform="translate(-1.6191379e-5,-0.08553947)"
inkscape:label="Layer 1">
<metadata
id="metadata857" />
<path
id="path859"
style="fill:none;stroke:#ffffff;stroke-width:0.0966867"
class="fil0 str0"
d="m 0.684386,0.61075097 a 0.15916,0.15916 0 0 1 -0.15916,0.15916001 0.15916,0.15916 0 0 1 -0.15916001,-0.15916001 0.15916,0.15916 0 0 1 0.15916001,-0.15916 0.15916,0.15916 0 0 1 0.15916,0.15916 z" />
<path
id="path861"
style="fill:none;stroke:#ffffff;stroke-width:0.193345"
class="fil0 str1"
d="M 0.953765,0.61075097 A 0.42853901,0.42853901 0 0 1 0.525226,1.03929 0.42853901,0.42853901 0 0 1 0.09668699,0.61075097 0.42853901,0.42853901 0 0 1 0.525226,0.18221197 a 0.42853901,0.42853901 0 0 1 0.428539,0.428539 z" />
</g>
</g>
<g
transform="translate(-0.09449404,0.14174107)"
id="g883"
style="font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;font-size:10.5833px;line-height:1.25;font-family:'DejaVu Sans';-inkscape-font-specification:'DejaVu Sans, Normal';font-variant-ligatures:normal;font-variant-caps:normal;font-variant-numeric:normal;text-align:start;letter-spacing:0px;word-spacing:0px;writing-mode:lr-tb;text-anchor:start;fill:#000000;fill-opacity:1;stroke:none;stroke-width:0.264583"
aria-label="Cardinal">
<path
id="path867"
style="font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;font-size:6.35px;font-family:'DejaVu Sans';-inkscape-font-specification:'DejaVu Sans, Normal';font-variant-ligatures:normal;font-variant-caps:normal;font-variant-numeric:normal;font-feature-settings:normal;text-align:start;writing-mode:lr-tb;text-anchor:start;fill:#ffffff;fill-opacity:1;stroke-width:0.264583"
d="m 17.923601,176.99103 v 0.66043 q -0.31626,-0.29456 -0.675928,-0.44028 -0.356567,-0.14573 -0.759643,-0.14573 -0.79375,0 -1.21543,0.48679 -0.42168,0.48369 -0.42168,1.40146 0,0.91468 0.42168,1.40147 0.42168,0.48369 1.21543,0.48369 0.403076,0 0.759643,-0.14573 0.359668,-0.14572 0.675928,-0.44028 v 0.65422 q -0.328662,0.22325 -0.697632,0.33487 -0.365869,0.11162 -0.775146,0.11162 -1.051099,0 -1.655713,-0.64182 -0.604615,-0.64492 -0.604615,-1.75804 0,-1.11621 0.604615,-1.75803 0.604614,-0.64492 1.655713,-0.64492 0.415478,0 0.781347,0.11162 0.36897,0.10852 0.691431,0.32866 z" />
<path
id="path869"
style="font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;font-size:6.35px;font-family:'DejaVu Sans';-inkscape-font-specification:'DejaVu Sans, Normal';font-variant-ligatures:normal;font-variant-caps:normal;font-variant-numeric:normal;font-feature-settings:normal;text-align:start;writing-mode:lr-tb;text-anchor:start;fill:#ffffff;fill-opacity:1;stroke-width:0.264583"
d="m 20.444377,179.51801 q -0.69143,0 -0.958081,0.15813 -0.26665,0.15813 -0.26665,0.5395 0,0.30386 0.198437,0.48369 0.201538,0.17674 0.545703,0.17674 0.47439,0 0.759644,-0.33487 0.288355,-0.33796 0.288355,-0.89606 v -0.12713 z m 1.137915,-0.23564 v 1.98127 h -0.570507 v -0.5271 q -0.195337,0.31626 -0.486792,0.46819 -0.291456,0.14883 -0.713135,0.14883 -0.533301,0 -0.849561,-0.29766 -0.313159,-0.30075 -0.313159,-0.80305 0,-0.58601 0.390674,-0.88367 0.393774,-0.29765 1.172021,-0.29765 h 0.799952 v -0.0558 q 0,-0.39378 -0.26045,-0.60772 -0.257348,-0.21704 -0.725537,-0.21704 -0.297656,0 -0.579809,0.0713 -0.282154,0.0713 -0.542603,0.21394 v -0.52709 q 0.313159,-0.12093 0.607715,-0.17984 0.294556,-0.062 0.573608,-0.062 0.753443,0 1.125513,0.39067 0.37207,0.39068 0.37207,1.18443 z" />
<path
id="path871"
style="font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;font-size:6.35px;font-family:'DejaVu Sans';-inkscape-font-specification:'DejaVu Sans, Normal';font-variant-ligatures:normal;font-variant-caps:normal;font-variant-numeric:normal;font-feature-settings:normal;text-align:start;writing-mode:lr-tb;text-anchor:start;fill:#ffffff;fill-opacity:1;stroke-width:0.264583"
d="m 24.769695,178.32429 q -0.09612,-0.0558 -0.21084,-0.0806 -0.111621,-0.0279 -0.248047,-0.0279 -0.483691,0 -0.744141,0.31626 -0.257348,0.31315 -0.257348,0.90227 v 1.82934 H 22.73571 v -3.47265 h 0.573609 v 0.5395 q 0.179834,-0.31626 0.468188,-0.46819 0.288355,-0.15503 0.700733,-0.15503 0.05891,0 0.130224,0.009 0.07131,0.006 0.15813,0.0217 z" />
<path
id="path873"
style="font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;font-size:6.35px;font-family:'DejaVu Sans';-inkscape-font-specification:'DejaVu Sans, Normal';font-variant-ligatures:normal;font-variant-caps:normal;font-variant-numeric:normal;font-feature-settings:normal;text-align:start;writing-mode:lr-tb;text-anchor:start;fill:#ffffff;fill-opacity:1;stroke-width:0.264583"
d="m 27.541618,178.31808 v -1.87895 h 0.570508 v 4.82451 h -0.570508 v -0.5209 q -0.179834,0.31006 -0.455786,0.46199 -0.272851,0.14883 -0.657324,0.14883 -0.629419,0 -1.026294,-0.5023 -0.393774,-0.50229 -0.393774,-1.32085 0,-0.81855 0.393774,-1.32085 0.396875,-0.50229 1.026294,-0.50229 0.384473,0 0.657324,0.15193 0.275952,0.14883 0.455786,0.45888 z m -1.944067,1.21233 q 0,0.62942 0.257349,0.98909 0.260449,0.35657 0.713134,0.35657 0.452686,0 0.713135,-0.35657 0.260449,-0.35967 0.260449,-0.98909 0,-0.62942 -0.260449,-0.98598 -0.260449,-0.35967 -0.713135,-0.35967 -0.452685,0 -0.713134,0.35967 -0.257349,0.35656 -0.257349,0.98598 z" />
<path
id="path875"
style="font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;font-size:6.35px;font-family:'DejaVu Sans';-inkscape-font-specification:'DejaVu Sans, Normal';font-variant-ligatures:normal;font-variant-caps:normal;font-variant-numeric:normal;font-feature-settings:normal;text-align:start;writing-mode:lr-tb;text-anchor:start;fill:#ffffff;fill-opacity:1;stroke-width:0.264583"
d="m 29.287248,177.79099 h 0.570508 v 3.47265 h -0.570508 z m 0,-1.35186 h 0.570508 v 0.72244 h -0.570508 z" />
<path
id="path877"
style="font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;font-size:6.35px;font-family:'DejaVu Sans';-inkscape-font-specification:'DejaVu Sans, Normal';font-variant-ligatures:normal;font-variant-caps:normal;font-variant-numeric:normal;font-feature-settings:normal;text-align:start;writing-mode:lr-tb;text-anchor:start;fill:#ffffff;fill-opacity:1;stroke-width:0.264583"
d="m 33.938127,179.16765 v 2.09599 h -0.570508 v -2.07739 q 0,-0.49299 -0.192236,-0.73794 -0.192236,-0.24495 -0.576709,-0.24495 -0.461987,0 -0.728638,0.29456 -0.26665,0.29455 -0.26665,0.80305 v 1.96267 h -0.573608 v -3.47265 h 0.573608 v 0.5395 q 0.204639,-0.31316 0.480591,-0.46819 0.279053,-0.15503 0.641821,-0.15503 0.598413,0 0.905371,0.37207 0.306958,0.36897 0.306958,1.08831 z" />
<path
id="path879"
style="font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;font-size:6.35px;font-family:'DejaVu Sans';-inkscape-font-specification:'DejaVu Sans, Normal';font-variant-ligatures:normal;font-variant-caps:normal;font-variant-numeric:normal;font-feature-settings:normal;text-align:start;writing-mode:lr-tb;text-anchor:start;fill:#ffffff;fill-opacity:1;stroke-width:0.264583"
d="m 36.654241,179.51801 q -0.691431,0 -0.958081,0.15813 -0.26665,0.15813 -0.26665,0.5395 0,0.30386 0.198437,0.48369 0.201538,0.17674 0.545703,0.17674 0.47439,0 0.759644,-0.33487 0.288354,-0.33796 0.288354,-0.89606 v -0.12713 z m 1.137915,-0.23564 v 1.98127 h -0.570508 v -0.5271 q -0.195337,0.31626 -0.486792,0.46819 -0.291455,0.14883 -0.713135,0.14883 -0.5333,0 -0.84956,-0.29766 -0.313159,-0.30075 -0.313159,-0.80305 0,-0.58601 0.390674,-0.88367 0.393774,-0.29765 1.172021,-0.29765 h 0.799951 v -0.0558 q 0,-0.39378 -0.260449,-0.60772 -0.257349,-0.21704 -0.725537,-0.21704 -0.297656,0 -0.57981,0.0713 -0.282153,0.0713 -0.542602,0.21394 v -0.52709 q 0.313159,-0.12093 0.607715,-0.17984 0.294555,-0.062 0.573608,-0.062 0.753442,0 1.125513,0.39067 0.37207,0.39068 0.37207,1.18443 z" />
<path
id="path881"
style="font-style:normal;font-variant:normal;font-weight:normal;font-stretch:normal;font-size:6.35px;font-family:'DejaVu Sans';-inkscape-font-specification:'DejaVu Sans, Normal';font-variant-ligatures:normal;font-variant-caps:normal;font-variant-numeric:normal;font-feature-settings:normal;text-align:start;writing-mode:lr-tb;text-anchor:start;fill:#ffffff;fill-opacity:1;stroke-width:0.264583"
d="m 38.967278,176.43913 h 0.570508 v 4.82451 h -0.570508 z" />
</g>
</g>
</clipPath>
</defs>
<metadata
id="metadata4617">
<rdf:RDF>
<cc:Work
rdf:about="">
<dc:format>image/svg+xml</dc:format>
<dc:type
rdf:resource="http://purl.org/dc/dcmitype/StillImage" />
</cc:Work>
</rdf:RDF>
</metadata>
</svg>

BIN
plugins/Cardinal/res/aida-x-background-p2.png View File

Before After
Width: 512  |  Height: 256  |  Size: 38KB

+ 46
- 0
plugins/Cardinal/res/aida-x-knob.svg View File

@@ -0,0 +1,46 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<svg
width="36"
height="36"
version="1.1"
xml:space="preserve"
style="clip-rule:evenodd;fill-rule:evenodd"
id="svg6"
sodipodi:docname="aida-x-knob.svg"
inkscape:version="1.1.2 (0a00cf5339, 2022-02-04)"
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
xmlns="http://www.w3.org/2000/svg"
xmlns:svg="http://www.w3.org/2000/svg"><defs
id="defs10" /><sodipodi:namedview
id="namedview8"
pagecolor="#ffffff"
bordercolor="#666666"
borderopacity="1.0"
inkscape:pageshadow="2"
inkscape:pageopacity="0.0"
inkscape:pagecheckerboard="0"
showgrid="false"
width="36px"
inkscape:zoom="13.702128"
inkscape:cx="19.267081"
inkscape:cy="23.463509"
inkscape:window-width="2560"
inkscape:window-height="1367"
inkscape:window-x="0"
inkscape:window-y="0"
inkscape:window-maximized="1"
inkscape:current-layer="svg6" />
<g
id="knobLDark"
transform="matrix(0.7652677,0,0,0.76595949,6.0168332e-5,0)">
<path
id="path3832"
d="m 23.521,45.109 c -7.674,0 -3.302,3.9 -10.224,0.498 C 6.375,42.204 12.095,43.266 7.3,37.106 2.505,30.947 2.241,36.905 0.537,29.279 -1.167,21.654 1.58,26.859 3.297,19.233 5.015,11.607 0.299,15.131 5.094,9.012 9.889,2.892 7.604,8.339 14.526,4.977 21.447,1.614 15.847,0 23.521,0 c 7.675,0 2.087,1.574 8.996,4.977 6.909,3.402 4.636,-2.045 9.432,4.035 4.795,6.078 0.079,2.689 1.796,10.26 1.717,7.572 4.465,2.422 2.761,10.048 -1.704,7.625 -1.982,1.708 -6.763,7.827 -4.782,6.119 0.924,5.057 -5.998,8.46 -6.921,3.402 -2.549,-0.498 -10.224,-0.498 z"
style="fill:#e6e5e5;fill-rule:nonzero" />
<path
d="M 23.521,23.5 V 0"
style="fill:none;fill-rule:nonzero;stroke:#333333;stroke-width:2.29px"
id="path3" />
</g>
</svg>

BIN
plugins/Cardinal/res/aida-x-logo.png View File

Before After
Width: 485  |  Height: 109  |  Size: 18KB

+ 35
- 0
plugins/Cardinal/res/aida-x-scale.svg View File

@@ -0,0 +1,35 @@
<?xml version="1.0" encoding="utf-8"?>
<!-- Generator: Adobe Illustrator 16.0.3, SVG Export Plug-In . SVG Version: 6.00 Build 0) -->
<!DOCTYPE svg PUBLIC "-//W3C//DTD SVG 1.1//EN" "http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd">
<svg version="1.1" id="Layer_1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" x="0px" y="0px"
width="1000px" height="1000px" viewBox="0 0 1000 1000" enable-background="new 0 0 1000 1000" xml:space="preserve">
<image display="none" overflow="visible" width="1100" height="1100" xlink:href="scale.png" transform="matrix(0.9999 0 0 0.9999 -50 -20)">
</image>
<circle display="none" fill="#969696" cx="500" cy="529.932" r="397"/>
<path fill="#969696" d="M504.417,129.643c0,2.913-2.238,5.274-5,5.274l0,0c-2.761,0-5-2.361-5-5.274V64.774
c0-2.913,2.239-5.274,5-5.274l0,0c2.762,0,5,2.361,5,5.274V129.643z"/>
<path fill="#969696" d="M350.896,158.423c1.114,2.69-0.05,5.729-2.602,6.785l0,0c-2.551,1.057-5.523-0.268-6.638-2.958
l-24.824-59.931c-1.114-2.691,0.05-5.729,2.602-6.786l0,0c2.552-1.057,5.522,0.269,6.638,2.959L350.896,158.423z"/>
<path fill="#969696" d="M220.075,243.762c2.06,2.06,2.146,5.312,0.193,7.264l0,0c-1.952,1.953-5.205,1.867-7.265-0.193
l-45.869-45.87c-2.06-2.059-2.146-5.312-0.193-7.265l0,0c1.953-1.953,5.205-1.865,7.265,0.194L220.075,243.762z"/>
<path fill="#969696" d="M131.87,372.668c2.691,1.114,4.016,4.086,2.959,6.637l0,0c-1.057,2.551-4.095,3.716-6.786,2.602
l-59.931-24.825c-2.69-1.114-4.016-4.086-2.959-6.638l0,0c1.058-2.552,4.095-3.715,6.786-2.601L131.87,372.668z"/>
<path fill="#969696" d="M99.71,525.516c2.913,0,5.273,2.238,5.273,5l0,0c0,2.762-2.36,5-5.274,5.001H34.841
c-2.912,0-5.274-2.239-5.274-5.001l0,0c0.001-2.762,2.361-5,5.274-5H99.71z"/>
<path fill="#969696" d="M128.49,679.037c2.691-1.115,5.729,0.049,6.785,2.601l0,0c1.057,2.552-0.268,5.522-2.959,6.639
l-59.931,24.824c-2.69,1.114-5.729-0.051-6.787-2.603l0,0c-1.056-2.552,0.269-5.522,2.96-6.638L128.49,679.037z"/>
<path fill="#969696" d="M213.829,809.857c2.06-2.06,5.312-2.146,7.265-0.193l0,0c1.952,1.953,1.865,5.205-0.193,7.266
l-45.869,45.869c-2.06,2.059-5.313,2.146-7.267,0.192l0,0c-1.952-1.953-1.865-5.204,0.194-7.265L213.829,809.857z"/>
<path fill="#969696" d="M779.925,816.104c-2.06-2.06-2.146-5.313-0.193-7.266l0,0c1.952-1.952,5.206-1.864,7.266,0.195
l45.868,45.869c2.06,2.06,2.146,5.311,0.192,7.266l0,0c-1.952,1.953-5.202,1.864-7.263-0.194L779.925,816.104z"/>
<path fill="#969696" d="M868.129,687.197c-2.69-1.114-4.015-4.087-2.959-6.639l0,0c1.057-2.551,4.097-3.715,6.788-2.6l59.93,24.824
c2.69,1.115,4.015,4.086,2.958,6.64l0,0c-1.057,2.551-4.093,3.713-6.784,2.6L868.129,687.197z"/>
<path fill="#969696" d="M900.289,534.35c-2.912,0-5.273-2.24-5.274-5.001l0,0c0-2.762,2.363-5,5.276-5l64.868,0.001
c2.913,0,5.272,2.238,5.273,5.002l0,0c0,2.761-2.36,4.996-5.272,4.998H900.289z"/>
<path fill="#969696" d="M871.509,380.829c-2.69,1.115-5.729-0.052-6.786-2.602l0,0c-1.058-2.552,0.27-5.524,2.961-6.639
l59.931-24.823c2.691-1.114,5.728,0.051,6.786,2.604l0,0c1.057,2.551-0.269,5.519-2.958,6.635L871.509,380.829z"/>
<path fill="#969696" d="M786.17,250.009c-2.06,2.06-5.313,2.145-7.266,0.193l0,0c-1.953-1.953-1.864-5.207,0.195-7.267
l45.869-45.868c2.061-2.06,5.311-2.145,7.266-0.191l0,0c1.953,1.952,1.864,5.201-0.193,7.262L786.17,250.009z"/>
<path fill="#969696" d="M657.265,161.804c-1.115,2.691-4.089,4.015-6.64,2.959l0,0c-2.551-1.057-3.714-4.097-2.6-6.789l24.824-59.93
c1.115-2.691,4.086-4.014,6.64-2.957l0,0c2.552,1.056,3.713,4.092,2.601,6.783L657.265,161.804z"/>
</svg>

+ 1114
- 0
plugins/Cardinal/src/AIDA-X.cpp
File diff suppressed because it is too large
View File


+ 165
- 0
plugins/Cardinal/src/AIDA-X/Biquad.cpp View File

@@ -0,0 +1,165 @@
//
// Biquad.cpp
//
// Created by Nigel Redmon on 11/24/12
// EarLevel Engineering: earlevel.com
// Copyright 2012 Nigel Redmon
//
// For a complete explanation of the Biquad code:
// http://www.earlevel.com/main/2012/11/26/biquad-c-source-code/
//
// License:
//
// This source code is provided as is, without warranty.
// You may copy and distribute verbatim copies of this document.
// You may modify and use this source code to create binary code
// for your own purposes, free or commercial.
//

#include <math.h>
#include "Biquad.h"

Biquad::Biquad() {
type = bq_type_lowpass;
a0 = 1.0;
a1 = a2 = b1 = b2 = 0.0;
Fc = 0.50;
Q = 0.707;
peakGain = 0.0;
z1 = z2 = 0.0;
}

Biquad::Biquad(int type, double Fc, double Q, double peakGainDB) {
setBiquad(type, Fc, Q, peakGainDB);
z1 = z2 = 0.0;
}

Biquad::~Biquad() {
}

void Biquad::setType(int type) {
this->type = type;
calcBiquad();
}

void Biquad::setQ(double Q) {
this->Q = Q;
calcBiquad();
}

void Biquad::setFc(double Fc) {
this->Fc = Fc;
calcBiquad();
}

void Biquad::setPeakGain(double peakGainDB) {
this->peakGain = peakGainDB;
calcBiquad();
}

void Biquad::setBiquad(int type, double Fc, double Q, double peakGainDB) {
this->type = type;
this->Q = Q;
this->Fc = Fc;
setPeakGain(peakGainDB);
}

void Biquad::calcBiquad(void) {
double norm;
double V = pow(10, fabs(peakGain) / 20.0);
double K = tan(M_PI * Fc);
switch (this->type) {
case bq_type_lowpass:
norm = 1 / (1 + K / Q + K * K);
a0 = K * K * norm;
a1 = 2 * a0;
a2 = a0;
b1 = 2 * (K * K - 1) * norm;
b2 = (1 - K / Q + K * K) * norm;
break;

case bq_type_highpass:
norm = 1 / (1 + K / Q + K * K);
a0 = 1 * norm;
a1 = -2 * a0;
a2 = a0;
b1 = 2 * (K * K - 1) * norm;
b2 = (1 - K / Q + K * K) * norm;
break;

case bq_type_bandpass:
norm = 1 / (1 + K / Q + K * K);
a0 = K / Q * norm;
a1 = 0;
a2 = -a0;
b1 = 2 * (K * K - 1) * norm;
b2 = (1 - K / Q + K * K) * norm;
break;

case bq_type_notch:
norm = 1 / (1 + K / Q + K * K);
a0 = (1 + K * K) * norm;
a1 = 2 * (K * K - 1) * norm;
a2 = a0;
b1 = a1;
b2 = (1 - K / Q + K * K) * norm;
break;

case bq_type_peak:
if (peakGain >= 0) { // boost
norm = 1 / (1 + 1/Q * K + K * K);
a0 = (1 + V/Q * K + K * K) * norm;
a1 = 2 * (K * K - 1) * norm;
a2 = (1 - V/Q * K + K * K) * norm;
b1 = a1;
b2 = (1 - 1/Q * K + K * K) * norm;
}
else { // cut
norm = 1 / (1 + V/Q * K + K * K);
a0 = (1 + 1/Q * K + K * K) * norm;
a1 = 2 * (K * K - 1) * norm;
a2 = (1 - 1/Q * K + K * K) * norm;
b1 = a1;
b2 = (1 - V/Q * K + K * K) * norm;
}
break;
case bq_type_lowshelf:
if (peakGain >= 0) { // boost
norm = 1 / (1 + sqrt(2) * K + K * K);
a0 = (1 + sqrt(2*V) * K + V * K * K) * norm;
a1 = 2 * (V * K * K - 1) * norm;
a2 = (1 - sqrt(2*V) * K + V * K * K) * norm;
b1 = 2 * (K * K - 1) * norm;
b2 = (1 - sqrt(2) * K + K * K) * norm;
}
else { // cut
norm = 1 / (1 + sqrt(2*V) * K + V * K * K);
a0 = (1 + sqrt(2) * K + K * K) * norm;
a1 = 2 * (K * K - 1) * norm;
a2 = (1 - sqrt(2) * K + K * K) * norm;
b1 = 2 * (V * K * K - 1) * norm;
b2 = (1 - sqrt(2*V) * K + V * K * K) * norm;
}
break;
case bq_type_highshelf:
if (peakGain >= 0) { // boost
norm = 1 / (1 + sqrt(2) * K + K * K);
a0 = (V + sqrt(2*V) * K + K * K) * norm;
a1 = 2 * (K * K - V) * norm;
a2 = (V - sqrt(2*V) * K + K * K) * norm;
b1 = 2 * (K * K - 1) * norm;
b2 = (1 - sqrt(2) * K + K * K) * norm;
}
else { // cut
norm = 1 / (V + sqrt(2*V) * K + K * K);
a0 = (1 + sqrt(2) * K + K * K) * norm;
a1 = 2 * (K * K - 1) * norm;
a2 = (1 - sqrt(2) * K + K * K) * norm;
b1 = 2 * (K * K - V) * norm;
b2 = (V - sqrt(2*V) * K + K * K) * norm;
}
break;
}

return;
}

+ 60
- 0
plugins/Cardinal/src/AIDA-X/Biquad.h View File

@@ -0,0 +1,60 @@
//
// Biquad.h
//
// Created by Nigel Redmon on 11/24/12
// EarLevel Engineering: earlevel.com
// Copyright 2012 Nigel Redmon
//
// For a complete explanation of the Biquad code:
// http://www.earlevel.com/main/2012/11/26/biquad-c-source-code/
//
// License:
//
// This source code is provided as is, without warranty.
// You may copy and distribute verbatim copies of this document.
// You may modify and use this source code to create binary code
// for your own purposes, free or commercial.
//

#ifndef Biquad_h
#define Biquad_h

enum {
bq_type_lowpass = 0,
bq_type_highpass,
bq_type_bandpass,
bq_type_notch,
bq_type_peak,
bq_type_lowshelf,
bq_type_highshelf
};

class Biquad {
public:
Biquad();
Biquad(int type, double Fc, double Q, double peakGainDB);
~Biquad();
void setType(int type);
void setQ(double Q);
void setFc(double Fc);
void setPeakGain(double peakGainDB);
void setBiquad(int type, double Fc, double Q, double peakGainDB);
float process(float in);

protected:
void calcBiquad(void);

int type;
double a0, a1, a2, b1, b2;
double Fc, Q, peakGain;
double z1, z2;
};

inline float Biquad::process(float in) {
double out = in * a0 + z1;
z1 = in * a1 + z2 - b1 * out;
z2 = in * a2 - b2 * out;
return out;
}

#endif // Biquad_h

+ 1
- 0
plugins/Cardinal/src/AIDA-X/RTNeural

@@ -0,0 +1 @@
Subproject commit 74e9d354937346f31858e976a2eefc1c25cdcccd

+ 683
- 0
plugins/Cardinal/src/AIDA-X/model_variant.hpp View File

@@ -0,0 +1,683 @@
#include <variant>
#include <RTNeural/RTNeural.h>

#define MAX_INPUT_SIZE 3
struct NullModel { static constexpr int input_size = 0; static constexpr int output_size = 0; };
using ModelType_GRU_8_1 = RTNeural::ModelT<float, 1, 1, RTNeural::GRULayerT<float, 1, 8>, RTNeural::DenseT<float, 8, 1>>;
using ModelType_GRU_8_2 = RTNeural::ModelT<float, 2, 1, RTNeural::GRULayerT<float, 2, 8>, RTNeural::DenseT<float, 8, 1>>;
using ModelType_GRU_8_3 = RTNeural::ModelT<float, 3, 1, RTNeural::GRULayerT<float, 3, 8>, RTNeural::DenseT<float, 8, 1>>;
using ModelType_GRU_12_1 = RTNeural::ModelT<float, 1, 1, RTNeural::GRULayerT<float, 1, 12>, RTNeural::DenseT<float, 12, 1>>;
using ModelType_GRU_12_2 = RTNeural::ModelT<float, 2, 1, RTNeural::GRULayerT<float, 2, 12>, RTNeural::DenseT<float, 12, 1>>;
using ModelType_GRU_12_3 = RTNeural::ModelT<float, 3, 1, RTNeural::GRULayerT<float, 3, 12>, RTNeural::DenseT<float, 12, 1>>;
using ModelType_GRU_16_1 = RTNeural::ModelT<float, 1, 1, RTNeural::GRULayerT<float, 1, 16>, RTNeural::DenseT<float, 16, 1>>;
using ModelType_GRU_16_2 = RTNeural::ModelT<float, 2, 1, RTNeural::GRULayerT<float, 2, 16>, RTNeural::DenseT<float, 16, 1>>;
using ModelType_GRU_16_3 = RTNeural::ModelT<float, 3, 1, RTNeural::GRULayerT<float, 3, 16>, RTNeural::DenseT<float, 16, 1>>;
using ModelType_GRU_20_1 = RTNeural::ModelT<float, 1, 1, RTNeural::GRULayerT<float, 1, 20>, RTNeural::DenseT<float, 20, 1>>;
using ModelType_GRU_20_2 = RTNeural::ModelT<float, 2, 1, RTNeural::GRULayerT<float, 2, 20>, RTNeural::DenseT<float, 20, 1>>;
using ModelType_GRU_20_3 = RTNeural::ModelT<float, 3, 1, RTNeural::GRULayerT<float, 3, 20>, RTNeural::DenseT<float, 20, 1>>;
using ModelType_GRU_32_1 = RTNeural::ModelT<float, 1, 1, RTNeural::GRULayerT<float, 1, 32>, RTNeural::DenseT<float, 32, 1>>;
using ModelType_GRU_32_2 = RTNeural::ModelT<float, 2, 1, RTNeural::GRULayerT<float, 2, 32>, RTNeural::DenseT<float, 32, 1>>;
using ModelType_GRU_32_3 = RTNeural::ModelT<float, 3, 1, RTNeural::GRULayerT<float, 3, 32>, RTNeural::DenseT<float, 32, 1>>;
using ModelType_GRU_40_1 = RTNeural::ModelT<float, 1, 1, RTNeural::GRULayerT<float, 1, 40>, RTNeural::DenseT<float, 40, 1>>;
using ModelType_GRU_40_2 = RTNeural::ModelT<float, 2, 1, RTNeural::GRULayerT<float, 2, 40>, RTNeural::DenseT<float, 40, 1>>;
using ModelType_GRU_40_3 = RTNeural::ModelT<float, 3, 1, RTNeural::GRULayerT<float, 3, 40>, RTNeural::DenseT<float, 40, 1>>;
using ModelType_GRU_64_1 = RTNeural::ModelT<float, 1, 1, RTNeural::GRULayerT<float, 1, 64>, RTNeural::DenseT<float, 64, 1>>;
using ModelType_GRU_64_2 = RTNeural::ModelT<float, 2, 1, RTNeural::GRULayerT<float, 2, 64>, RTNeural::DenseT<float, 64, 1>>;
using ModelType_GRU_64_3 = RTNeural::ModelT<float, 3, 1, RTNeural::GRULayerT<float, 3, 64>, RTNeural::DenseT<float, 64, 1>>;
using ModelType_LSTM_8_1 = RTNeural::ModelT<float, 1, 1, RTNeural::LSTMLayerT<float, 1, 8>, RTNeural::DenseT<float, 8, 1>>;
using ModelType_LSTM_8_2 = RTNeural::ModelT<float, 2, 1, RTNeural::LSTMLayerT<float, 2, 8>, RTNeural::DenseT<float, 8, 1>>;
using ModelType_LSTM_8_3 = RTNeural::ModelT<float, 3, 1, RTNeural::LSTMLayerT<float, 3, 8>, RTNeural::DenseT<float, 8, 1>>;
using ModelType_LSTM_12_1 = RTNeural::ModelT<float, 1, 1, RTNeural::LSTMLayerT<float, 1, 12>, RTNeural::DenseT<float, 12, 1>>;
using ModelType_LSTM_12_2 = RTNeural::ModelT<float, 2, 1, RTNeural::LSTMLayerT<float, 2, 12>, RTNeural::DenseT<float, 12, 1>>;
using ModelType_LSTM_12_3 = RTNeural::ModelT<float, 3, 1, RTNeural::LSTMLayerT<float, 3, 12>, RTNeural::DenseT<float, 12, 1>>;
using ModelType_LSTM_16_1 = RTNeural::ModelT<float, 1, 1, RTNeural::LSTMLayerT<float, 1, 16>, RTNeural::DenseT<float, 16, 1>>;
using ModelType_LSTM_16_2 = RTNeural::ModelT<float, 2, 1, RTNeural::LSTMLayerT<float, 2, 16>, RTNeural::DenseT<float, 16, 1>>;
using ModelType_LSTM_16_3 = RTNeural::ModelT<float, 3, 1, RTNeural::LSTMLayerT<float, 3, 16>, RTNeural::DenseT<float, 16, 1>>;
using ModelType_LSTM_20_1 = RTNeural::ModelT<float, 1, 1, RTNeural::LSTMLayerT<float, 1, 20>, RTNeural::DenseT<float, 20, 1>>;
using ModelType_LSTM_20_2 = RTNeural::ModelT<float, 2, 1, RTNeural::LSTMLayerT<float, 2, 20>, RTNeural::DenseT<float, 20, 1>>;
using ModelType_LSTM_20_3 = RTNeural::ModelT<float, 3, 1, RTNeural::LSTMLayerT<float, 3, 20>, RTNeural::DenseT<float, 20, 1>>;
using ModelType_LSTM_32_1 = RTNeural::ModelT<float, 1, 1, RTNeural::LSTMLayerT<float, 1, 32>, RTNeural::DenseT<float, 32, 1>>;
using ModelType_LSTM_32_2 = RTNeural::ModelT<float, 2, 1, RTNeural::LSTMLayerT<float, 2, 32>, RTNeural::DenseT<float, 32, 1>>;
using ModelType_LSTM_32_3 = RTNeural::ModelT<float, 3, 1, RTNeural::LSTMLayerT<float, 3, 32>, RTNeural::DenseT<float, 32, 1>>;
using ModelType_LSTM_40_1 = RTNeural::ModelT<float, 1, 1, RTNeural::LSTMLayerT<float, 1, 40>, RTNeural::DenseT<float, 40, 1>>;
using ModelType_LSTM_40_2 = RTNeural::ModelT<float, 2, 1, RTNeural::LSTMLayerT<float, 2, 40>, RTNeural::DenseT<float, 40, 1>>;
using ModelType_LSTM_40_3 = RTNeural::ModelT<float, 3, 1, RTNeural::LSTMLayerT<float, 3, 40>, RTNeural::DenseT<float, 40, 1>>;
using ModelType_LSTM_64_1 = RTNeural::ModelT<float, 1, 1, RTNeural::LSTMLayerT<float, 1, 64>, RTNeural::DenseT<float, 64, 1>>;
using ModelType_LSTM_64_2 = RTNeural::ModelT<float, 2, 1, RTNeural::LSTMLayerT<float, 2, 64>, RTNeural::DenseT<float, 64, 1>>;
using ModelType_LSTM_64_3 = RTNeural::ModelT<float, 3, 1, RTNeural::LSTMLayerT<float, 3, 64>, RTNeural::DenseT<float, 64, 1>>;
using ModelVariantType = std::variant<NullModel,ModelType_GRU_8_1,ModelType_GRU_8_2,ModelType_GRU_8_3,ModelType_GRU_12_1,ModelType_GRU_12_2,ModelType_GRU_12_3,ModelType_GRU_16_1,ModelType_GRU_16_2,ModelType_GRU_16_3,ModelType_GRU_20_1,ModelType_GRU_20_2,ModelType_GRU_20_3,ModelType_GRU_32_1,ModelType_GRU_32_2,ModelType_GRU_32_3,ModelType_GRU_40_1,ModelType_GRU_40_2,ModelType_GRU_40_3,ModelType_GRU_64_1,ModelType_GRU_64_2,ModelType_GRU_64_3,ModelType_LSTM_8_1,ModelType_LSTM_8_2,ModelType_LSTM_8_3,ModelType_LSTM_12_1,ModelType_LSTM_12_2,ModelType_LSTM_12_3,ModelType_LSTM_16_1,ModelType_LSTM_16_2,ModelType_LSTM_16_3,ModelType_LSTM_20_1,ModelType_LSTM_20_2,ModelType_LSTM_20_3,ModelType_LSTM_32_1,ModelType_LSTM_32_2,ModelType_LSTM_32_3,ModelType_LSTM_40_1,ModelType_LSTM_40_2,ModelType_LSTM_40_3,ModelType_LSTM_64_1,ModelType_LSTM_64_2,ModelType_LSTM_64_3>;

inline bool is_model_type_ModelType_GRU_8_1 (const nlohmann::json& model_json) {
const auto json_layers = model_json.at ("layers");
const auto rnn_layer_type = json_layers.at (0).at ("type").get<std::string>();
const auto is_layer_type_correct = rnn_layer_type == "gru";
const auto hidden_size = json_layers.at (0).at ("shape").back().get<int>();
const auto is_hidden_size_correct = hidden_size == 8;
const auto input_size = model_json.at ("in_shape").back().get<int>();
const auto is_input_size_correct = input_size == 1;
return is_layer_type_correct && is_hidden_size_correct && is_input_size_correct;
}

inline bool is_model_type_ModelType_GRU_8_2 (const nlohmann::json& model_json) {
const auto json_layers = model_json.at ("layers");
const auto rnn_layer_type = json_layers.at (0).at ("type").get<std::string>();
const auto is_layer_type_correct = rnn_layer_type == "gru";
const auto hidden_size = json_layers.at (0).at ("shape").back().get<int>();
const auto is_hidden_size_correct = hidden_size == 8;
const auto input_size = model_json.at ("in_shape").back().get<int>();
const auto is_input_size_correct = input_size == 2;
return is_layer_type_correct && is_hidden_size_correct && is_input_size_correct;
}

inline bool is_model_type_ModelType_GRU_8_3 (const nlohmann::json& model_json) {
const auto json_layers = model_json.at ("layers");
const auto rnn_layer_type = json_layers.at (0).at ("type").get<std::string>();
const auto is_layer_type_correct = rnn_layer_type == "gru";
const auto hidden_size = json_layers.at (0).at ("shape").back().get<int>();
const auto is_hidden_size_correct = hidden_size == 8;
const auto input_size = model_json.at ("in_shape").back().get<int>();
const auto is_input_size_correct = input_size == 3;
return is_layer_type_correct && is_hidden_size_correct && is_input_size_correct;
}

inline bool is_model_type_ModelType_GRU_12_1 (const nlohmann::json& model_json) {
const auto json_layers = model_json.at ("layers");
const auto rnn_layer_type = json_layers.at (0).at ("type").get<std::string>();
const auto is_layer_type_correct = rnn_layer_type == "gru";
const auto hidden_size = json_layers.at (0).at ("shape").back().get<int>();
const auto is_hidden_size_correct = hidden_size == 12;
const auto input_size = model_json.at ("in_shape").back().get<int>();
const auto is_input_size_correct = input_size == 1;
return is_layer_type_correct && is_hidden_size_correct && is_input_size_correct;
}

inline bool is_model_type_ModelType_GRU_12_2 (const nlohmann::json& model_json) {
const auto json_layers = model_json.at ("layers");
const auto rnn_layer_type = json_layers.at (0).at ("type").get<std::string>();
const auto is_layer_type_correct = rnn_layer_type == "gru";
const auto hidden_size = json_layers.at (0).at ("shape").back().get<int>();
const auto is_hidden_size_correct = hidden_size == 12;
const auto input_size = model_json.at ("in_shape").back().get<int>();
const auto is_input_size_correct = input_size == 2;
return is_layer_type_correct && is_hidden_size_correct && is_input_size_correct;
}

inline bool is_model_type_ModelType_GRU_12_3 (const nlohmann::json& model_json) {
const auto json_layers = model_json.at ("layers");
const auto rnn_layer_type = json_layers.at (0).at ("type").get<std::string>();
const auto is_layer_type_correct = rnn_layer_type == "gru";
const auto hidden_size = json_layers.at (0).at ("shape").back().get<int>();
const auto is_hidden_size_correct = hidden_size == 12;
const auto input_size = model_json.at ("in_shape").back().get<int>();
const auto is_input_size_correct = input_size == 3;
return is_layer_type_correct && is_hidden_size_correct && is_input_size_correct;
}

inline bool is_model_type_ModelType_GRU_16_1 (const nlohmann::json& model_json) {
const auto json_layers = model_json.at ("layers");
const auto rnn_layer_type = json_layers.at (0).at ("type").get<std::string>();
const auto is_layer_type_correct = rnn_layer_type == "gru";
const auto hidden_size = json_layers.at (0).at ("shape").back().get<int>();
const auto is_hidden_size_correct = hidden_size == 16;
const auto input_size = model_json.at ("in_shape").back().get<int>();
const auto is_input_size_correct = input_size == 1;
return is_layer_type_correct && is_hidden_size_correct && is_input_size_correct;
}

inline bool is_model_type_ModelType_GRU_16_2 (const nlohmann::json& model_json) {
const auto json_layers = model_json.at ("layers");
const auto rnn_layer_type = json_layers.at (0).at ("type").get<std::string>();
const auto is_layer_type_correct = rnn_layer_type == "gru";
const auto hidden_size = json_layers.at (0).at ("shape").back().get<int>();
const auto is_hidden_size_correct = hidden_size == 16;
const auto input_size = model_json.at ("in_shape").back().get<int>();
const auto is_input_size_correct = input_size == 2;
return is_layer_type_correct && is_hidden_size_correct && is_input_size_correct;
}

inline bool is_model_type_ModelType_GRU_16_3 (const nlohmann::json& model_json) {
const auto json_layers = model_json.at ("layers");
const auto rnn_layer_type = json_layers.at (0).at ("type").get<std::string>();
const auto is_layer_type_correct = rnn_layer_type == "gru";
const auto hidden_size = json_layers.at (0).at ("shape").back().get<int>();
const auto is_hidden_size_correct = hidden_size == 16;
const auto input_size = model_json.at ("in_shape").back().get<int>();
const auto is_input_size_correct = input_size == 3;
return is_layer_type_correct && is_hidden_size_correct && is_input_size_correct;
}

inline bool is_model_type_ModelType_GRU_20_1 (const nlohmann::json& model_json) {
const auto json_layers = model_json.at ("layers");
const auto rnn_layer_type = json_layers.at (0).at ("type").get<std::string>();
const auto is_layer_type_correct = rnn_layer_type == "gru";
const auto hidden_size = json_layers.at (0).at ("shape").back().get<int>();
const auto is_hidden_size_correct = hidden_size == 20;
const auto input_size = model_json.at ("in_shape").back().get<int>();
const auto is_input_size_correct = input_size == 1;
return is_layer_type_correct && is_hidden_size_correct && is_input_size_correct;
}

inline bool is_model_type_ModelType_GRU_20_2 (const nlohmann::json& model_json) {
const auto json_layers = model_json.at ("layers");
const auto rnn_layer_type = json_layers.at (0).at ("type").get<std::string>();
const auto is_layer_type_correct = rnn_layer_type == "gru";
const auto hidden_size = json_layers.at (0).at ("shape").back().get<int>();
const auto is_hidden_size_correct = hidden_size == 20;
const auto input_size = model_json.at ("in_shape").back().get<int>();
const auto is_input_size_correct = input_size == 2;
return is_layer_type_correct && is_hidden_size_correct && is_input_size_correct;
}

inline bool is_model_type_ModelType_GRU_20_3 (const nlohmann::json& model_json) {
const auto json_layers = model_json.at ("layers");
const auto rnn_layer_type = json_layers.at (0).at ("type").get<std::string>();
const auto is_layer_type_correct = rnn_layer_type == "gru";
const auto hidden_size = json_layers.at (0).at ("shape").back().get<int>();
const auto is_hidden_size_correct = hidden_size == 20;
const auto input_size = model_json.at ("in_shape").back().get<int>();
const auto is_input_size_correct = input_size == 3;
return is_layer_type_correct && is_hidden_size_correct && is_input_size_correct;
}

inline bool is_model_type_ModelType_GRU_32_1 (const nlohmann::json& model_json) {
const auto json_layers = model_json.at ("layers");
const auto rnn_layer_type = json_layers.at (0).at ("type").get<std::string>();
const auto is_layer_type_correct = rnn_layer_type == "gru";
const auto hidden_size = json_layers.at (0).at ("shape").back().get<int>();
const auto is_hidden_size_correct = hidden_size == 32;
const auto input_size = model_json.at ("in_shape").back().get<int>();
const auto is_input_size_correct = input_size == 1;
return is_layer_type_correct && is_hidden_size_correct && is_input_size_correct;
}

inline bool is_model_type_ModelType_GRU_32_2 (const nlohmann::json& model_json) {
const auto json_layers = model_json.at ("layers");
const auto rnn_layer_type = json_layers.at (0).at ("type").get<std::string>();
const auto is_layer_type_correct = rnn_layer_type == "gru";
const auto hidden_size = json_layers.at (0).at ("shape").back().get<int>();
const auto is_hidden_size_correct = hidden_size == 32;
const auto input_size = model_json.at ("in_shape").back().get<int>();
const auto is_input_size_correct = input_size == 2;
return is_layer_type_correct && is_hidden_size_correct && is_input_size_correct;
}

inline bool is_model_type_ModelType_GRU_32_3 (const nlohmann::json& model_json) {
const auto json_layers = model_json.at ("layers");
const auto rnn_layer_type = json_layers.at (0).at ("type").get<std::string>();
const auto is_layer_type_correct = rnn_layer_type == "gru";
const auto hidden_size = json_layers.at (0).at ("shape").back().get<int>();
const auto is_hidden_size_correct = hidden_size == 32;
const auto input_size = model_json.at ("in_shape").back().get<int>();
const auto is_input_size_correct = input_size == 3;
return is_layer_type_correct && is_hidden_size_correct && is_input_size_correct;
}

inline bool is_model_type_ModelType_GRU_40_1 (const nlohmann::json& model_json) {
const auto json_layers = model_json.at ("layers");
const auto rnn_layer_type = json_layers.at (0).at ("type").get<std::string>();
const auto is_layer_type_correct = rnn_layer_type == "gru";
const auto hidden_size = json_layers.at (0).at ("shape").back().get<int>();
const auto is_hidden_size_correct = hidden_size == 40;
const auto input_size = model_json.at ("in_shape").back().get<int>();
const auto is_input_size_correct = input_size == 1;
return is_layer_type_correct && is_hidden_size_correct && is_input_size_correct;
}

inline bool is_model_type_ModelType_GRU_40_2 (const nlohmann::json& model_json) {
const auto json_layers = model_json.at ("layers");
const auto rnn_layer_type = json_layers.at (0).at ("type").get<std::string>();
const auto is_layer_type_correct = rnn_layer_type == "gru";
const auto hidden_size = json_layers.at (0).at ("shape").back().get<int>();
const auto is_hidden_size_correct = hidden_size == 40;
const auto input_size = model_json.at ("in_shape").back().get<int>();
const auto is_input_size_correct = input_size == 2;
return is_layer_type_correct && is_hidden_size_correct && is_input_size_correct;
}

inline bool is_model_type_ModelType_GRU_40_3 (const nlohmann::json& model_json) {
const auto json_layers = model_json.at ("layers");
const auto rnn_layer_type = json_layers.at (0).at ("type").get<std::string>();
const auto is_layer_type_correct = rnn_layer_type == "gru";
const auto hidden_size = json_layers.at (0).at ("shape").back().get<int>();
const auto is_hidden_size_correct = hidden_size == 40;
const auto input_size = model_json.at ("in_shape").back().get<int>();
const auto is_input_size_correct = input_size == 3;
return is_layer_type_correct && is_hidden_size_correct && is_input_size_correct;
}

inline bool is_model_type_ModelType_GRU_64_1 (const nlohmann::json& model_json) {
const auto json_layers = model_json.at ("layers");
const auto rnn_layer_type = json_layers.at (0).at ("type").get<std::string>();
const auto is_layer_type_correct = rnn_layer_type == "gru";
const auto hidden_size = json_layers.at (0).at ("shape").back().get<int>();
const auto is_hidden_size_correct = hidden_size == 64;
const auto input_size = model_json.at ("in_shape").back().get<int>();
const auto is_input_size_correct = input_size == 1;
return is_layer_type_correct && is_hidden_size_correct && is_input_size_correct;
}

inline bool is_model_type_ModelType_GRU_64_2 (const nlohmann::json& model_json) {
const auto json_layers = model_json.at ("layers");
const auto rnn_layer_type = json_layers.at (0).at ("type").get<std::string>();
const auto is_layer_type_correct = rnn_layer_type == "gru";
const auto hidden_size = json_layers.at (0).at ("shape").back().get<int>();
const auto is_hidden_size_correct = hidden_size == 64;
const auto input_size = model_json.at ("in_shape").back().get<int>();
const auto is_input_size_correct = input_size == 2;
return is_layer_type_correct && is_hidden_size_correct && is_input_size_correct;
}

inline bool is_model_type_ModelType_GRU_64_3 (const nlohmann::json& model_json) {
const auto json_layers = model_json.at ("layers");
const auto rnn_layer_type = json_layers.at (0).at ("type").get<std::string>();
const auto is_layer_type_correct = rnn_layer_type == "gru";
const auto hidden_size = json_layers.at (0).at ("shape").back().get<int>();
const auto is_hidden_size_correct = hidden_size == 64;
const auto input_size = model_json.at ("in_shape").back().get<int>();
const auto is_input_size_correct = input_size == 3;
return is_layer_type_correct && is_hidden_size_correct && is_input_size_correct;
}

inline bool is_model_type_ModelType_LSTM_8_1 (const nlohmann::json& model_json) {
const auto json_layers = model_json.at ("layers");
const auto rnn_layer_type = json_layers.at (0).at ("type").get<std::string>();
const auto is_layer_type_correct = rnn_layer_type == "lstm";
const auto hidden_size = json_layers.at (0).at ("shape").back().get<int>();
const auto is_hidden_size_correct = hidden_size == 8;
const auto input_size = model_json.at ("in_shape").back().get<int>();
const auto is_input_size_correct = input_size == 1;
return is_layer_type_correct && is_hidden_size_correct && is_input_size_correct;
}

inline bool is_model_type_ModelType_LSTM_8_2 (const nlohmann::json& model_json) {
const auto json_layers = model_json.at ("layers");
const auto rnn_layer_type = json_layers.at (0).at ("type").get<std::string>();
const auto is_layer_type_correct = rnn_layer_type == "lstm";
const auto hidden_size = json_layers.at (0).at ("shape").back().get<int>();
const auto is_hidden_size_correct = hidden_size == 8;
const auto input_size = model_json.at ("in_shape").back().get<int>();
const auto is_input_size_correct = input_size == 2;
return is_layer_type_correct && is_hidden_size_correct && is_input_size_correct;
}

inline bool is_model_type_ModelType_LSTM_8_3 (const nlohmann::json& model_json) {
const auto json_layers = model_json.at ("layers");
const auto rnn_layer_type = json_layers.at (0).at ("type").get<std::string>();
const auto is_layer_type_correct = rnn_layer_type == "lstm";
const auto hidden_size = json_layers.at (0).at ("shape").back().get<int>();
const auto is_hidden_size_correct = hidden_size == 8;
const auto input_size = model_json.at ("in_shape").back().get<int>();
const auto is_input_size_correct = input_size == 3;
return is_layer_type_correct && is_hidden_size_correct && is_input_size_correct;
}

inline bool is_model_type_ModelType_LSTM_12_1 (const nlohmann::json& model_json) {
const auto json_layers = model_json.at ("layers");
const auto rnn_layer_type = json_layers.at (0).at ("type").get<std::string>();
const auto is_layer_type_correct = rnn_layer_type == "lstm";
const auto hidden_size = json_layers.at (0).at ("shape").back().get<int>();
const auto is_hidden_size_correct = hidden_size == 12;
const auto input_size = model_json.at ("in_shape").back().get<int>();
const auto is_input_size_correct = input_size == 1;
return is_layer_type_correct && is_hidden_size_correct && is_input_size_correct;
}

inline bool is_model_type_ModelType_LSTM_12_2 (const nlohmann::json& model_json) {
const auto json_layers = model_json.at ("layers");
const auto rnn_layer_type = json_layers.at (0).at ("type").get<std::string>();
const auto is_layer_type_correct = rnn_layer_type == "lstm";
const auto hidden_size = json_layers.at (0).at ("shape").back().get<int>();
const auto is_hidden_size_correct = hidden_size == 12;
const auto input_size = model_json.at ("in_shape").back().get<int>();
const auto is_input_size_correct = input_size == 2;
return is_layer_type_correct && is_hidden_size_correct && is_input_size_correct;
}

inline bool is_model_type_ModelType_LSTM_12_3 (const nlohmann::json& model_json) {
const auto json_layers = model_json.at ("layers");
const auto rnn_layer_type = json_layers.at (0).at ("type").get<std::string>();
const auto is_layer_type_correct = rnn_layer_type == "lstm";
const auto hidden_size = json_layers.at (0).at ("shape").back().get<int>();
const auto is_hidden_size_correct = hidden_size == 12;
const auto input_size = model_json.at ("in_shape").back().get<int>();
const auto is_input_size_correct = input_size == 3;
return is_layer_type_correct && is_hidden_size_correct && is_input_size_correct;
}

inline bool is_model_type_ModelType_LSTM_16_1 (const nlohmann::json& model_json) {
const auto json_layers = model_json.at ("layers");
const auto rnn_layer_type = json_layers.at (0).at ("type").get<std::string>();
const auto is_layer_type_correct = rnn_layer_type == "lstm";
const auto hidden_size = json_layers.at (0).at ("shape").back().get<int>();
const auto is_hidden_size_correct = hidden_size == 16;
const auto input_size = model_json.at ("in_shape").back().get<int>();
const auto is_input_size_correct = input_size == 1;
return is_layer_type_correct && is_hidden_size_correct && is_input_size_correct;
}

inline bool is_model_type_ModelType_LSTM_16_2 (const nlohmann::json& model_json) {
const auto json_layers = model_json.at ("layers");
const auto rnn_layer_type = json_layers.at (0).at ("type").get<std::string>();
const auto is_layer_type_correct = rnn_layer_type == "lstm";
const auto hidden_size = json_layers.at (0).at ("shape").back().get<int>();
const auto is_hidden_size_correct = hidden_size == 16;
const auto input_size = model_json.at ("in_shape").back().get<int>();
const auto is_input_size_correct = input_size == 2;
return is_layer_type_correct && is_hidden_size_correct && is_input_size_correct;
}

inline bool is_model_type_ModelType_LSTM_16_3 (const nlohmann::json& model_json) {
const auto json_layers = model_json.at ("layers");
const auto rnn_layer_type = json_layers.at (0).at ("type").get<std::string>();
const auto is_layer_type_correct = rnn_layer_type == "lstm";
const auto hidden_size = json_layers.at (0).at ("shape").back().get<int>();
const auto is_hidden_size_correct = hidden_size == 16;
const auto input_size = model_json.at ("in_shape").back().get<int>();
const auto is_input_size_correct = input_size == 3;
return is_layer_type_correct && is_hidden_size_correct && is_input_size_correct;
}

inline bool is_model_type_ModelType_LSTM_20_1 (const nlohmann::json& model_json) {
const auto json_layers = model_json.at ("layers");
const auto rnn_layer_type = json_layers.at (0).at ("type").get<std::string>();
const auto is_layer_type_correct = rnn_layer_type == "lstm";
const auto hidden_size = json_layers.at (0).at ("shape").back().get<int>();
const auto is_hidden_size_correct = hidden_size == 20;
const auto input_size = model_json.at ("in_shape").back().get<int>();
const auto is_input_size_correct = input_size == 1;
return is_layer_type_correct && is_hidden_size_correct && is_input_size_correct;
}

inline bool is_model_type_ModelType_LSTM_20_2 (const nlohmann::json& model_json) {
const auto json_layers = model_json.at ("layers");
const auto rnn_layer_type = json_layers.at (0).at ("type").get<std::string>();
const auto is_layer_type_correct = rnn_layer_type == "lstm";
const auto hidden_size = json_layers.at (0).at ("shape").back().get<int>();
const auto is_hidden_size_correct = hidden_size == 20;
const auto input_size = model_json.at ("in_shape").back().get<int>();
const auto is_input_size_correct = input_size == 2;
return is_layer_type_correct && is_hidden_size_correct && is_input_size_correct;
}

inline bool is_model_type_ModelType_LSTM_20_3 (const nlohmann::json& model_json) {
const auto json_layers = model_json.at ("layers");
const auto rnn_layer_type = json_layers.at (0).at ("type").get<std::string>();
const auto is_layer_type_correct = rnn_layer_type == "lstm";
const auto hidden_size = json_layers.at (0).at ("shape").back().get<int>();
const auto is_hidden_size_correct = hidden_size == 20;
const auto input_size = model_json.at ("in_shape").back().get<int>();
const auto is_input_size_correct = input_size == 3;
return is_layer_type_correct && is_hidden_size_correct && is_input_size_correct;
}

inline bool is_model_type_ModelType_LSTM_32_1 (const nlohmann::json& model_json) {
const auto json_layers = model_json.at ("layers");
const auto rnn_layer_type = json_layers.at (0).at ("type").get<std::string>();
const auto is_layer_type_correct = rnn_layer_type == "lstm";
const auto hidden_size = json_layers.at (0).at ("shape").back().get<int>();
const auto is_hidden_size_correct = hidden_size == 32;
const auto input_size = model_json.at ("in_shape").back().get<int>();
const auto is_input_size_correct = input_size == 1;
return is_layer_type_correct && is_hidden_size_correct && is_input_size_correct;
}

inline bool is_model_type_ModelType_LSTM_32_2 (const nlohmann::json& model_json) {
const auto json_layers = model_json.at ("layers");
const auto rnn_layer_type = json_layers.at (0).at ("type").get<std::string>();
const auto is_layer_type_correct = rnn_layer_type == "lstm";
const auto hidden_size = json_layers.at (0).at ("shape").back().get<int>();
const auto is_hidden_size_correct = hidden_size == 32;
const auto input_size = model_json.at ("in_shape").back().get<int>();
const auto is_input_size_correct = input_size == 2;
return is_layer_type_correct && is_hidden_size_correct && is_input_size_correct;
}

inline bool is_model_type_ModelType_LSTM_32_3 (const nlohmann::json& model_json) {
const auto json_layers = model_json.at ("layers");
const auto rnn_layer_type = json_layers.at (0).at ("type").get<std::string>();
const auto is_layer_type_correct = rnn_layer_type == "lstm";
const auto hidden_size = json_layers.at (0).at ("shape").back().get<int>();
const auto is_hidden_size_correct = hidden_size == 32;
const auto input_size = model_json.at ("in_shape").back().get<int>();
const auto is_input_size_correct = input_size == 3;
return is_layer_type_correct && is_hidden_size_correct && is_input_size_correct;
}

inline bool is_model_type_ModelType_LSTM_40_1 (const nlohmann::json& model_json) {
const auto json_layers = model_json.at ("layers");
const auto rnn_layer_type = json_layers.at (0).at ("type").get<std::string>();
const auto is_layer_type_correct = rnn_layer_type == "lstm";
const auto hidden_size = json_layers.at (0).at ("shape").back().get<int>();
const auto is_hidden_size_correct = hidden_size == 40;
const auto input_size = model_json.at ("in_shape").back().get<int>();
const auto is_input_size_correct = input_size == 1;
return is_layer_type_correct && is_hidden_size_correct && is_input_size_correct;
}

inline bool is_model_type_ModelType_LSTM_40_2 (const nlohmann::json& model_json) {
const auto json_layers = model_json.at ("layers");
const auto rnn_layer_type = json_layers.at (0).at ("type").get<std::string>();
const auto is_layer_type_correct = rnn_layer_type == "lstm";
const auto hidden_size = json_layers.at (0).at ("shape").back().get<int>();
const auto is_hidden_size_correct = hidden_size == 40;
const auto input_size = model_json.at ("in_shape").back().get<int>();
const auto is_input_size_correct = input_size == 2;
return is_layer_type_correct && is_hidden_size_correct && is_input_size_correct;
}

inline bool is_model_type_ModelType_LSTM_40_3 (const nlohmann::json& model_json) {
const auto json_layers = model_json.at ("layers");
const auto rnn_layer_type = json_layers.at (0).at ("type").get<std::string>();
const auto is_layer_type_correct = rnn_layer_type == "lstm";
const auto hidden_size = json_layers.at (0).at ("shape").back().get<int>();
const auto is_hidden_size_correct = hidden_size == 40;
const auto input_size = model_json.at ("in_shape").back().get<int>();
const auto is_input_size_correct = input_size == 3;
return is_layer_type_correct && is_hidden_size_correct && is_input_size_correct;
}

inline bool is_model_type_ModelType_LSTM_64_1 (const nlohmann::json& model_json) {
const auto json_layers = model_json.at ("layers");
const auto rnn_layer_type = json_layers.at (0).at ("type").get<std::string>();
const auto is_layer_type_correct = rnn_layer_type == "lstm";
const auto hidden_size = json_layers.at (0).at ("shape").back().get<int>();
const auto is_hidden_size_correct = hidden_size == 64;
const auto input_size = model_json.at ("in_shape").back().get<int>();
const auto is_input_size_correct = input_size == 1;
return is_layer_type_correct && is_hidden_size_correct && is_input_size_correct;
}

inline bool is_model_type_ModelType_LSTM_64_2 (const nlohmann::json& model_json) {
const auto json_layers = model_json.at ("layers");
const auto rnn_layer_type = json_layers.at (0).at ("type").get<std::string>();
const auto is_layer_type_correct = rnn_layer_type == "lstm";
const auto hidden_size = json_layers.at (0).at ("shape").back().get<int>();
const auto is_hidden_size_correct = hidden_size == 64;
const auto input_size = model_json.at ("in_shape").back().get<int>();
const auto is_input_size_correct = input_size == 2;
return is_layer_type_correct && is_hidden_size_correct && is_input_size_correct;
}

inline bool is_model_type_ModelType_LSTM_64_3 (const nlohmann::json& model_json) {
const auto json_layers = model_json.at ("layers");
const auto rnn_layer_type = json_layers.at (0).at ("type").get<std::string>();
const auto is_layer_type_correct = rnn_layer_type == "lstm";
const auto hidden_size = json_layers.at (0).at ("shape").back().get<int>();
const auto is_hidden_size_correct = hidden_size == 64;
const auto input_size = model_json.at ("in_shape").back().get<int>();
const auto is_input_size_correct = input_size == 3;
return is_layer_type_correct && is_hidden_size_correct && is_input_size_correct;
}

inline bool custom_model_creator (const nlohmann::json& model_json, ModelVariantType& model) {
if (is_model_type_ModelType_GRU_8_1 (model_json)) {
model.emplace<ModelType_GRU_8_1>();
return true;
}
else if (is_model_type_ModelType_GRU_8_2 (model_json)) {
model.emplace<ModelType_GRU_8_2>();
return true;
}
else if (is_model_type_ModelType_GRU_8_3 (model_json)) {
model.emplace<ModelType_GRU_8_3>();
return true;
}
else if (is_model_type_ModelType_GRU_12_1 (model_json)) {
model.emplace<ModelType_GRU_12_1>();
return true;
}
else if (is_model_type_ModelType_GRU_12_2 (model_json)) {
model.emplace<ModelType_GRU_12_2>();
return true;
}
else if (is_model_type_ModelType_GRU_12_3 (model_json)) {
model.emplace<ModelType_GRU_12_3>();
return true;
}
else if (is_model_type_ModelType_GRU_16_1 (model_json)) {
model.emplace<ModelType_GRU_16_1>();
return true;
}
else if (is_model_type_ModelType_GRU_16_2 (model_json)) {
model.emplace<ModelType_GRU_16_2>();
return true;
}
else if (is_model_type_ModelType_GRU_16_3 (model_json)) {
model.emplace<ModelType_GRU_16_3>();
return true;
}
else if (is_model_type_ModelType_GRU_20_1 (model_json)) {
model.emplace<ModelType_GRU_20_1>();
return true;
}
else if (is_model_type_ModelType_GRU_20_2 (model_json)) {
model.emplace<ModelType_GRU_20_2>();
return true;
}
else if (is_model_type_ModelType_GRU_20_3 (model_json)) {
model.emplace<ModelType_GRU_20_3>();
return true;
}
else if (is_model_type_ModelType_GRU_32_1 (model_json)) {
model.emplace<ModelType_GRU_32_1>();
return true;
}
else if (is_model_type_ModelType_GRU_32_2 (model_json)) {
model.emplace<ModelType_GRU_32_2>();
return true;
}
else if (is_model_type_ModelType_GRU_32_3 (model_json)) {
model.emplace<ModelType_GRU_32_3>();
return true;
}
else if (is_model_type_ModelType_GRU_40_1 (model_json)) {
model.emplace<ModelType_GRU_40_1>();
return true;
}
else if (is_model_type_ModelType_GRU_40_2 (model_json)) {
model.emplace<ModelType_GRU_40_2>();
return true;
}
else if (is_model_type_ModelType_GRU_40_3 (model_json)) {
model.emplace<ModelType_GRU_40_3>();
return true;
}
else if (is_model_type_ModelType_GRU_64_1 (model_json)) {
model.emplace<ModelType_GRU_64_1>();
return true;
}
else if (is_model_type_ModelType_GRU_64_2 (model_json)) {
model.emplace<ModelType_GRU_64_2>();
return true;
}
else if (is_model_type_ModelType_GRU_64_3 (model_json)) {
model.emplace<ModelType_GRU_64_3>();
return true;
}
else if (is_model_type_ModelType_LSTM_8_1 (model_json)) {
model.emplace<ModelType_LSTM_8_1>();
return true;
}
else if (is_model_type_ModelType_LSTM_8_2 (model_json)) {
model.emplace<ModelType_LSTM_8_2>();
return true;
}
else if (is_model_type_ModelType_LSTM_8_3 (model_json)) {
model.emplace<ModelType_LSTM_8_3>();
return true;
}
else if (is_model_type_ModelType_LSTM_12_1 (model_json)) {
model.emplace<ModelType_LSTM_12_1>();
return true;
}
else if (is_model_type_ModelType_LSTM_12_2 (model_json)) {
model.emplace<ModelType_LSTM_12_2>();
return true;
}
else if (is_model_type_ModelType_LSTM_12_3 (model_json)) {
model.emplace<ModelType_LSTM_12_3>();
return true;
}
else if (is_model_type_ModelType_LSTM_16_1 (model_json)) {
model.emplace<ModelType_LSTM_16_1>();
return true;
}
else if (is_model_type_ModelType_LSTM_16_2 (model_json)) {
model.emplace<ModelType_LSTM_16_2>();
return true;
}
else if (is_model_type_ModelType_LSTM_16_3 (model_json)) {
model.emplace<ModelType_LSTM_16_3>();
return true;
}
else if (is_model_type_ModelType_LSTM_20_1 (model_json)) {
model.emplace<ModelType_LSTM_20_1>();
return true;
}
else if (is_model_type_ModelType_LSTM_20_2 (model_json)) {
model.emplace<ModelType_LSTM_20_2>();
return true;
}
else if (is_model_type_ModelType_LSTM_20_3 (model_json)) {
model.emplace<ModelType_LSTM_20_3>();
return true;
}
else if (is_model_type_ModelType_LSTM_32_1 (model_json)) {
model.emplace<ModelType_LSTM_32_1>();
return true;
}
else if (is_model_type_ModelType_LSTM_32_2 (model_json)) {
model.emplace<ModelType_LSTM_32_2>();
return true;
}
else if (is_model_type_ModelType_LSTM_32_3 (model_json)) {
model.emplace<ModelType_LSTM_32_3>();
return true;
}
else if (is_model_type_ModelType_LSTM_40_1 (model_json)) {
model.emplace<ModelType_LSTM_40_1>();
return true;
}
else if (is_model_type_ModelType_LSTM_40_2 (model_json)) {
model.emplace<ModelType_LSTM_40_2>();
return true;
}
else if (is_model_type_ModelType_LSTM_40_3 (model_json)) {
model.emplace<ModelType_LSTM_40_3>();
return true;
}
else if (is_model_type_ModelType_LSTM_64_1 (model_json)) {
model.emplace<ModelType_LSTM_64_1>();
return true;
}
else if (is_model_type_ModelType_LSTM_64_2 (model_json)) {
model.emplace<ModelType_LSTM_64_2>();
return true;
}
else if (is_model_type_ModelType_LSTM_64_3 (model_json)) {
model.emplace<ModelType_LSTM_64_3>();
return true;
}
model.emplace<NullModel>();
return false;
}

+ 16
- 14
plugins/Cardinal/src/AudioFile.cpp View File

@@ -79,6 +79,7 @@ struct CarlaInternalPluginModule : Module, Runner {
kParameterHostSync,
kParameterVolume,
kParameterEnabled,
kParameterQuadChannels,
kParameterInfoChannels,
kParameterInfoBitRate,
kParameterInfoBitDepth,
@@ -96,8 +97,8 @@ struct CarlaInternalPluginModule : Module, Runner {
NativeHostDescriptor fCarlaHostDescriptor = {};
NativeTimeInfo fCarlaTimeInfo;

float dataOut[NUM_OUTPUTS][BUFFER_SIZE];
float* dataOutPtr[NUM_OUTPUTS];
float dataOut[NUM_OUTPUTS+1][BUFFER_SIZE];
float* dataOutPtr[NUM_OUTPUTS+1];
unsigned audioDataFill = 0;
uint32_t lastProcessCounter = 0;
bool fileChanged = false;
@@ -105,11 +106,11 @@ struct CarlaInternalPluginModule : Module, Runner {

struct {
float preview[108];
uint channels; // 4
uint bitDepth; // 6
uint sampleRate; // 7
uint length; // 8
float position; // 9
uint channels;
uint bitDepth;
uint sampleRate;
uint length;
float position;
} audioInfo;

CarlaInternalPluginModule()
@@ -122,6 +123,7 @@ struct CarlaInternalPluginModule : Module, Runner {

dataOutPtr[0] = dataOut[0];
dataOutPtr[1] = dataOut[1];
dataOutPtr[2] = dataOut[2];

std::memset(dataOut, 0, sizeof(dataOut));
std::memset(&audioInfo, 0, sizeof(audioInfo));
@@ -315,11 +317,11 @@ struct CarlaInternalPluginModule : Module, Runner {
audioDataFill = 0;
fCarlaPluginDescriptor->process(fCarlaPluginHandle, nullptr, dataOutPtr, BUFFER_SIZE, nullptr, 0);

audioInfo.channels = fCarlaPluginDescriptor->get_parameter_value(fCarlaPluginHandle, 4);
audioInfo.bitDepth = fCarlaPluginDescriptor->get_parameter_value(fCarlaPluginHandle, 6);
audioInfo.sampleRate = fCarlaPluginDescriptor->get_parameter_value(fCarlaPluginHandle, 7);
audioInfo.length = fCarlaPluginDescriptor->get_parameter_value(fCarlaPluginHandle, 8);
audioInfo.position = fCarlaPluginDescriptor->get_parameter_value(fCarlaPluginHandle, 9);
audioInfo.channels = fCarlaPluginDescriptor->get_parameter_value(fCarlaPluginHandle, kParameterInfoChannels);
audioInfo.bitDepth = fCarlaPluginDescriptor->get_parameter_value(fCarlaPluginHandle, kParameterInfoBitDepth);
audioInfo.sampleRate = fCarlaPluginDescriptor->get_parameter_value(fCarlaPluginHandle, kParameterInfoSampleRate);
audioInfo.length = fCarlaPluginDescriptor->get_parameter_value(fCarlaPluginHandle, kParameterInfoLength);
audioInfo.position = fCarlaPluginDescriptor->get_parameter_value(fCarlaPluginHandle, kParameterInfoPosition);
}
}

@@ -471,10 +473,10 @@ struct AudioFileListWidget : ImGuiWidget {
selectedFile = (size_t)-1;

static constexpr const char* const supportedExtensions[] = {
#ifdef HAVE_SNDFILE
#ifdef HAVE_SNDFILE
".aif",".aifc",".aiff",".au",".bwf",".flac",".htk",".iff",".mat4",".mat5",".oga",".ogg",".opus",
".paf",".pvf",".pvf5",".sd2",".sf",".snd",".svx",".vcc",".w64",".wav",".xi",
#endif
#endif
".mp3"
};



+ 8
- 0
plugins/Cardinal/src/AudioToCVPitch.cpp View File

@@ -95,6 +95,14 @@ struct AudioToCVPitch : Module {
configParam(PARAM_TOLERANCE, 0.f, 99.f, kDefaultTolerance, "Tolerance", " %");
}

~AudioToCVPitch() override
{
if (pitchDetector != nullptr)
del_aubio_pitch(pitchDetector);
del_fvec(detectedPitch);
del_fvec(inputBuffer);
}

void process(const ProcessArgs& args) override
{
float cvPitch = lastUsedOutputPitch;


+ 10
- 8
plugins/Cardinal/src/Blank.cpp View File

@@ -41,7 +41,7 @@ struct CardinalBlankModule : Module {
};

struct CardinalBlankImage : Widget {
int imageId = -2;
std::shared_ptr<Image> image;
int imageWidth = 0;
int imageHeight = 0;
bool hasModule;
@@ -53,26 +53,28 @@ struct CardinalBlankImage : Widget {

void draw(const DrawArgs& args) override
{
if (imageId == -2)
Image* img = image.get();

if (img == nullptr)
{
imageId = nvgCreateImage(args.vg, asset::plugin(pluginInstance, "res/Miku/Miku.png").c_str(), 0);
image = APP->window->loadImage(asset::plugin(pluginInstance, "res/Miku/Miku.png"));

if (imageId != -1)
nvgImageSize(args.vg, imageId, &imageWidth, &imageHeight);
if ((img = image.get()) != nullptr)
nvgImageSize(args.vg, img->handle, &imageWidth, &imageHeight);
}

if (imageId != -1 && imageWidth != 0 && imageHeight != 0)
if (img != nullptr && imageWidth != 0 && imageHeight != 0)
{
const float pixelRatio = hasModule ? APP->window->pixelRatio : 1.0f;
const float boxscale = std::min(box.size.x / imageWidth, box.size.y / imageHeight);
const float imgHeight = (imageHeight / pixelRatio) * boxscale;
nvgBeginPath(args.vg);
nvgRect(args.vg, 0, 0, box.size.x, box.size.y);
nvgRect(args.vg, 0, box.size.y * 0.5f - imgHeight * 0.5f, box.size.x, imgHeight);
nvgFillPaint(args.vg, nvgImagePattern(args.vg,
0,
(box.size.y / pixelRatio) * 0.5f - imgHeight * 0.5f,
box.size.x / pixelRatio,
imgHeight, 0, imageId, 1.0f));
imgHeight, 0, img->handle, 1.0f));
nvgFill(args.vg);
}
}


+ 17
- 14
plugins/Cardinal/src/Carla.cpp View File

@@ -1,6 +1,6 @@
/*
* DISTRHO Cardinal Plugin
* Copyright (C) 2021-2022 Filipe Coelho <falktx@falktx.com>
* Copyright (C) 2021-2023 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
@@ -132,7 +132,17 @@ struct CarlaModule : Module {
const char* binaryDir = nullptr;
const char* resourceDir = nullptr;

#if defined(CARLA_OS_MAC)
#if defined(CARLA_OS_WIN)
const std::string winBinaryDir = system::join(asset::systemDir, "Carla");

if (system::exists(winBinaryDir))
{
winResourceDir = system::join(winBinaryDir, "resources");
binaryDir = winBinaryDir.c_str();
resourceDir = winResourceDir.c_str();
}
#else // CARLA_OS_WIN
#if defined(CARLA_OS_MAC)
if (system::exists("~/Applications/Carla.app"))
{
binaryDir = "~/Applications/Carla.app/Contents/MacOS";
@@ -143,17 +153,10 @@ struct CarlaModule : Module {
binaryDir = "/Applications/Carla.app/Contents/MacOS";
resourceDir = "/Applications/Carla.app/Contents/MacOS/resources";
}
#elif defined(CARLA_OS_WIN)
const std::string winBinaryDir = system::join(asset::systemDir, "Carla");

if (system::exists(winBinaryDir))
{
winResourceDir = system::join(winBinaryDir, "resources");
binaryDir = winBinaryDir.c_str();
resourceDir = winResourceDir.c_str();
}
#else
if (system::exists("/usr/local/lib/carla"))
#else // CARLA_OS_MAC
if (false) {}
#endif // CARLA_OS_MAC
else if (system::exists("/usr/local/lib/carla"))
{
binaryDir = "/usr/local/lib/carla";
resourceDir = "/usr/local/share/carla/resources";
@@ -163,7 +166,7 @@ struct CarlaModule : Module {
binaryDir = "/usr/lib/carla";
resourceDir = "/usr/share/carla/resources";
}
#endif
#endif // CARLA_OS_WIN

if (binaryDir == nullptr)
{


+ 1
- 1
plugins/Cardinal/src/DearImGui.cpp View File

@@ -28,7 +28,7 @@
#include "DearImGui/imgui_draw.cpp"
#include "DearImGui/imgui_tables.cpp"
#include "DearImGui/imgui_widgets.cpp"
#if defined(DGL_USE_GLES2) || defined(DGL_USE_GLES3) || defined(DGL_USE_OPENGL3)
#if defined(DGL_USE_OPENGL3)
# include "DearImGui/imgui_impl_opengl3.cpp"
#else
# include "DearImGui/imgui_impl_opengl2.cpp"


+ 2
- 2
plugins/Cardinal/src/DearImGuiColorTextEditor/TextEditor.cpp View File

@@ -2038,11 +2038,11 @@ const TextEditor::Palette & TextEditor::GetDarkPalette()
const TextEditor::Palette & TextEditor::GetLightPalette()
{
const static Palette p = { {
0xff7f7f7f, // None
0xff000000, // None
0xffff0c06, // Keyword
0xff008000, // Number
0xff2020a0, // String
0xff304070, // Char literal
0xff000000, // Char literal
0xff000000, // Punctuation
0xff406060, // Preprocessor
0xff404040, // Identifier


+ 58
- 27
plugins/Cardinal/src/HostAudio.cpp View File

@@ -127,20 +127,13 @@ struct HostAudio2 : HostAudio<2> {
#ifndef HEADLESS
// for stereo meter
uint32_t internalDataFrame = 0;
float internalDataBuffer[2][128];
float internalDataBufferL[128] = {};
float internalDataBufferR[128] = {};
volatile bool resetMeters = true;
float gainMeterL = 0.0f;
float gainMeterR = 0.0f;
#endif

HostAudio2()
: HostAudio<2>()
{
#ifndef HEADLESS
std::memset(internalDataBuffer, 0, sizeof(internalDataBuffer));
#endif
}

#ifndef HEADLESS
void onReset() override
{
@@ -189,6 +182,9 @@ struct HostAudio2 : HostAudio<2> {

if (in1connected)
{
if (!std::isfinite(dataOuts[0][k]))
__builtin_unreachable();

valueL = inputs[0].getVoltageSum() * 0.1f;

if (dcFilterEnabled)
@@ -207,6 +203,9 @@ struct HostAudio2 : HostAudio<2> {

if (in2connected)
{
if (!std::isfinite(dataOuts[1][k]))
__builtin_unreachable();

valueR = inputs[1].getVoltageSum() * 0.1f;

if (dcFilterEnabled)
@@ -229,25 +228,51 @@ struct HostAudio2 : HostAudio<2> {
valueR = 0.0f;
}

const uint32_t j = internalDataFrame++;
internalDataBuffer[0][j] = valueL;
internalDataBuffer[1][j] = valueR;
if (pcontext->variant == kCardinalVariantMini)
{
const uint32_t j = internalDataFrame++;
internalDataBufferL[j] = valueL;
internalDataBufferR[j] = valueR;

if (internalDataFrame == 128)
if (internalDataFrame == 4)
{
internalDataFrame = 0;

if (resetMeters)
gainMeterL = gainMeterR = 0.0f;

gainMeterL = std::max(gainMeterL, d_findMaxNormalizedFloat<4>(internalDataBufferL));

if (in2connected)
gainMeterR = std::max(gainMeterR, d_findMaxNormalizedFloat<4>(internalDataBufferR));
else
gainMeterR = gainMeterL;

resetMeters = false;
}
}
else
{
internalDataFrame = 0;
const uint32_t j = internalDataFrame++;
internalDataBufferL[j] = valueL;
internalDataBufferR[j] = valueR;

if (resetMeters)
gainMeterL = gainMeterR = 0.0f;
if (internalDataFrame == 128)
{
internalDataFrame = 0;

gainMeterL = std::max(gainMeterL, d_findMaxNormalizedFloat(internalDataBuffer[0], 128));
if (resetMeters)
gainMeterL = gainMeterR = 0.0f;

if (in2connected)
gainMeterR = std::max(gainMeterR, d_findMaxNormalizedFloat(internalDataBuffer[1], 128));
else
gainMeterR = gainMeterL;
gainMeterL = std::max(gainMeterL, d_findMaxNormalizedFloat128(internalDataBufferL));

resetMeters = false;
if (in2connected)
gainMeterR = std::max(gainMeterR, d_findMaxNormalizedFloat128(internalDataBufferR));
else
gainMeterR = gainMeterL;

resetMeters = false;
}
}
#endif
}
@@ -294,19 +319,23 @@ struct HostAudio8 : HostAudio<8> {
template<int numIO>
struct HostAudioWidget : ModuleWidgetWith8HP {
HostAudio<numIO>* const module;
CardinalPluginContext* const pcontext;

HostAudioWidget(HostAudio<numIO>* const m)
: module(m)
: module(m),
pcontext(static_cast<CardinalPluginContext*>(APP))
{
setModule(m);
setPanel(APP->window->loadSvg(asset::plugin(pluginInstance, "res/HostAudio.svg")));

createAndAddScrews();

const uint8_t ioCount = pcontext->variant == kCardinalVariantMain ? 8 : 2;

for (uint i=0; i<numIO; ++i)
{
createAndAddInput(i);
createAndAddOutput(i);
createAndAddInput(i, i, i<ioCount);
createAndAddOutput(i, i, i<ioCount);
}
}

@@ -376,11 +405,13 @@ struct HostAudioWidget8 : HostAudioWidget<8> {

void draw(const DrawArgs& args) override
{
const uint8_t ioCount = pcontext->variant == kCardinalVariantMain ? 8 : 2;

drawBackground(args.vg);
drawOutputJacksArea(args.vg, 8);
drawOutputJacksArea(args.vg, ioCount);
setupTextLines(args.vg);

for (int i=0; i<8; ++i)
for (int i=0; i<ioCount; ++i)
{
char text[] = {'A','u','d','i','o',' ',static_cast<char>('0'+i+1),'\0'};
drawTextLine(args.vg, i, text);


+ 129
- 53
plugins/Cardinal/src/HostCV.cpp View File

@@ -18,8 +18,6 @@
#include "plugincontext.hpp"
#include "ModuleWidgets.hpp"

#define CARDINAL_AUDIO_IO_OFFSET 8

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

USE_NAMESPACE_DISTRHO;
@@ -54,17 +52,28 @@ struct HostCV : TerminalModule {
throw rack::Exception("Plugin context is null");

config(NUM_PARAMS, NUM_INPUTS, NUM_OUTPUTS, NUM_LIGHTS);
configParam<SwitchQuantity>(BIPOLAR_INPUTS_1_5, 0.f, 1.f, 0.f, "Bipolar Inputs 1-5")->randomizeEnabled = false;

if (pcontext->variant == kCardinalVariantMini)
{
configParam<SwitchQuantity>(BIPOLAR_INPUTS_1_5, 0.f, 1.f, 0.f, "Bipolar Inputs")->randomizeEnabled = false;
configParam<SwitchQuantity>(BIPOLAR_OUTPUTS_1_5, 0.f, 1.f, 0.f, "Bipolar Outputs")->randomizeEnabled = false;
}
else
{
configParam<SwitchQuantity>(BIPOLAR_INPUTS_1_5, 0.f, 1.f, 0.f, "Bipolar Inputs 1-5")->randomizeEnabled = false;
configParam<SwitchQuantity>(BIPOLAR_OUTPUTS_1_5, 0.f, 1.f, 0.f, "Bipolar Outputs 1-5")->randomizeEnabled = false;
}

configParam<SwitchQuantity>(BIPOLAR_INPUTS_6_10, 0.f, 1.f, 0.f, "Bipolar Inputs 6-10")->randomizeEnabled = false;
configParam<SwitchQuantity>(BIPOLAR_OUTPUTS_1_5, 0.f, 1.f, 0.f, "Bipolar Outputs 1-5")->randomizeEnabled = false;
configParam<SwitchQuantity>(BIPOLAR_OUTPUTS_6_10, 0.f, 1.f, 0.f, "Bipolar Outputs 6-10")->randomizeEnabled = false;
}

void processTerminalInput(const ProcessArgs&) override
{
if (pcontext->variant != kCardinalVariantMain)
if (pcontext->variant != kCardinalVariantMain && pcontext->variant != kCardinalVariantMini)
return;

const uint8_t ioOffset = pcontext->variant == kCardinalVariantMini ? 2 : 8;
const uint32_t bufferSize = pcontext->bufferSize;
const uint32_t processCounter = pcontext->processCounter;

@@ -87,27 +96,38 @@ struct HostCV : TerminalModule {
}
else if (const float* const* const dataIns = pcontext->dataIns)
{
if (dataIns[CARDINAL_AUDIO_IO_OFFSET] == nullptr)
if (dataIns[ioOffset] == nullptr)
return;

float outputOffset;
outputOffset = params[BIPOLAR_OUTPUTS_1_5].getValue() > 0.1f ? 5.0f : 0.0f;
outputOffset = params[BIPOLAR_OUTPUTS_1_5].getValue() > 0.1f ? 5.f : 0.f;

for (int i=0; i<5; ++i)
outputs[i].setVoltage(dataIns[i+CARDINAL_AUDIO_IO_OFFSET][k] - outputOffset);

outputOffset = params[BIPOLAR_OUTPUTS_6_10].getValue() > 0.1f ? 5.0f : 0.0f;

for (int i=5; i<10; ++i)
outputs[i].setVoltage(dataIns[i+CARDINAL_AUDIO_IO_OFFSET][k] - outputOffset);
outputs[i].setVoltage(dataIns[i+ioOffset][k] - outputOffset);

if (pcontext->variant == kCardinalVariantMain)
{
outputOffset = params[BIPOLAR_OUTPUTS_6_10].getValue() > 0.1f ? 5.f : 0.f;

for (int i=5; i<10; ++i)
outputs[i].setVoltage(dataIns[i+ioOffset][k] - outputOffset);
}
else
{
for (int i=5; i<10; ++i)
outputs[i].setVoltage(0.f);
}
}
}

void processTerminalOutput(const ProcessArgs&) override
{
if (pcontext->variant != kCardinalVariantMain || pcontext->bypassed)
if (pcontext->variant != kCardinalVariantMain && pcontext->variant != kCardinalVariantMini)
return;
if (pcontext->bypassed)
return;

const uint8_t ioOffset = pcontext->variant == kCardinalVariantMini ? 2 : 8;
const uint32_t bufferSize = pcontext->bufferSize;

// only incremented on output
@@ -119,54 +139,95 @@ struct HostCV : TerminalModule {

float** const dataOuts = pcontext->dataOuts;

if (dataOuts[CARDINAL_AUDIO_IO_OFFSET] == nullptr)
if (dataOuts[ioOffset] == nullptr)
return;

float inputOffset;
inputOffset = params[BIPOLAR_INPUTS_1_5].getValue() > 0.1f ? 5.0f : 0.0f;

for (int i=0; i<5; ++i)
dataOuts[i+CARDINAL_AUDIO_IO_OFFSET][k] += inputs[i].getVoltage() + inputOffset;
{
if (!std::isfinite(dataOuts[i+ioOffset][k]))
__builtin_unreachable();
dataOuts[i+ioOffset][k] += inputs[i].getVoltage() + inputOffset;
}

inputOffset = params[BIPOLAR_INPUTS_6_10].getValue() > 0.1f ? 5.0f : 0.0f;
if (pcontext->variant == kCardinalVariantMain)
{
inputOffset = params[BIPOLAR_INPUTS_6_10].getValue() > 0.1f ? 5.0f : 0.0f;

for (int i=5; i<10; ++i)
dataOuts[i+CARDINAL_AUDIO_IO_OFFSET][k] += inputs[i].getVoltage() + inputOffset;
for (int i=5; i<10; ++i)
{
if (!std::isfinite(dataOuts[i+ioOffset][k]))
__builtin_unreachable();
dataOuts[i+ioOffset][k] += inputs[i].getVoltage() + inputOffset;
}
}
}
};

#ifndef HEADLESS
struct HostCVWidget : ModuleWidgetWith8HP {
CardinalPluginContext* const pcontext;

HostCVWidget(HostCV* const module)
: pcontext(static_cast<CardinalPluginContext*>(APP))
{
setModule(module);
setPanel(APP->window->loadSvg(asset::plugin(pluginInstance, "res/HostCV.svg")));

createAndAddScrews();

uint8_t maxVisible;
switch (pcontext->variant)
{
case kCardinalVariantMain:
maxVisible = HostCV::NUM_INPUTS;
break;
case kCardinalVariantMini:
maxVisible = 5;
break;
default:
maxVisible = 0;
break;
}

for (uint i=0; i<HostCV::NUM_INPUTS; ++i)
createAndAddInput(i);
createAndAddInput(i, i, i<maxVisible);

for (uint i=0; i<HostCV::NUM_OUTPUTS; ++i)
createAndAddOutput(i);
createAndAddOutput(i, i, i<maxVisible);
}

void draw(const DrawArgs& args) override
{
drawBackground(args.vg);
drawOutputJacksArea(args.vg, HostCV::NUM_INPUTS);
setupTextLines(args.vg);

drawTextLine(args.vg, 0, "CV 1");
drawTextLine(args.vg, 1, "CV 2");
drawTextLine(args.vg, 2, "CV 3");
drawTextLine(args.vg, 3, "CV 4");
drawTextLine(args.vg, 4, "CV 5");
drawTextLine(args.vg, 5, "CV 6");
drawTextLine(args.vg, 6, "CV 7");
drawTextLine(args.vg, 7, "CV 8");
drawTextLine(args.vg, 8, "CV 9");
drawTextLine(args.vg, 9, "CV 10");

if (pcontext->variant == kCardinalVariantMain || pcontext->variant == kCardinalVariantMini)
{
drawOutputJacksArea(args.vg, pcontext->variant == kCardinalVariantMini ? 5 : HostCV::NUM_INPUTS);
setupTextLines(args.vg);

switch (pcontext->variant)
{
case kCardinalVariantMain:
drawTextLine(args.vg, 5, "CV 6");
drawTextLine(args.vg, 6, "CV 7");
drawTextLine(args.vg, 7, "CV 8");
drawTextLine(args.vg, 8, "CV 9");
drawTextLine(args.vg, 9, "CV 10");
// fall through
case kCardinalVariantMini:
drawTextLine(args.vg, 0, "CV 1");
drawTextLine(args.vg, 1, "CV 2");
drawTextLine(args.vg, 2, "CV 3");
drawTextLine(args.vg, 3, "CV 4");
drawTextLine(args.vg, 4, "CV 5");
break;
default:
break;
}
}

ModuleWidgetWith8HP::draw(args);
}
@@ -175,25 +236,40 @@ struct HostCVWidget : ModuleWidgetWith8HP {
{
menu->addChild(new ui::MenuSeparator);

menu->addChild(createCheckMenuItem("Bipolar Inputs 1-5", "",
[=]() {return module->params[HostCV::BIPOLAR_INPUTS_1_5].getValue() > 0.1f;},
[=]() {module->params[HostCV::BIPOLAR_INPUTS_1_5].setValue(1.0f - module->params[HostCV::BIPOLAR_INPUTS_1_5].getValue());}
));

menu->addChild(createCheckMenuItem("Bipolar Inputs 6-10", "",
[=]() {return module->params[HostCV::BIPOLAR_INPUTS_6_10].getValue() > 0.1f;},
[=]() {module->params[HostCV::BIPOLAR_INPUTS_6_10].setValue(1.0f - module->params[HostCV::BIPOLAR_INPUTS_6_10].getValue());}
));

menu->addChild(createCheckMenuItem("Bipolar Outputs 1-5", "",
[=]() {return module->params[HostCV::BIPOLAR_OUTPUTS_1_5].getValue() > 0.1f;},
[=]() {module->params[HostCV::BIPOLAR_OUTPUTS_1_5].setValue(1.0f - module->params[HostCV::BIPOLAR_OUTPUTS_1_5].getValue());}
));

menu->addChild(createCheckMenuItem("Bipolar Outputs 6-10", "",
[=]() {return module->params[HostCV::BIPOLAR_OUTPUTS_6_10].getValue() > 0.1f;},
[=]() {module->params[HostCV::BIPOLAR_OUTPUTS_6_10].setValue(1.0f - module->params[HostCV::BIPOLAR_OUTPUTS_6_10].getValue());}
));
if (pcontext->variant == kCardinalVariantMini)
{
menu->addChild(createCheckMenuItem("Bipolar Inputs", "",
[=]() {return module->params[HostCV::BIPOLAR_INPUTS_1_5].getValue() > 0.1f;},
[=]() {module->params[HostCV::BIPOLAR_INPUTS_1_5].setValue(1.0f - module->params[HostCV::BIPOLAR_INPUTS_1_5].getValue());}
));

menu->addChild(createCheckMenuItem("Bipolar Outputs", "",
[=]() {return module->params[HostCV::BIPOLAR_OUTPUTS_1_5].getValue() > 0.1f;},
[=]() {module->params[HostCV::BIPOLAR_OUTPUTS_1_5].setValue(1.0f - module->params[HostCV::BIPOLAR_OUTPUTS_1_5].getValue());}
));
}
else
{
menu->addChild(createCheckMenuItem("Bipolar Inputs 1-5", "",
[=]() {return module->params[HostCV::BIPOLAR_INPUTS_1_5].getValue() > 0.1f;},
[=]() {module->params[HostCV::BIPOLAR_INPUTS_1_5].setValue(1.0f - module->params[HostCV::BIPOLAR_INPUTS_1_5].getValue());}
));

menu->addChild(createCheckMenuItem("Bipolar Inputs 6-10", "",
[=]() {return module->params[HostCV::BIPOLAR_INPUTS_6_10].getValue() > 0.1f;},
[=]() {module->params[HostCV::BIPOLAR_INPUTS_6_10].setValue(1.0f - module->params[HostCV::BIPOLAR_INPUTS_6_10].getValue());}
));

menu->addChild(createCheckMenuItem("Bipolar Outputs 1-5", "",
[=]() {return module->params[HostCV::BIPOLAR_OUTPUTS_1_5].getValue() > 0.1f;},
[=]() {module->params[HostCV::BIPOLAR_OUTPUTS_1_5].setValue(1.0f - module->params[HostCV::BIPOLAR_OUTPUTS_1_5].getValue());}
));

menu->addChild(createCheckMenuItem("Bipolar Outputs 6-10", "",
[=]() {return module->params[HostCV::BIPOLAR_OUTPUTS_6_10].getValue() > 0.1f;},
[=]() {module->params[HostCV::BIPOLAR_OUTPUTS_6_10].setValue(1.0f - module->params[HostCV::BIPOLAR_OUTPUTS_6_10].getValue());}
));
}
}
};
#else


+ 13
- 8
plugins/Cardinal/src/HostMIDI.cpp View File

@@ -148,22 +148,27 @@ struct HostMIDI : TerminalModule {
channels = 1;
polyMode = ROTATE_MODE;
pwRange = 0;
panic();
panic(true);
}

/** Resets performance state */
void panic()
void panic(const bool resetPitch)
{
for (int c = 0; c < 16; c++) {
notes[c] = 60;
gates[c] = false;
velocities[c] = 0;
aftertouches[c] = 0;
pws[c] = 8192;
mods[c] = 0;
pwFilters[c].reset();
modFilters[c].reset();
}
if (resetPitch) {
for (int c = 0; c < 16; c++) {
notes[c] = 60;
pws[c] = 8192;
mods[c] = 0;
}
}
pedal = false;
rotateIndex = -1;
heldNotes.clear();
@@ -374,7 +379,7 @@ struct HostMIDI : TerminalModule {
// all notes off (panic)
case 0x7b: {
if (msg.getValue() == 0) {
panic();
panic(false);
}
} break;
default: break;
@@ -529,7 +534,7 @@ struct HostMIDI : TerminalModule {
if (channels == this->channels)
return;
this->channels = channels;
panic();
panic(true);
}

void setPolyMode(const PolyMode polyMode)
@@ -537,7 +542,7 @@ struct HostMIDI : TerminalModule {
if (polyMode == this->polyMode)
return;
this->polyMode = polyMode;
panic();
panic(true);
}
} midiInput;

@@ -886,7 +891,7 @@ struct HostMIDIWidget : ModuleWidgetWith9HP {
menu->addChild(createMenuLabel("MIDI Input & Output"));

menu->addChild(createMenuItem("Panic", "",
[=]() { module->midiInput.panic(); module->midiOutput.panic(); }
[=]() { module->midiInput.panic(true); module->midiOutput.panic(); }
));
}
};


+ 8
- 8
plugins/Cardinal/src/HostParameters-Map.cpp View File

@@ -63,8 +63,8 @@ struct HostParametersMap : TerminalModule {
uint8_t learningId = UINT8_MAX;

CardinalPluginContext* const pcontext;
bool parametersChanged[kModuleParameters] = {};
float parameterValues[kModuleParameters];
bool parametersChanged[kModuleParameterCount] = {};
float parameterValues[kModuleParameterCount];
bool bypassed = false;
bool firstRun = true;
uint32_t lastProcessCounter = 0;
@@ -135,7 +135,7 @@ struct HostParametersMap : TerminalModule {
if (isBypassed())
return;

for (uint32_t i = 0; i < kModuleParameters; ++i)
for (uint32_t i = 0; i < kModuleParameterCount; ++i)
{
if (d_isEqual(pcontext->parameters[i], parameterValues[i]))
continue;
@@ -161,7 +161,7 @@ struct HostParametersMap : TerminalModule {

// Validate hostParamId
const uint8_t hostParamId = mappings[id].hostParamId;
if (hostParamId >= kModuleParameters)
if (hostParamId >= kModuleParameterCount)
continue;

// Set filter from param value if filter is uninitialized
@@ -350,7 +350,7 @@ struct ParameterIndexQuantity : Quantity {
return 0;
}
float getMaxValue() override {
return kModuleParameters - 1;
return kModuleParameterCount - 1;
}
float getDefaultValue() override {
return 0;
@@ -360,7 +360,7 @@ struct ParameterIndexQuantity : Quantity {
}
void setValue(float value) override {
v = math::clamp(value, getMinValue(), getMaxValue());
mapping.hostParamId = math::clamp(static_cast<int>(v + 0.5f), 0, kModuleParameters - 1);
mapping.hostParamId = math::clamp(static_cast<int>(v + 0.5f), 0, kModuleParameterCount - 1);
}
float getDisplayValue() override {
return mapping.hostParamId + 1;
@@ -437,7 +437,7 @@ struct HostParametersMapChoice : CardinalLedDisplayChoice {
if (ParamWidget* const touchedParam = APP->scene->rack->touchedParam)
{
APP->scene->rack->touchedParam = nullptr;
DISTRHO_SAFE_ASSERT_RETURN(mapping.hostParamId < kModuleParameters,);
DISTRHO_SAFE_ASSERT_RETURN(mapping.hostParamId < kModuleParameterCount,);

const int64_t moduleId = touchedParam->module->id;
const int paramId = touchedParam->paramId;
@@ -453,7 +453,7 @@ struct HostParametersMapChoice : CardinalLedDisplayChoice {
text.clear();

// mapped
if (module->mappings[id].hostParamId < kModuleParameters)
if (module->mappings[id].hostParamId < kModuleParameterCount)
text += string::f("P%02d: ", module->mappings[id].hostParamId + 1);
if (module->mappings[id].paramHandle.moduleId >= 0)
text += getParamName();


+ 6
- 6
plugins/Cardinal/src/HostParameters.cpp View File

@@ -28,15 +28,15 @@ struct HostParameters : TerminalModule {
NUM_INPUTS
};
enum OutputIds {
NUM_OUTPUTS = 24
NUM_OUTPUTS = kModuleParameterCount
};
enum LightIds {
NUM_LIGHTS
};

CardinalPluginContext* const pcontext;
rack::dsp::SlewLimiter parameters[kModuleParameters];
bool parametersConnected[kModuleParameters] = {};
rack::dsp::SlewLimiter parameters[kModuleParameterCount];
bool parametersConnected[kModuleParameterCount] = {};
bool bypassed = false;
bool smooth = true;
uint32_t lastProcessCounter = 0;
@@ -59,7 +59,7 @@ struct HostParameters : TerminalModule {
bypassed = isBypassed();
lastProcessCounter = processCounter;

for (uint32_t i=0; i<kModuleParameters; ++i)
for (uint32_t i=0; i<kModuleParameterCount; ++i)
{
const bool connected = outputs[i].isConnected();

@@ -74,7 +74,7 @@ struct HostParameters : TerminalModule {
if (bypassed)
return;

for (uint32_t i=0; i<kModuleParameters; ++i)
for (uint32_t i=0; i<kModuleParameterCount; ++i)
{
if (parametersConnected[i])
outputs[i].setVoltage(smooth ? parameters[i].process(args.sampleTime, pcontext->parameters[i])
@@ -89,7 +89,7 @@ struct HostParameters : TerminalModule {
{
const double fall = 1.0 / (double(pcontext->bufferSize) / e.sampleRate);

for (uint32_t i=0; i<kModuleParameters; ++i)
for (uint32_t i=0; i<kModuleParameterCount; ++i)
{
parameters[i].reset();
parameters[i].setRiseFall(fall, fall);


+ 3
- 1
plugins/Cardinal/src/HostTime.cpp View File

@@ -93,12 +93,14 @@ struct HostTime : TerminalModule {
{
if (d_isZero(tick))
{
pulseClock.trigger();
pulseBeat.trigger();
if (timeInfo.beat == 1)
pulseBar.trigger();
}

if (d_isZero(tickClock))
pulseClock.trigger();

if (timeInfo.reset)
{
timeInfo.reset = false;


+ 780
- 186
plugins/Cardinal/src/Ildaeil.cpp
File diff suppressed because it is too large
View File


+ 13
- 10
plugins/Cardinal/src/ImGuiWidget.cpp View File

@@ -23,7 +23,7 @@
# include "../../../dpf/dgl/src/Resources.hpp"
#endif

#if defined(DGL_USE_GLES2) || defined(DGL_USE_GLES3) || defined(DGL_USE_OPENGL3)
#if defined(DGL_USE_OPENGL3)
# include "DearImGui/imgui_impl_opengl3.h"
#else
# include "DearImGui/imgui_impl_opengl2.h"
@@ -97,7 +97,7 @@ struct ImGuiWidget::PrivateData {
if (created)
{
ImGui::SetCurrentContext(context);
#if defined(DGL_USE_GLES2) || defined(DGL_USE_GLES3) || defined(DGL_USE_OPENGL3)
#if defined(DGL_USE_OPENGL3)
ImGui_ImplOpenGL3_Shutdown();
#else
ImGui_ImplOpenGL2_Shutdown();
@@ -171,7 +171,7 @@ struct ImGuiWidget::PrivateData {
if (created)
{
ImGui::SetCurrentContext(context);
#if defined(DGL_USE_GLES2) || defined(DGL_USE_GLES3) || defined(DGL_USE_OPENGL3)
#if defined(DGL_USE_OPENGL3)
ImGui_ImplOpenGL3_Shutdown();
#else
ImGui_ImplOpenGL2_Shutdown();
@@ -191,7 +191,7 @@ struct ImGuiWidget::PrivateData {

if (doInit)
{
#if defined(DGL_USE_GLES2) || defined(DGL_USE_GLES3) || defined(DGL_USE_OPENGL3)
#if defined(DGL_USE_OPENGL3)
ImGui_ImplOpenGL3_Init();
#else
ImGui_ImplOpenGL2_Init();
@@ -262,7 +262,7 @@ void ImGuiWidget::onContextCreate(const ContextCreateEvent& e)
DISTRHO_SAFE_ASSERT_RETURN(!imData->created,);

ImGui::SetCurrentContext(imData->context);
#if defined(DGL_USE_GLES2) || defined(DGL_USE_GLES3) || defined(DGL_USE_OPENGL3)
#if defined(DGL_USE_OPENGL3)
ImGui_ImplOpenGL3_Init();
#else
ImGui_ImplOpenGL2_Init();
@@ -275,7 +275,7 @@ void ImGuiWidget::onContextDestroy(const ContextDestroyEvent& e)
if (imData->created)
{
ImGui::SetCurrentContext(imData->context);
#if defined(DGL_USE_GLES2) || defined(DGL_USE_GLES3) || defined(DGL_USE_OPENGL3)
#if defined(DGL_USE_OPENGL3)
ImGui_ImplOpenGL3_Shutdown();
#else
ImGui_ImplOpenGL2_Shutdown();
@@ -481,7 +481,7 @@ void ImGuiWidget::drawFramebufferCommon(const Vec& fbSize, const float scaleFact
}
}

#if defined(DGL_USE_GLES2) || defined(DGL_USE_GLES3) || defined(DGL_USE_OPENGL3)
#if defined(DGL_USE_OPENGL3)
// TODO?
#else
glMatrixMode(GL_PROJECTION);
@@ -492,6 +492,9 @@ void ImGuiWidget::drawFramebufferCommon(const Vec& fbSize, const float scaleFact
glMatrixMode(GL_MODELVIEW);
glPushMatrix();
glLoadIdentity();

glClearColor(0.0f, 0.0f, 0.0f, 0.0f);
glClear(GL_COLOR_BUFFER_BIT);
#endif

io.DisplaySize = ImVec2(box.size.x * scaleFactor, box.size.y * scaleFactor);
@@ -499,7 +502,7 @@ void ImGuiWidget::drawFramebufferCommon(const Vec& fbSize, const float scaleFact

if (!imData->created)
{
#if defined(DGL_USE_GLES2) || defined(DGL_USE_GLES3) || defined(DGL_USE_OPENGL3)
#if defined(DGL_USE_OPENGL3)
ImGui_ImplOpenGL3_Init();
#else
ImGui_ImplOpenGL2_Init();
@@ -511,7 +514,7 @@ void ImGuiWidget::drawFramebufferCommon(const Vec& fbSize, const float scaleFact
io.DeltaTime = time - imData->lastFrameTime;
imData->lastFrameTime = time;

#if defined(DGL_USE_GLES2) || defined(DGL_USE_GLES3) || defined(DGL_USE_OPENGL3)
#if defined(DGL_USE_OPENGL3)
ImGui_ImplOpenGL3_NewFrame();
#else
ImGui_ImplOpenGL2_NewFrame();
@@ -523,7 +526,7 @@ void ImGuiWidget::drawFramebufferCommon(const Vec& fbSize, const float scaleFact

if (ImDrawData* const data = ImGui::GetDrawData())
{
#if defined(DGL_USE_GLES2) || defined(DGL_USE_GLES3) || defined(DGL_USE_OPENGL3)
#if defined(DGL_USE_OPENGL3)
ImGui_ImplOpenGL3_RenderDrawData(data);
#else
ImGui_ImplOpenGL2_RenderDrawData(data);


+ 8
- 4
plugins/Cardinal/src/ModuleWidgets.hpp View File

@@ -37,16 +37,20 @@ struct ModuleWidgetWithSideScrews : ModuleWidget {
createAndAddInput(paramId, paramId);
}

void createAndAddInput(const uint posY, const uint paramId) {
addInput(createInput<PJ301MPort>(Vec(startX_In, startY + padding * posY), module, paramId));
void createAndAddInput(const uint posY, const uint paramId, bool visible = true) {
PortWidget* const widget = createInput<PJ301MPort>(Vec(startX_In, startY + padding * posY), module, paramId);
widget->visible = visible;
addInput(widget);
}

void createAndAddOutput(const uint paramId) {
createAndAddOutput(paramId, paramId);
}

void createAndAddOutput(const uint posY, const uint paramId) {
addOutput(createOutput<PJ301MPort>(Vec(startX_Out, startY + padding * posY), module, paramId));
void createAndAddOutput(const uint posY, const uint paramId, bool visible = true) {
PortWidget* const widget = createOutput<PJ301MPort>(Vec(startX_Out, startY + padding * posY), module, paramId);
widget->visible = visible;
addOutput(widget);
}

void createAndAddScrews() {


Some files were not shown because too many files changed in this diff

Loading…
Cancel
Save