7 changed files with 456 additions and 10 deletions
@ -0,0 +1,4 @@
@@ -0,0 +1,4 @@
|
||||
Test Plugin |
||||
=========== |
||||
|
||||
Used for testing Zrythm features. |
@ -0,0 +1,81 @@
@@ -0,0 +1,81 @@
|
||||
/*
|
||||
* Copyright (C) 2021 Alexandros Theodotou <alex at zrythm dot org> |
||||
* |
||||
* This file is part of ZPlugins |
||||
* |
||||
* ZPlugins is free software: you can redistribute it and/or modify |
||||
* it under the terms of the GNU Affero General Public License as |
||||
* published by the Free Software Foundation, either version 3 of the |
||||
* License, or (at your option) any later version. |
||||
* |
||||
* ZPlugins 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 Affero General Public License for more details. |
||||
* |
||||
* You should have received a copy of the GNU General Affero Public License |
||||
* along with ZPlugins. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/ |
||||
|
||||
/**
|
||||
* \file |
||||
* |
||||
* Common code for both the DSP and the UI. |
||||
*/ |
||||
|
||||
#ifndef __Z_TEST_PLUGIN_COMMON_H__ |
||||
#define __Z_TEST_PLUGIN_COMMON_H__ |
||||
|
||||
#include PLUGIN_CONFIG |
||||
|
||||
#include "../common.h" |
||||
|
||||
typedef struct TestPluginUris |
||||
{ |
||||
} TestPluginUris; |
||||
|
||||
typedef enum PortIndex |
||||
{ |
||||
/** GUI to plugin communication. */ |
||||
TEST_PLUGIN_CONTROL, |
||||
/** Plugin to UI communication. */ |
||||
TEST_PLUGIN_NOTIFY, |
||||
|
||||
TEST_PLUGIN_MAJOR, |
||||
|
||||
/** Outputs. */ |
||||
TEST_PLUGIN_MIDI_OUT, |
||||
|
||||
NUM_PORTS, |
||||
} PortIndex; |
||||
|
||||
/**
|
||||
* Group of variables needed by both the DSP and |
||||
* the UI. |
||||
*/ |
||||
typedef struct TestPluginCommon |
||||
{ |
||||
/** Custom URIs. */ |
||||
TestPluginUris uris; |
||||
|
||||
PluginCommon pl_common; |
||||
} TestPluginCommon; |
||||
|
||||
static inline void |
||||
map_uris ( |
||||
LV2_URID_Map* urid_map, |
||||
TestPluginCommon * chordz_common) |
||||
{ |
||||
map_common_uris ( |
||||
urid_map, &chordz_common->pl_common.uris); |
||||
|
||||
#define MAP(x,uri) \ |
||||
chordz_common->uris.x = \ |
||||
urid_map->map (urid_map->handle, uri) |
||||
|
||||
/* custom URIs */ |
||||
|
||||
#undef MAP |
||||
} |
||||
|
||||
#endif |
@ -0,0 +1,260 @@
@@ -0,0 +1,260 @@
|
||||
/*
|
||||
* Copyright (C) 2018, 2020 Alexandros Theodotou <alex at zrythm dot org> |
||||
* |
||||
* This file is part of ZPlugins |
||||
* |
||||
* ZPlugins is free software: you can redistribute it and/or modify |
||||
* it under the terms of the GNU Affero General Public License as |
||||
* published by the Free Software Foundation, either version 3 of the |
||||
* License, or (at your option) any later version. |
||||
* |
||||
* ZPlugins 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 Affero General Public License for more details. |
||||
* |
||||
* You should have received a copy of the GNU General Affero Public License |
||||
* along with ZPlugins. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/ |
||||
|
||||
#include PLUGIN_CONFIG |
||||
|
||||
#include <float.h> |
||||
#include <math.h> |
||||
#include <stdlib.h> |
||||
#include <stdint.h> |
||||
#include <stdio.h> |
||||
#include <time.h> |
||||
#include <sys/time.h> |
||||
|
||||
#include "../math.h" |
||||
#include PLUGIN_COMMON |
||||
|
||||
/**
|
||||
* Struct for a 3 byte MIDI event, used for writing notes. |
||||
*/ |
||||
typedef struct MidiNoteEvent |
||||
{ |
||||
LV2_Atom_Event event; |
||||
uint8_t msg[3]; |
||||
} MidiNoteEvent; |
||||
|
||||
typedef struct TestPlugin |
||||
{ |
||||
/** Plugin ports. */ |
||||
const LV2_Atom_Sequence* control; |
||||
LV2_Atom_Sequence* notify; |
||||
const float * major; |
||||
|
||||
/* outputs */ |
||||
LV2_Atom_Sequence * midi_out; |
||||
|
||||
TestPluginCommon common; |
||||
|
||||
} TestPlugin; |
||||
|
||||
static LV2_Handle |
||||
instantiate ( |
||||
const LV2_Descriptor* descriptor, |
||||
double rate, |
||||
const char* bundle_path, |
||||
const LV2_Feature* const* features) |
||||
{ |
||||
TestPlugin * self = calloc (1, sizeof (TestPlugin)); |
||||
|
||||
SET_SAMPLERATE (self, rate); |
||||
|
||||
PluginCommon * pl_common = &self->common.pl_common; |
||||
int ret = |
||||
plugin_common_instantiate ( |
||||
pl_common, features, 0); |
||||
if (ret) |
||||
goto fail; |
||||
|
||||
/* map uris */ |
||||
map_uris (pl_common->map, &self->common); |
||||
|
||||
/* init atom forge */ |
||||
lv2_atom_forge_init ( |
||||
&pl_common->forge, pl_common->map); |
||||
|
||||
/* init logger */ |
||||
lv2_log_logger_init ( |
||||
&pl_common->logger, pl_common->map, pl_common->log); |
||||
|
||||
/* print info */ |
||||
if (pl_common->options) |
||||
{ |
||||
int j = 0; |
||||
while (true) |
||||
{ |
||||
LV2_Options_Option opt; |
||||
memcpy ( |
||||
&opt, &pl_common->options[j++], |
||||
sizeof (LV2_Options_Option)); |
||||
if (opt.key == 0 && opt.value == 0) |
||||
{ |
||||
break; |
||||
} |
||||
|
||||
if (opt.key == |
||||
pl_common->map->map ( |
||||
pl_common->map->handle, |
||||
"https://lv2.zrythm.org/ns/ext/host-info#name")) |
||||
{ |
||||
lv2_log_note ( |
||||
&pl_common->logger, "Host: %s\n", |
||||
*((const char **) opt.value)); |
||||
} |
||||
if (opt.key == |
||||
pl_common->map->map ( |
||||
pl_common->map->handle, |
||||
"https://lv2.zrythm.org/ns/ext/host-info#version")) |
||||
{ |
||||
lv2_log_note ( |
||||
&pl_common->logger, "Host Version: %s\n", |
||||
*((const char **) opt.value)); |
||||
} |
||||
} |
||||
} |
||||
|
||||
return (LV2_Handle) self; |
||||
|
||||
fail: |
||||
free (self); |
||||
return NULL; |
||||
} |
||||
|
||||
static void |
||||
connect_port ( |
||||
LV2_Handle instance, |
||||
uint32_t port, |
||||
void * data) |
||||
{ |
||||
TestPlugin * self = (TestPlugin *) instance; |
||||
|
||||
switch ((PortIndex) port) |
||||
{ |
||||
case TEST_PLUGIN_CONTROL: |
||||
self->control = |
||||
(const LV2_Atom_Sequence *) data; |
||||
break; |
||||
case TEST_PLUGIN_NOTIFY: |
||||
self->notify = |
||||
(LV2_Atom_Sequence *) data; |
||||
break; |
||||
case TEST_PLUGIN_MAJOR: |
||||
self->major = (const float *) data; |
||||
break; |
||||
case TEST_PLUGIN_MIDI_OUT: |
||||
self->midi_out = |
||||
(LV2_Atom_Sequence *) data; |
||||
break; |
||||
default: |
||||
break; |
||||
} |
||||
} |
||||
|
||||
static void |
||||
activate ( |
||||
LV2_Handle instance) |
||||
{ |
||||
/*TestPlugin * self = (TestPlugin*) instance;*/ |
||||
} |
||||
|
||||
static void |
||||
run ( |
||||
LV2_Handle instance, |
||||
uint32_t n_samples) |
||||
{ |
||||
TestPlugin * self = (TestPlugin *) instance; |
||||
|
||||
#ifdef TRIAL_VER |
||||
if (get_time_since_instantiation ( |
||||
&self->common.pl_common) > SECONDS_TO_SILENCE) |
||||
return; |
||||
#endif |
||||
|
||||
const uint32_t out_capacity = |
||||
self->midi_out->atom.size; |
||||
|
||||
/* write an empty Sequence header to the output */ |
||||
lv2_atom_sequence_clear (self->midi_out); |
||||
self->midi_out->atom.type = self->control->atom.type; |
||||
|
||||
/* read incoming events from host and UI */ |
||||
LV2_ATOM_SEQUENCE_FOREACH ( |
||||
self->control, ev) |
||||
{ |
||||
if (ev->body.type == PL_URIS(self)->midi_MidiEvent) |
||||
{ |
||||
const uint8_t * const msg = |
||||
(const uint8_t *) (ev + 1); |
||||
switch (lv2_midi_message_type(msg)) |
||||
{ |
||||
case LV2_MIDI_MSG_NOTE_ON: |
||||
break; |
||||
case LV2_MIDI_MSG_NOTE_OFF: |
||||
break; |
||||
case LV2_MIDI_MSG_CONTROLLER: |
||||
/* all notes off */ |
||||
if (msg[1] == 0x7b) |
||||
{ |
||||
} |
||||
break; |
||||
default: |
||||
/* forward all other MIDI events directly */ |
||||
lv2_atom_sequence_append_event( |
||||
self->midi_out, out_capacity, ev); |
||||
break; |
||||
} |
||||
} |
||||
} |
||||
} |
||||
|
||||
static void |
||||
deactivate ( |
||||
LV2_Handle instance) |
||||
{ |
||||
/*Saw * self = (Saw *) instance;*/ |
||||
} |
||||
|
||||
static void |
||||
cleanup ( |
||||
LV2_Handle instance) |
||||
{ |
||||
TestPlugin * self = (TestPlugin *) instance; |
||||
free (self); |
||||
} |
||||
|
||||
static const void* |
||||
extension_data ( |
||||
const char * uri) |
||||
{ |
||||
return NULL; |
||||
} |
||||
|
||||
static const LV2_Descriptor descriptor = { |
||||
PLUGIN_URI, |
||||
instantiate, |
||||
connect_port, |
||||
activate, |
||||
run, |
||||
deactivate, |
||||
cleanup, |
||||
extension_data |
||||
}; |
||||
|
||||
LV2_SYMBOL_EXPORT |
||||
const LV2_Descriptor* |
||||
lv2_descriptor ( |
||||
uint32_t index) |
||||
{ |
||||
switch (index) |
||||
{ |
||||
case 0: |
||||
return &descriptor; |
||||
default: |
||||
return NULL; |
||||
} |
||||
} |
@ -0,0 +1,92 @@
@@ -0,0 +1,92 @@
|
||||
/*
|
||||
* Copyright (C) 2021 Alexandros Theodotou <alex at zrythm dot org> |
||||
* |
||||
* This file is part of ZPlugins |
||||
* |
||||
* ZPlugins is free software: you can redistribute it and/or modify |
||||
* it under the terms of the GNU Affero General Public License as |
||||
* published by the Free Software Foundation, either version 3 of the |
||||
* License, or (at your option) any later version. |
||||
* |
||||
* ZPlugins 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 Affero General Public License for more details. |
||||
* |
||||
* You should have received a copy of the GNU General Affero Public License |
||||
* along with ZPlugins. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/ |
||||
|
||||
static void |
||||
print_ttl (FILE * f) |
||||
{ |
||||
fprintf (f, |
||||
"@prefix atom: <http://lv2plug.in/ns/ext/atom#> .\n\
|
||||
@prefix doap: <http://usefulinc.com/ns/doap#> .\n\ |
||||
@prefix log: <http://lv2plug.in/ns/ext/log#> .\n\ |
||||
@prefix lv2: <http://lv2plug.in/ns/lv2core#> .\n\ |
||||
@prefix midi: <http://lv2plug.in/ns/ext/midi#> .\n\ |
||||
@prefix pprop: <http://lv2plug.in/ns/ext/port-props#> .\n\ |
||||
@prefix rdf: <http://www.w3.org/1999/02/22-rdf-syntax-ns#> .\n\ |
||||
@prefix rdfs: <http://www.w3.org/2000/01/rdf-schema#> .\n\ |
||||
@prefix rsz: <http://lv2plug.in/ns/ext/resize-port#> .\n\ |
||||
@prefix time: <http://lv2plug.in/ns/ext/time#> .\n\ |
||||
@prefix urid: <http://lv2plug.in/ns/ext/urid#> .\n\ |
||||
@prefix ui: <http://lv2plug.in/ns/extensions/ui#> .\n\ |
||||
@prefix work: <http://lv2plug.in/ns/ext/worker#> .\n\n");
|
||||
|
||||
fprintf (f, |
||||
"<" PLUGIN_URI ">\n\
|
||||
a lv2:Plugin,\n\ |
||||
lv2:MIDIPlugin ;\n\ |
||||
doap:name \"" PLUGIN_NAME "\" ;\n\
|
||||
doap:license <https://www.gnu.org/licenses/agpl-3.0.html> ;\n\ |
||||
lv2:project <" PROJECT_URI "> ;\n\ |
||||
lv2:requiredFeature urid:map ;\n\ |
||||
lv2:optionalFeature log:log ,\n\ |
||||
lv2:hardRTCapable ;\n\ |
||||
lv2:port [\n\ |
||||
a lv2:InputPort ,\n\ |
||||
atom:AtomPort ;\n\ |
||||
atom:bufferType atom:Sequence ;\n\ |
||||
atom:supports <http://lv2plug.in/ns/ext/midi#MidiEvent> ;\n\ |
||||
rsz:minimumSize 2048 ;\n\ |
||||
lv2:index 0 ;\n\ |
||||
lv2:designation lv2:control ;\n\ |
||||
lv2:symbol \"control\" ;\n\
|
||||
lv2:name \"Control\" ;\n\
|
||||
rdfs:comment \"GUI/host to plugin communication\" ;\n\
|
||||
] , [\n\ |
||||
a lv2:OutputPort ,\n\ |
||||
atom:AtomPort ;\n\ |
||||
atom:bufferType atom:Sequence ;\n\ |
||||
lv2:index 1 ;\n\ |
||||
lv2:designation lv2:control ;\n\ |
||||
lv2:symbol \"notify\" ;\n\
|
||||
lv2:name \"Notify\" ;\n\
|
||||
rdfs:comment \"Plugin to GUI communication\" ;\n\
|
||||
] , [\n\ |
||||
a lv2:InputPort ,\n\ |
||||
lv2:ControlPort ;\n\ |
||||
lv2:index 2 ;\n\ |
||||
lv2:symbol \"major\" ;\n\
|
||||
lv2:name \"Major\" ;\n\
|
||||
lv2:portProperty lv2:toggled ;\n\ |
||||
lv2:default 1 ;\n\ |
||||
lv2:minimum 0 ;\n\ |
||||
lv2:maximum 1 ;\n\ |
||||
] , [\n"); |
||||
|
||||
fprintf (f, "\
|
||||
a lv2:OutputPort ,\n\ |
||||
atom:AtomPort ;\n\ |
||||
atom:bufferType atom:Sequence ;\n\ |
||||
atom:supports <http://lv2plug.in/ns/ext/midi#MidiEvent> ;\n\ |
||||
rsz:minimumSize 2048 ;\n\ |
||||
lv2:index 3 ;\n\ |
||||
lv2:designation lv2:control ;\n\ |
||||
lv2:symbol \"midi_out\" ;\n\
|
||||
lv2:name \"MIDI out\" ;\n\
|
||||
rdfs:comment \"MIDI output\" ;\n\
|
||||
] .\n\n"); |
||||
} |
Loading…
Reference in new issue