1 /**
2 FL Plugin interface.
3 
4 Copyright: Guillaume Piolat 2023.
5 License:   $(LINK2 http://www.boost.org/LICENSE_1_0.txt, Boost License 1.0)
6 */
7 module dplug.flp.types;
8 
9 nothrow @nogc:
10 
11 import core.stdc.config;
12 
13 // interlaced stereo 32Bit float buffer
14 alias TWAV32FS = float[2];
15 alias PWAV32FS = TWAV32FS*;
16 alias TWAV32FM = float;
17 alias PWAV32FM = float*;
18 
19 // MIDI out message structure (3 bytes standard MIDI message + port)
20 struct TMIDIOutMsg
21 {
22     align(1):
23     char Status;
24     char Data1;
25     char Data2;
26     char Port;
27 }
28 static assert(TMIDIOutMsg.sizeof == 4);
29 alias PMIDIOutMsg = TMIDIOutMsg*;
30 
31 // Bar:Step:Tick
32 struct TSongTime
33 {
34     int Bar;
35     int Step;
36     int Tick;
37 }
38 
39 // Time sig info (easily converted to standard x/x time sig, but more powerful)
40 struct TTimeSigInfo
41 {
42     int StepsPerBar;
43     int StepsPerBeat;
44     int PPQ;
45 }
46 
47 alias HANDLE = void*;
48 alias ULONG = uint;
49 alias HRESULT = c_long;
50 
51 
52 // plugin flags
53 enum int FPF_Generator         = 1;        // plugin is a generator (not effect)
54 enum int FPF_RenderVoice       = 1 << 1;   // generator will render voices separately (Voice_Render) (not used yet)
55 enum int FPF_UseSampler        = 1 << 2;   // 'hybrid' generator that will stream voices into the host sampler (Voice_Render)
56 enum int FPF_GetChanCustomShape= 1 << 3;   // generator will use the extra shape sample loaded in its parent channel (see FPD_ChanSampleChanged)
57 enum int FPF_GetNoteInput      = 1 << 4;   // plugin accepts note events (not used yet, but effects might also get note input later)(EDIT: was implemented apparently)
58 enum int FPF_WantNewTick       = 1 << 5;   // plugin will be notified before each mixed tick (& be able to control params (like a built-in MIDI controller) (see NewTick))
59 enum int FPF_NoProcess         = 1 << 6;   // plugin won't process buffers at all (FPF_WantNewTick, or special visual plugins (Fruity NoteBook))
60 enum int FPF_NoWindow          = 1 << 10;  // plugin will show in the channel settings window & not in its own floating window
61 enum int FPF_Interfaceless     = 1 << 11;  // plugin doesn't provide its own interface (not used yet)
62 enum int FPF_TimeWarp          = 1 << 13;  // supports timewarps, that is, can be told to change the playing position in a voice (direct from disk music tracks, ...) (not used yet)
63 enum int FPF_MIDIOut           = 1 << 14;  // plugin will send MIDI out messages (only those will be enabled when rendering to a MIDI file)
64 enum int FPF_DemoVersion       = 1 << 15;  // plugin is a trial version, & the host won't save its automation
65 enum int FPF_CanSend           = 1 << 16;  // plugin has access to the send tracks, so it can't be dropped into a send track or into the master
66 enum int FPF_MsgOut            = 1 << 17;  // plugin will send delayed messages to itself (will require the internal sync clock to be enabled)
67 enum int FPF_HybridCanRelease  = 1 << 18;  // plugin is a hybrid generator & can release its envelope by itself. If the host's volume envelope is disabled, then the sound will keep going when the voice is stopped, until the plugin has finished its own release
68 enum int FPF_GetChanSample     = 1 << 19;  // generator will use the sample loaded in its parent channel (see FPD_ChanSampleChanged)
69 enum int FPF_WantFitTime       = 1 << 20;  // fit to time selector will appear in channel settings window (see FPD_SetFitTime)
70 enum int FPF_NewVoiceParams    = 1 << 21;  // MUST BE USED - tell the host to use TVoiceParams instead of TVoiceParams_Old
71 enum int FPF_Reserved1         = 1 << 22;  // don't use (Delphi version specific)
72 enum int FPF_CantSmartDisable  = 1 << 23;  // plugin can't be smart disabled
73 enum int FPF_WantSettingsBtn   = 1 << 24;  // plugin wants a settings button on the titlebar (mainly for the wrapper)
74 enum int FPF_CanStealKBFocus   = 1 << 25;  // plugin can steal keyboard focus away from FL
75 enum int FPF_VFX               = 1 << 26;  // is VFX plugin
76 enum int FPF_MacNeedsNSView    = 1 << 27;  // On Mac: This plugin requires a NSView parent
77 
78 
79 // plugin dispatcher ID's
80 // called from GUI thread unless specified
81 enum int FPD_ShowEditor        =0;     // shows the editor (ParentHandle in Value)
82 enum int FPD_ProcessMode       =1;     // sets processing mode flags (flags in value) (can be ignored)
83 enum int FPD_Flush             =2;     // breaks continuity (empty delay buffers, filter mem, etc.) (warning: can be called from the mixing thread) (GM)
84 enum int FPD_SetBlockSize      =3;     // max processing length (samples) (in value)
85 enum int FPD_SetSampleRate     =4;     // sample rate in Value
86 enum int FPD_WindowMinMax      =5;     // allows the plugin to set the editor window resizable (min/max PRect in index, sizing snap PPoint in value)
87 enum int FPD_KillAVoice        =6;     // (in case the mixer was eating way too much CPU) the plugin is asked to kill its weakest voice & return 1 if it did something (not used yet)
88 enum int FPD_UseVoiceLevels    =7;     // return 0 if the plugin doesn't support the default per-voice level Index
89                                         // return 1 if the plugin supports the default per-voice level Index (filter cutoff (0) or filter resonance (1))
90                                         // return 2 if the plugin supports the per-voice level Index, but for another function (then check FPN_VoiceLevel)
91                                         //=8;     (private message)
92 enum int FPD_SetPreset         =9;     // set internal preset Index (mainly for wrapper)
93 enum int FPD_ChanSampleChanged =10;    // (see FPF_GetChanCustomShape) sample has been loaded into the parent channel, & given to the plugin
94 // either as a wavetable (FPF_GetChanCustomshape) (pointer to shape in Value, same format as WaveTables)
95 // or as a sample (FPF_GetChanSample) (TSampleHandle in Index)
96 enum int FPD_SetEnabled        =11;    // the host has enabled/disabled the plugin (state in Value) (warning: can be called from the mixing thread) (GM)
97 enum int FPD_SetPlaying        =12;    // the host is playing (song pos info is valid when playing) (state in Value) (warning: can be called from the mixing thread) (GM)
98 enum int FPD_SongPosChanged    =13;    // song position has been relocated (by other means than by playing of course) (warning: can be called from the mixing thread) (GM)
99 enum int FPD_SetTimeSig        =14;    // PTimeSigInfo in Value (GM)
100 enum int FPD_CollectFile       =15;    // let the plugin tell which files need to be collected or put in zip files. File # in Index, starts from 0 until no more filenames are returned (PChar in Result).
101 enum int FPD_SetInternalParam  =16;    // (private message to known plugins, ignore) tells the plugin to update a specific, non-automated param
102 enum int FPD_SetNumSends       =17;    // tells the plugin how many send tracks there are (fixed to 4, but could be set by the user at any time in a future update) (number in Value) (!!! will be 0 if the plugin is in the master or a send track, since it can't access sends)
103 enum int FPD_LoadFile          =18;    // when a file has been dropped onto the parent channel's button (LFT_ type in Index, filename in Value). Result should be 0 if not handled, 1 if handled and 2 if a dropped file should be rejected
104 // LFT_DownloadDataPack option is used to download Flex packs: Result is -1 if failed, or Pack index on success
105 enum int FPD_SetFitTime        =19;    // set fit to time in beats (FLOAT time in value (need to typecast))
106 enum int FPD_SetSamplesPerTick =20;    // # of samples per tick (changes when tempo, PPQ or sample rate changes) (FLOAT in Value (need to typecast)) (warning: can be called from the mixing thread) (GM)
107 enum int FPD_SetIdleTime       =21;    // set the freq at which Idle is called (can vary), ms time in Value
108 enum int FPD_SetFocus          =22;    // the host has focused/unfocused the editor (focused in Value) (plugin can use this to steal keyboard focus ... also see FPD_StealKBFocus)
109 enum int FPD_Transport         =23;    // special transport messages, from a controller. See GenericTransport.pas for Index. Must return 1 if handled.
110 enum int FPD_MIDIIn            =24;    // live MIDI input preview, allows the plugin to steal messages (mostly for transport purposes). Must return 1 if handled. Packed message (only note on/off for now) in Value.
111 enum int FPD_RoutingChanged    =25;    // mixer routing changed, must check FHD_GetInOuts if necessary. See RCV_ constants for the meaning of the Value parameter.
112 enum int FPD_GetParamInfo      =26;    // retrieves info about a parameter. Param number in Index, see PI_Float for the result
113 enum int FPD_ProjLoaded        =27;    // called after a project has been loaded, to leave a chance to kill automation (that could be loaded after the plugin is created) if necessary
114 enum int FPD_WrapperLoadState  =28;    // (private message to the plugin wrapper) load a (VST1, DX) plugin state, pointer in Index, length in Value
115 enum int FPD_ShowSettings      =29;    // called when the settings button on the titlebar is switched. On/off in Value (1=active). See FPF_WantSettingsBtn
116 enum int FPD_SetIOLatency      =30;    // input/output latency (Index,Value) of the output, in samples (only for information)
117 enum int FPD_PreferredNumIO    =32;    // (message from Patcher) retrieves the preferred number (0=default, -1=none) of audio inputs (Index=0), audio outputs (Index=1) or voice outputs (Index=2)
118 enum int FPD_GetGUIColor       =33;    // retrieves the darkest background color of the GUI (Index=0 for background), for a nicer border around it
119 enum int FPD_CloseAllWindows   =34;    // hide all windows opened by the plugin (except the plugin editor window)
120 enum int FPD_RenderWindowBitmap=35;    // used by ZgeViz
121 enum int FPD_StealKBFocus      =36;    // switch stealing keyboard focus off or on (Value = 0 or 1)
122 enum int FPD_GetHelpContext    =37;    // for plugins that want to show specific help pages, like Patcher. Return the context as a UTF-8 encoded PAnsiChar as the result. Return 0 or an empty string for the default context.
123 enum int FPD_RegChanged        =38;    // notify plugin about registration change
124 enum int FPD_ArrangeWindows    =39;    // arrange subwindows into the workspace (Value = workspace PRect)
125 enum int FPD_PluginLoaded      =40;    // done opening the plugin - note that SaveRestoreState is called before this!
126 enum int FPD_ContextInfoChanged=41;    // Index holds the type of information (see CI_ constants), call FHD_GetContextInfo for the new value(s)
127 enum int FPD_ProjectInfoChanged=42;    // Index holds the value that changed (see GPI_ contants)
128 enum int FPD_GetDemoPlugins    =43;    // Returns ; delimited list (formatted as "productCode|name") of plugins in demo mode. If Value is 1, it should only list plugins that were saved as a demo.
129 enum int FPD_UnLockDemoPlugins =44;    // Tells a plugin to recheck demo mode and unlock purchased plugins
130 enum int FPD_ColorWasPicked = 46; // called after FHD_PickVoiceColor finishes. The new color value (an index, not RGB) is passed in Value.
131 enum int FPD_IsInDebugMode = 47; // return 0 for no, 1 for yes
132 enum int FPD_ColorsHaveChanged = 48; // some shared colors have changed. Index indicates the palette (see CP_ constants).
133 enum int FPD_GetStateSizeEstimate = 49; //get plugin estimated state size
134 enum int FPD_UseIncreasedMIDIResolution = 50; // return 1 if increased MIDI resolution is supported
135 enum int FPD_ConvertStringToValue = 51;  //let plugin do string to value conversion, value is pointer to TConvertStringToValueData record , used for custom type in value
136 enum int FPD_GetParamType = 52; //return control (Index) param type, see //FPD_GetParamType options below
137 
138 // host dispatcher IDs
139 enum int FHD_ParamMenu         =0;     // the popup menu for each control (Index=param index, Value=popup item index (see FHP_EditEvents))
140 enum int FHD_GetParamMenuFlags =1;     // [OBSOLETE, see FHD_GetParamMenuEntry] before the popup menu is shown, you must ask the host to tell if items are checked or disabled (Index=param index, Value=popup item index, Result=flags (see FHP_Disabled))
141 enum int FHD_EditorResized     =2;     // to notify the host that the editor (EditorHandle) has been resized
142 enum int FHD_NamesChanged      =3;     // to notify the host that names (GetName function) have changed, with the type of names in Value (see the FPN_ constants)
143 enum int FHD_ActivateMIDI      =4;     // makes the host enable its MIDI output, useful when a MIDI out plugin is created (but not useful for plugin wrappers)
144 enum int FHD_WantMIDIInput     =5;     // plugin wants to be notified about MIDI messages (for processing or filtering) (switch in Value)
145 enum int FHD_WantMIDITick      =6;     // plugin wants to receive MIDITick events, allowing MIDI out plugins (not used yet)
146 enum int FHD_LocatePlugin      =7;     // ask the host to find a plugin, pass the simple filename in Value, full path is returned as Result (both PAnsiChar). Set Index to 1 if you want host to show a warning if plugin could not be found.
147 enum int FHD_KillAutomation    =8;     // ask the host to kill the automation linked to the plugin, for params # between Index & Value (included) (can be used for a trial version of the plugin)
148 enum int FHD_SetNumPresets     =9;     // tell the host how many (Value) internal presets the plugin supports (mainly for wrapper)
149 enum int FHD_SetNewName        =10;    // sets a new short name for the parent (PChar in Value)
150 enum int FHD_VSTiIdle          =11;    // used by the VSTi wrapper, because the dumb VSTGUI needs idling for his knobs
151 enum int FHD_SelectChanSample  =12;    // ask the parent to open a selector for its channel sample (see FPF_UseChanSample)
152 enum int FHD_WantIdle          =13;    // plugin wants to receive the idle message (enabled by default) (Value=0 for disabled, 1 for enabled when UI is visible, 2 for always enabled)
153 enum int FHD_LocateDataFile    =14;    // ask the host to search for a file in its search paths, pass the simple filename in Value, full path is returned as Result (both PChar) (Result doesn't live long, please copy it asap)
154 enum int FHD_ShowPlugSelector  =15;    // ask the host to show the plugin selector (Index: see SPSF flags)
155 enum int FHD_TicksToTime       =16;    // translate tick time (Value) into Bar:Step:Tick (PSongTime in Index) (warning: it's *not* Bar:Beat:Tick)
156 enum int FHD_AddNotesToPR      =17;    // add a note to the piano roll, PNotesParams in Value
157 enum int FHD_GetParamMenuEntry =18;    // before the popup menu is shown, you must fill it with the entries set by the host (Index=param index, Value=popup item index (starting from 0), Result=PParamMenuEntry, or null pointer if no more entry)
158 enum int FHD_MsgBox            =19;    // make fruity show a message box (PChar in Index [formatted as 'Title|Message'], flags in Value (MB_OkCancel, MB_IconWarning, etc.), result in IDOk, IDCancel format (as in TApplication.MessageBox)
159 enum int FHD_NoteOn            =20;    // preview note on (semitone in Index low word, color in index high word (0=default), velocity in Value)
160 enum int FHD_NoteOff           =21;    // preview note off (semitone in Index, color in index high word, velocity in Value (-1=default otherwise 0..127))
161 enum int FHD_OnHint_Direct     =22;    // same as OnHint, but show it immediately (to show a progress while you're doing something) (PChar in Value)
162 enum int FHD_SetNewColor       =23;    // sets a new color for the parent (color in Value) (see FHD_SetNewName);
163 enum int FHD_GetInstance       =24;    // (Windows) returns the module instance of the host (could be an exe or a DLL, so not the process itself)
164 enum int FHD_KillIntCtrl       =25;    // ask the host to kill anything linked to an internal controller, for # between Index & Value (included) (used when undeclaring internal controllers)
165 enum int FHD_CheckProdCode     =26;    // reserved
166 enum int FHD_SetNumParams      =27;    // override the # of parameters (for plugins that have a different set of parameters per instance) (number of parameters in Value)
167 enum int FHD_PackDataFile      =28;    // ask the host to pack an absolute filename into a local filemane, pass the simple filename in Value, packed path is returned as Result (both PChar) (Result doesn't live long, please copy it asap)
168 enum int FHD_GetPath           =29;    // ask the host for a path specified by Index (see GP_ constants) (returned as Result)
169 enum int FHD_SetLatency        =30;    // set plugin latency, if any (samples in Value)
170 enum int FHD_CallDownloader    =31;    // call the presets downloader (optional plugin name PAnsiChar in Value)
171 enum int FHD_EditSample		=32;	// edits sample in Edison (PChar in Value, Index=1 means an existing Edison can be re-used)
172 enum int FHD_SetThreadSafe     =33;    // plugin is thread-safe, doing its own thread-sync using LockMix_Shared (switch in Value)
173 enum int FHD_SmartDisable      =34;    // plugin asks FL to exit or enter smart disabling (if currently active), mainly for generators when they get MIDI input (switch in Value)
174 enum int FHD_SetUID            =35;    // sets a unique identifying string for this plugin. This will be used to save/restore custom data related to this plugin. Handy for wrapper plugins. (PChar in Value)
175 enum int FHD_GetMixingTime     =36;    // get mixer time, Index is the time format required (see GT_... constants). Value is a pointer to a TFPTime, which is filled with an optional offset in samples
176 enum int FHD_GetPlaybackTime   =37;    // get playback time, same as above
177 enum int FHD_GetSelTime        =38;    // get selection time in t & t2, same as above. Returns 0 if no selection (t & t2 are then filled with full song length).
178 enum int FHD_GetTimeMul        =39;    // get current tempo multiplicator, that's not part of the song but used for fast-forward
179 enum int FHD_Captionize        =40;    // captionize the plugin (useful when dragging) (captionized in Value)
180 enum int FHD_SendSysEx         =41;    // send a SysEx string (pointer to array in Value, the first integer being the length of the string, the rest being the string), through port Index, immediately (do not abuse)
181 enum int FHD_LoadAudioClip     =42;    // send an audio file to the playlist as an audio clip, starting at the playlist selection. Options in Index (see LAC_ constants). FileName as PAnsiChar in Value.
182 enum int FHD_LoadInChannel     =43;    // send a file to the selected channel(s) (mainly for Edison), FileName as PChar in Value
183 enum int FHD_ShowInBrowser     =44;    // locates the file in the browser & jumps to it (Index is one of SIB_ constants, PAnsiChar filename in Value)
184 enum int FHD_DebugLogMsg       =45;    // adds message to the debug log (PChar in Value)
185 enum int FHD_GetMainFormHandle =46;    // gets the handle of the main form (HWND in Value, 0 if none)
186 enum int FHD_GetProjDataPath   =47;    // [OBSOLETE - use FHD_GetPath instead] ask the host where the project data is, to store project data (returned as Result)
187 enum int FHD_SetDirty          =48;    // mark project as dirty (not required for automatable parameters, only for tweaks the host can't be aware of)
188 enum int FHD_AddToRecent       =49;    // add file to recent files (PChar in Value)
189 enum int FHD_GetNumInOut       =50;    // ask the host how many inputs (Index=0) are routed to this effect (see GetInBuffer), or how many outputs (Index=1) this effect is routed to (see GetOutBuffer)
190 enum int FHD_GetInName         =51;    // ask the host the name of the input Index (!!! first = 1), in Value as a PNameColor, Result=0 if failed (Index out of range)
191 enum int FHD_GetOutName        =52;    // ask the host the name of the ouput Index (!!! first = 1), in Value as a PNameColor, Result=0 if failed (Index out of range)
192 enum int FHD_ShowEditor        =53;    // make host bring plugin's editor (visibility in Value, -1 to toggle)
193 enum int FHD_FloatAutomation   = 54;   // (for the plugin wrapper only) ask the host to turn 0..FromMIDI_Max automation into 0..1 float, for params # between Index & Value (included)
194 enum int FHD_ShowSettings      =55;    // called when the settings button on the titlebar should be updated switched. On/off in Value (1=active). See FPF_WantSettingsBtn
195 enum int FHD_NoteOnOff         =56;    // generators only! note on/off (semitone in Index low word, color in index high word, NOT recorded in bit 30, velocity in Value (<=0 = note off))
196 enum int FHD_ShowPicker        =57;    // show picker (mode [0=plugins, 1=project] in Index, categories [gen=0/FX=1/both=-1/Patcher (includes VFX)=-2] in Value)
197 enum int FHD_GetIdleOverflow   =58;    // ask the host for the # of extra frames Idle should process, generally 0 if no overflow/frameskip occured
198 enum int FHD_ModalIdle         =59;    // used by FL plugins, when idling from a modal window, mainly for the smoothness hack
199 enum int FHD_RenderProject     =60;    // prompt the rendering dialog in song mode
200 enum int FHD_GetProjectInfo    =61;    // get project title, author, comments, URL, naked filename (Index), (returned as Result as a *PWideChar*)
201 enum int FHD_ForceDetached     =62;    // used by Wrapper in OSX to force the plugin form to be detached
202 enum int FHD_StartDrag         =63;    // sent by Patcher when starting dragging a preset
203 enum int FHD_EndDrag           =64;    // sent by Patcher when finished dragging a preset
204 enum int FHD_PreviewKey        =65;    // chance for host to handle keyboard messages, Index=flags in lower 16 bits (see KUD constants) and virtual key in second 16 bits, Value=KeyData from WM_KeyUp or WM_KeyDown message (0 if not available), returns 1 if handled and 0 if not
205 enum int FHD_RenderWindowBitmap=66;    // used by ZgeViz
206 enum int FHD_UpdateStealKBFocus=67;    // the plugin will steal kb input or not (Value is 1 or 0)
207 //=68;    // [OBSOLETE]
208 enum int FHD_GetPluginMenuMode =69;    // returns the view mode of the favorite plugin menus in FL: 0=categories 1=tree 2=flat
209 enum int FHD_OpenTool          =70;    // open application in System\Tools folder. Index=tool to start (see OTI_ControlCreator), Value=PAnsiChar with command line params
210 enum int FHD_GetPathManager	=71;	// returns IPathManager instance (pointer)
211 enum int FHD_RegisterSideInput =72;	// let the host know that you intend to use a sidechained input, so latency can be calculated. Index=input index (first=1), Value=see RSIO_ constants
212 enum int FHD_RegisterSideOutput=73;	// let the host know that you intend to use a sidechained output, so latency can be calculated. Index=output index (depends on use of GetInsBuffer or GetOutBuffer), Value=see RSIO_ constants
213 
214 enum int FHD_ReportError		=74; 	// report error during plugin load (will show combined dialog for all missing plugins after project is loaded or MsgBox in case we are adding plugin to project)
215 enum int FHD_ShowStandardParamMenu=75; // ask FL to pop up a parameter menu, so the plugin doesn't have to implement it itself. Index is the parameter index.
216 enum int FHD_GetContextInfo	=76; 	// get information about various things. Index is the information type (see CI_ constants), Value and result depend on the type
217 enum int FHD_SetContextInfo	=77; 	// change some piece of context information. Index is the information type (see CI_ constants), Value and result depend on the type
218 enum int FHD_GetExternalMedia	=78;    // set Flags (bits) as index, for example : EMD_SearchImages or EMD_DownloadFile to search and download images
219 enum int FHD_Transport         =79;    // allows the plugin to control FL through some of the messages in GenericTransport. Index=message, Value=release/switch/hold value. Currently only FPT_Play and FPT_Stop are supported. Returns -1 if can't be handled, 0 if not handled, 1 if handled by focused plugin, 2 if handled by focused form, 4 if handled by menu, 5 if delayed, 8 if handled globally.
220 enum int FHD_DownloadMissing   =80;    // notify FL about missing data pack
221 enum int FHD_DownloadFinished  =81;    // notify FL that a pack download is finished
222 enum int FHD_DebugBuild        =82;    // tell FL to show a [DEBUG] warning in the plugin window caption. Value is 0 (release) or 1 (debug)
223 enum int FHD_PickVoiceColor    =83;    // Show the piano roll's color picker. Index = screen co-ordinates with x in first 2 bytes and y in next 2 bytes, Value = current color number (not an RGB value). Will call FPD_ColorWasPicked when the user selects a color.
224 enum int FHD_GetColorRGBValue  =84;    // Get the RGB value for a color in a palette. Index is the color palette (see CP_ constants for available palettes). Value is the index in the palette. If Value is -1, this returns the count of colors in the palette.
225 enum int FHD_ShowException     =85;    // Show application exception. Index is Exception.Message string. Value is Stack-trace string.
226 enum int FHD_GetTranslationMoFile =86; // Get the current translation object (for Plugins)
227 enum int FHD_PresetSelected    =87;    // tell the host internal preset is changed
228 
229 
230 enum int FPN_Param             =0;     // retrieve name of param Index
231 enum int FPN_ParamValue        =1;     // retrieve text label of param Index for value Value (used in event editor)
232 enum int FPN_Semitone          =2;     // retrieve name of note Index (used in piano roll), for color (=MIDI channel) Value
233 enum int FPN_Patch             =3;     // retrieve name of patch Index (not used yet)
234 enum int FPN_VoiceLevel        =4;     // retrieve name of per-voice param Index (default is filter cutoff (0) & resonance (1)) (optional)
235 enum int FPN_VoiceLevelHint    =5;     // longer description for per-voice param (works like FPN_VoiceLevels)
236 enum int FPN_Preset            =6;     // for plugins that support internal presets (mainly for the wrapper plugin), retrieve the name for program Index
237 enum int FPN_OutCtrl           =7;     // for plugins that output controllers, retrieve the name of output controller Index
238 enum int FPN_VoiceColor        =8;     // retrieve name of per-voice color (MIDI channel) Index
239 enum int FPN_OutVoice          =9;     // for plugins that output voices, retrieve the name of output voice Index
240 
241 enum int REC_UpdateValue       =1;     // update the value
242 enum int REC_GetValue          =2;     // retrieves the value
243 enum int REC_ShowHint          =4;     // updates the hint (if any)
244 enum int REC_UpdateControl     =16;    // updates the wheel/knob
245 enum int REC_FromMIDI          =32;    // value from 0 to FromMIDI_Max has to be translated (& always returned, even if REC_GetValue isn't set)
246 enum int REC_NoLink            =1024;  // don't check if wheels are linked (internal to plugins, useful for linked controls)
247 enum int REC_InternalCtrl      =2048;  // sent by an internal controller - internal controllers should pay attention to those, to avoid nasty feedbacks
248 enum int REC_PlugReserved      =4096;  // free to use by plugins
249 
250 // event ID's
251 enum int FPE_Tempo             =0;     // FLOAT tempo in value (need to typecast), & average samples per tick in Flags (DWORD) (warning: can be called from the mixing thread) (GM)
252 enum int FPE_MaxPoly           =1;     // max poly in value (infinite if <=0) (only interesting for standalone generators)
253 // since MIDI plugins, or other plugin wrappers won't support the voice system, they should be notified about channel pan, vol & pitch changes
254 enum int FPE_MIDI_Pan          =2;     // MIDI channel panning (0..127) in EventValue, FL panning in -64..+64 in Flags (warning: can be called from the mixing thread) (GM)
255 enum int FPE_MIDI_Vol          =3;     // MIDI channel volume (0..127) in EventValue + volume as normalized float in Flags (need to typecast) (warning: can be called from the mixing thread) (GM)
256 enum int FPE_MIDI_Pitch        =4;     // MIDI channel pitch in *cents* (to be translated according to current pitch bend range) in EventValue (warning: can be called from the mixing thread) (GM)
257 
258 enum int CI_TrackName         = 0;  // (R/W) PAnsiChar encoded as UTF-8
259 enum int CI_TrackIndex        = 1;  // (R)
260 enum int CI_TrackColor        = 2;  // (R/W) color is RGBA
261 enum int CI_TrackSelected     = 3;  // (R/W) the track is selected (0=false 1=true, 2=selected with other tracks)
262 enum int CI_TrackFocused      = 4;  // (R) the track is focused for user input (0=false 1=true)
263 enum int CI_TrackIsOutput     = 5;  // (R) the track sends directly to an audio device output (0=false, 1=true)
264 enum int CI_TrackVolume       = 6;  // (R/W) (float+string) the value of the tracks' volume slider. Info is floating point (single / float) cast to an int32
265 enum int CI_TrackPan          = 7;  // (R/W) (float+string) the value of the track's panning knob, as a single / float (-1..1) cast to int32
266 enum int CI_TrackMuteSolo     = 8;  // (R/W) flags indicate mute and solo state for a track (see CIMS_ constants)
267 enum int CI_TrackSendCount    = 9;  // (R) returns the send count for the plugin's track
268 enum int CI_TrackSendLevel    = 10; // (R/W) (float+string) get or set the level for a specific send of this track. On read, Value holds the send index. On write, Value holds a pointer to a TContextInfo record with the new value in FloatValue.
269 enum int CI_TrackMaxVolume    = 11; // (R) get the maximum value for mixer track volume
270 enum int CI_TrackMaxSendLevel = 12; // (R) get the maximum value for mixer track send level
271 
272 
273 alias TPluginTag = intptr_t;
274 
275 // plugin info, common to all instances of the same plugin
276 struct TFruityPlugInfo
277 {
278 align(4):
279     int SDKVersion;    // =CurrentSDKVersion
280     char* LongName;    // full plugin name (should be the same as DLL name)
281     char* ShortName;   // & short version (for labels)
282     int Flags;         // see FPF_Generator
283     int NumParams;     // (maximum) number of parameters, can be overridden using FHD_SetNumParams
284     int DefPoly;       // preferred (default) max polyphony (Fruity manages polyphony) (0=infinite)
285     int NumOutCtrls;   // number of internal output controllers
286     int NumOutVoices;  // number of internal output voices
287     int[30] Reserved;  // set to zero
288 }
289 
290 // Same as Delphi type.
291 struct TPoint
292 {
293     int x, y;
294 }
295 
296 // Same as Delphi type.
297 struct TRect
298 {
299     int x1, y1;
300     int x2, y2;
301 }
302 
303 alias PFruityPlugInfo = TFruityPlugInfo*;
304 
305 
306 
307 alias intptr_t = size_t;
308 alias TVoiceHandle = intptr_t;
309 alias TOutVoiceHandle = intptr_t;
310 
311 // sample handle
312 alias TSampleHandle = intptr_t;
313 
314 extern(C++) class IStream 
315 {
316 public:
317 nothrow:
318 @nogc:
319     extern(System) abstract
320     {
321         void QueryInterface();
322         ULONG AddRef();
323         ULONG Release();
324         HRESULT Read(void *pv, ULONG cb, ULONG *pcbRead);
325         HRESULT Write(const void *pv, ULONG cb, ULONG *pcbWritten);
326 
327         // There are more methods, but not useful for us
328     }
329 }
330 
331 
332 alias BOOL = int;
333 
334 alias PWaveFormatExtensible = void*;
335 alias PSampleInfo = void*;
336 alias PSampleRegion = void*;
337 alias PIOBuffer = void*;
338 
339 
340 // plugin class, made extern(C++) to have no field and an empty v-table.
341 extern(C++) class TFruityPlug 
342 {
343 public:
344 nothrow:
345 @nogc:
346 
347     /// free for the host to use (parent object reference, ...), passed as 'Sender' to the host
348     TPluginTag HostTag;
349 
350     PFruityPlugInfo Info;
351 
352     /// handle to the editor window panel (created by the plugin)
353     void* EditorHandle;       
354 
355     int MonoRender;         // 0 or 1, last rendered voice rendered mono data (not used yet)
356 
357     int[32] Reserved;        // for future use, set to zero
358 
359 
360     // *** functions ***
361     // (G) = called from GUI thread, (M) = called from mixer thread, (GM) = both, (S) = called from MIDI synchronization thread
362     // (M) calls are done inside the plugin lock (LockPlugin / UnlockPlugin)
363     // + TriggerVoice and Voice_ functions are also called inside the plugin lock
364     // + assume that any other call is not locked! (so call LockPlugin / UnlockPlugin where necessary, but no more than that)
365     // + don't call back to the host while inside a LockPlugin / UnlockPlugin block
366 
367     // messages (to the plugin)
368     extern(System) abstract
369     {
370         void DestroyObject();  // (G)
371         intptr_t Dispatcher(intptr_t ID, intptr_t Index, intptr_t Value);  // (GM)
372         void Idle_Public();  // (G) (used to be Idle())
373         void SaveRestoreState(IStream Stream, BOOL Save);  // (G)
374 
375         // names (see FPN_Param) (Name must be at least 256 chars long)
376         void GetName(int Section, int Index, int Value, char *Name);  // (GM)
377 
378         // events
379         int ProcessEvent(int EventID, int EventValue, int Flags);  // (GM)
380         int ProcessParam(int Index, int Value, int RECFlags);  // (GM)
381 
382         // effect processing (source & dest can be the same)
383         void Eff_Render(PWAV32FS SourceBuffer, PWAV32FS DestBuffer, int Length);  // (M)
384         // generator processing (can render less than length)
385         void Gen_Render(PWAV32FS DestBuffer, ref int Length);  // (M)
386 
387         // voice handling
388         TVoiceHandle TriggerVoice(TVoiceParams* VoiceParams, intptr_t SetTag);  // (GM)
389         void Voice_Release(TVoiceHandle Handle);  // (GM)
390         void Voice_Kill(TVoiceHandle Handle);  // (GM)
391         int Voice_ProcessEvent(TVoiceHandle Handle, intptr_t EventID, intptr_t EventValue, intptr_t Flags);  // (GM)
392         int Voice_Render(TVoiceHandle Handle, PWAV32FS DestBuffer, ref int Length);  // (GM)
393 
394 
395         // (see FPF_WantNewTick) called before a new tick is mixed (not played)
396         // internal controller plugins should call OnControllerChanged from here
397         void NewTick();  // (M)
398 
399         // (see FHD_WantMIDITick) called when a tick is being played (not mixed) (not used yet)
400         void MIDITick();  // (S)
401 
402         // MIDI input message (see FHD_WantMIDIInput & TMIDIOutMsg) (set Msg to MIDIMsg_Null if it has to be killed)
403         void MIDIIn(ref int Msg);  // (GM)
404 
405         // buffered messages to itself (see PlugMsg_Delayed)
406         void MsgIn(intptr_t Msg);  // (S)
407 
408         // voice handling
409         int OutputVoice_ProcessEvent(TOutVoiceHandle Handle, intptr_t EventID, intptr_t EventValue, intptr_t Flags);  // (GM)
410         void OutputVoice_Kill(TVoiceHandle Handle);  // (GM)
411     }
412 }
413 
414 extern(C++) class TFruityPlugHost 
415 {
416 public:
417 nothrow:
418 @nogc:
419 
420     alias PWaveT = void*;
421 
422     // *** params ***
423     int HostVersion;     // current FruityLoops version stored as 01002003 (integer) for 1.2.3
424     final int majorVersion() // this one should not go into v-table
425     {
426         return (HostVersion >>> 24);
427     }
428 
429     int Flags;           // reserved
430 
431     // windows
432     HANDLE AppHandle;    // application handle, for slaving windows
433 
434     // handy wavetables (32Bit float (-1..1), 16384 samples each)
435     // 6 are currently defined (sine, triangle, square, saw, analog saw, noise)
436     // those pointers are fixed
437     // (obsolete, avoid)
438     PWaveT[10] WaveTables;
439 
440     // handy free buffers, guaranteed to be at least the size of the buffer to be rendered (float stereo)
441     // those pointers are variable, please read & use while rendering only
442     // those buffers are contiguous, so you can see TempBuffer[0] as a huge buffer
443     PWAV32FS[4] TempBuffers;
444 
445     // reserved for future use
446     int[30] Reserved;    // set to zero
447 
448 
449     // *** functions ***
450 
451     extern(System) abstract
452     {
453         // messages (to the host) (Sender=plugin tag)
454         intptr_t Dispatcher(TPluginTag Sender, intptr_t ID, intptr_t Index, intptr_t Value);
455 
456         // for the host to store changes
457         void OnParamChanged(TPluginTag Sender, int Index, int Value);
458 
459         // for the host to display hints (call from GUI thread!)
460         void OnHint(TPluginTag Sender, char *Text);
461 
462         // compute left & right levels using pan & volume info (OLD, OBSOLETE VERSION, USE ComputeLRVol INSTEAD)
463         void ComputeLRVol_Old(ref float LVol, ref float RVol, int Pan, float Volume);
464 
465         // voice handling (Sender=voice tag)
466         void Voice_Release(intptr_t Sender);
467         void Voice_Kill(intptr_t Sender, BOOL KillHandle);
468         int Voice_ProcessEvent(intptr_t Sender, intptr_t EventID, intptr_t EventValue, intptr_t Flags);
469 
470         // thread synchronisation / safety
471         void LockMix_Old();  // will prevent any new voice creation & rendering
472         void UnlockMix_Old();
473 
474 
475         // delayed MIDI out message (see TMIDIOutMsg) (will be sent once the MIDI tick has reached the current mixer tick
476         void MIDIOut_Delayed(TPluginTag Sender, intptr_t Msg);
477         // direct MIDI out message
478         void MIDIOut(TPluginTag Sender, intptr_t Msg);
479 
480         // adds a mono float buffer to a stereo float buffer, with left/right levels & ramping if needed
481         // how it works: define 2 float params for each voice: LastLVol & LastRVol. Make them match LVol & RVol before the *first* rendering of that voice (unless ramping will occur from 0 to LVol at the beginning).
482         // then, don't touch them anymore, just pass them to the function.
483         // the level will ramp from the last ones (LastLVol) to the new ones (LVol) & will adjust LastLVol accordingly
484         // LVol & RVol are the result of the ComputeLRVol function
485         // for a quick & safe fade out, you can set LVol & RVol to zero, & kill the voice when both LastLVol & LastRVol will reach zero
486         void AddWave_32FM_32FS_Ramp(void *SourceBuffer, void *DestBuffer, int Length, float LVol, float RVol, ref float LastLVol, ref float LastRVol);
487         // same, but takes a stereo source
488         // note that left & right channels are not mixed (not a true panning), but might be later
489         void AddWave_32FS_32FS_Ramp(void *SourceBuffer, void *DestBuffer, int Length, float LVol, float RVol, ref float LastLVol, ref float LastRVol);
490 
491         // sample loading functions (FruityLoops 3.1.1 & over)
492         // load a sample (creates one if necessary)
493         // FileName must have room for 256 chars, since it gets written with the file that has been 'located'
494         // only 16Bit 44Khz Stereo is supported right now, but fill the format correctly!
495         // see FHLS_ShowDialog
496         bool LoadSample(ref TSampleHandle Handle, char *FileName, PWaveFormatExtensible NeededFormat, int Flags);
497         void * GetSampleData(TSampleHandle Handle, ref int Length);
498         void CloseSample(TSampleHandle Handle);
499 
500         // time info
501         // get the current mixing time, in ticks (integer result)
502         // obsolete, use FHD_GetMixingTime & FHD_GetPlaybackTime
503         int GetSongMixingTime();
504         // get the current mixing time, in ticks (more accurate, with decimals)
505         double GetSongMixingTime_A();
506         // get the current playing time, in ticks (with decimals)
507         double GetSongPlayingTime();
508 
509         // internal controller
510         void OnControllerChanged(TPluginTag Sender, intptr_t Index, intptr_t Value);
511 
512         // get a pointer to one of the send buffers (see FPD_SetNumSends)
513         // those pointers are variable, please read & use while processing only
514         // the size of those buffers is the same as the size of the rendering buffer requested to be rendered
515         void * GetSendBuffer(intptr_t Num);
516 
517         // ask for a message to be dispatched to itself when the current mixing tick will be played (to synchronize stuff) (see MsgIn)
518         // the message is guaranteed to be dispatched, however it could be sent immediately if it couldn't be buffered (it's only buffered when playing)
519         void PlugMsg_Delayed(TPluginTag Sender, intptr_t Msg);
520         // remove a buffered message, so that it will never be dispatched
521         void PlugMsg_Kill(TPluginTag Sender, intptr_t MSg);
522 
523         // get more details about a sample
524         void GetSampleInfo(TSampleHandle Handle, PSampleInfo Info);
525 
526         // distortion (same as TS404) on a piece of mono or stereo buffer
527         // DistType in 0..1, DistThres in 1..10
528         void DistWave_32FM(int DistType, int DistThres, void *SourceBuffer, int Length, float DryVol, float WetVol, float Mul);
529 
530         // same as GetSendBuffer, but Num is an offset to the mixer track assigned to the generator (Num=0 will then return the current rendering buffer)
531         // to be used by generators ONLY, & only while processing
532         void *  GetMixBuffer(int Num);
533 
534         // get a pointer to the insert (add-only) buffer following the buffer a generator is currently processing in
535         // Ofs is the offset to the current buffer, +1 means next insert track, -1 means previous one, 0 is forbidden
536         // only valid during Gen_Render
537         // protect using LockMix_Shared
538         void *  GetInsBuffer(TPluginTag Sender, int Ofs);
539 
540         // ask the host to prompt the user for a piece of text (s has room for 256 chars)
541         // set x & y to -1 to have the popup screen-centered
542         // if 0 is returned, ignore the results
543         // set c to -1 if you don't want the user to select a color
544         BOOL  PromptEdit(int x, int y, char *SetCaption, char *s, ref int c);
545 
546         // deprecated, use SuspendOutput and ResumeOutput instead
547         void  SuspendOutput_Old();
548         void  ResumeOutput_Old();
549 
550         // get the region of a sample
551         void  GetSampleRegion(TSampleHandle Handle, int RegionNum, PSampleRegion Region);
552 
553         // compute left & right levels using pan & volume info (USE THIS AFTER YOU DEFINED FPF_NewVoiceParams)
554         void  ComputeLRVol(ref float LVol, ref float RVol, float Pan, float Volume);
555 
556         // use this instead of PlugHost.LockMix
557         void  LockPlugin(TPluginTag Sender);
558         void  UnlockPlugin(TPluginTag Sender);
559 
560         // multithread processing synchronisation / safety
561         void  LockMix_Shared_Old();
562         void  UnlockMix_Shared_Old();
563 
564         // multi-in/output (for generators & effects) (only valid during Gen/Eff_Render)
565         // !!! Index starts at 1, to be compatible with GetInsBuffer (Index 0 would be Eff_Render's own buffer)
566         void  GetInBuffer(TPluginTag Sender, intptr_t Index, PIOBuffer IBuffer);    // returns (read-only) input buffer Index (or Nil if not available).
567         void  GetOutBuffer(TPluginTag Sender, intptr_t Index, PIOBuffer OBuffer);   // returns (add-only) output buffer Index (or Nil if not available). Use LockMix_Shared when adding to this buffer.
568 
569 
570         alias TVoiceParams = void;
571         // output voices (VFX "voice effects")
572         TOutVoiceHandle  TriggerOutputVoice(TVoiceParams *VoiceParams, intptr_t SetIndex, intptr_t SetTag);  // (GM)
573         void  OutputVoice_Release(TOutVoiceHandle Handle);  // (GM)
574         void  OutputVoice_Kill(TOutVoiceHandle Handle);  // (GM)
575         int  OutputVoice_ProcessEvent(TOutVoiceHandle Handle, intptr_t EventID, intptr_t EventValue, intptr_t Flags);  // (GM)
576 
577         // ask the host to prompt the user for a piece of text, color, icon ... See PEO_ constants for SetOptions. Text should be null or a pointer to an allocated buffer with at least 255 characters!
578         BOOL  PromptEdit_Ex(int x, int y, const char* SetCaption, char* Text, ref int Color1, ref int Color2, ref int IconIndex, int FontHeight, int SetOptions);
579 
580         // SuspendOutput removes the plugin from all processing lists, so Eff/Gen_Render and voice functions will no longer be called.
581         // To be used around lengthy operations (instead of straightforward locking)
582         void  SuspendOutput(TPluginTag Sender);
583         void  ResumeOutput(TPluginTag Sender);
584     }
585 }
586 
587 // NEW VERSION (all floats), USE THESE
588 struct TLevelParams 
589 {
590     float Pan;    // panning (-1..1)
591     float Vol;    // volume/velocity (0.0 = -inf dB .. 1.0 = 0 dB) - note: can go above 1.0!
592     float Pitch;  // pitch (in cents) (semitone=Pitch/100)
593     float FCut;   // filter cutoff (0..1)
594     float FRes;   // filter Q (0..1)
595 }
596 
597 struct TVoiceParams
598 {
599     TLevelParams InitLevels;
600     TLevelParams FinalLevels;
601 }
602 
603 struct TFPTime
604 {
605     double t, t2;
606 }