Skip to content

Commit

Permalink
UserInteractions Refactoring (#4379)
Browse files Browse the repository at this point in the history
Addresses #4337
Closes #2671 #3435

Refactor/Remove the UserInteractions in favor of JUCE equivalents
and appropirate wrappers

- openURL -> juce::URL.lauch
- showHTML -> surgeguieditor builtin
- Remove openFileInFinder or whatnot for juce::URL(juce::File()).laucnh
- promptInfo removed; single use replaced with an Alert box
- Remove UserInteractions::promptError to be data driven
- promptOKCancel moved to a gui free function which can be replaced and
  is replaced in SGE
- promptFileOpen replaced with juce::FileChooser
- Finally, remove the old files which were no longer used
  • Loading branch information
baconpaul authored Apr 23, 2021
1 parent 3a9157a commit 4ca0fa8
Show file tree
Hide file tree
Showing 36 changed files with 318 additions and 1,235 deletions.
19 changes: 0 additions & 19 deletions CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -357,7 +357,6 @@ if( APPLE )
)

set(SURGE_OS_GUI_SOURCES
src/mac/UserInteractionsMac.mm
)

set(OS_INCLUDE_DIRECTORIES
Expand Down Expand Up @@ -394,7 +393,6 @@ if( APPLE )

elseif( UNIX AND NOT APPLE )
set(SURGE_OS_GUI_SOURCES
src/linux/UserInteractionsLinux.cpp
)

find_package(PkgConfig REQUIRED)
Expand Down Expand Up @@ -469,7 +467,6 @@ elseif( UNIX AND NOT APPLE )
elseif( WIN32 )

set(SURGE_OS_GUI_SOURCES
src/windows/UserInteractionsWin.cpp
)

set(OS_COMPILE_DEFINITIONS
Expand Down Expand Up @@ -562,7 +559,6 @@ if( BUILD_HEADLESS )
${SURGE_OS_SOURCES}
${SURGE_GENERATED_SOURCES}
src/headless/main.cpp
src/headless/UserInteractionsHeadless.cpp
src/headless/LinkFixesHeadless.cpp
src/headless/HeadlessUtils.cpp
src/headless/Player.cpp
Expand Down Expand Up @@ -678,13 +674,6 @@ file(MAKE_DIRECTORY ${SURGE_PRODUCT_DIR})
add_custom_target(surge-staged-assets)

if( BUILD_SURGE_EFFECTS_BANK )
# LinkOrder on Linux matters so make a little lib which contains UIJUCE so I can link
# it AFTER surge-shared (since the libs come after the source in the JUCE build of course)
# FIXME of course that this should go away in surge-xt. These are also split now for
# XT vs FX since FX is production code in 19 and XT is not
add_library(surge-juce-userint-fx src/surge_effects_bank/UserInteractionsJUCE.cpp )
target_include_directories(surge-juce-userint-fx PRIVATE ${SURGE_COMMON_INCLUDES})

juce_add_plugin(surge-fx
PRODUCT_NAME "Surge XT Effects"
COMPANY_NAME "Surge Synth Team"
Expand Down Expand Up @@ -759,7 +748,6 @@ if( BUILD_SURGE_EFFECTS_BANK )
surge::tinyxml

surge-shared
surge-juce-userint-fx
surge-fx-binary

juce::juce_audio_utils
Expand Down Expand Up @@ -878,11 +866,6 @@ if( BUILD_SURGE_XT )
)
endif()

# LinkOrder on Linux matters so make a little lib which contains UIJUCE so I can link
# it AFTER surge-shared (since the libs come after the source in the JUCE build of course)
add_library(surge-xt-userint src/surge_synth_juce/UserInteractionsJUCE_Synth_XT.cpp)
target_include_directories(surge-xt-userint PRIVATE ${SURGE_COMMON_INCLUDES})

set(SURGE_SYNTH_JUCE_GUI_SOURCES
${SURGE_GUI_SOURCES}
)
Expand Down Expand Up @@ -928,7 +911,6 @@ if( BUILD_SURGE_XT )
surge::tinyxml

surge-shared
surge-xt-userint

juce::juce_audio_utils
juce::juce_audio_processors
Expand Down Expand Up @@ -1046,7 +1028,6 @@ if( ${BUILD_SURGE_PYTHON_BINDINGS} )

${PYSRCD}/surgepy.cpp
src/headless/HeadlessUtils.cpp
src/headless/UserInteractionsHeadless.cpp
)

target_compile_definitions(surgepy
Expand Down
3 changes: 1 addition & 2 deletions src/common/PatchDB.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,6 @@

#include "sqlite3.h"
#include "SurgeStorage.h"
#include "UserInteractions.h"
#include <sstream>
#include <iterator>
#include "vt_dsp_endian.h"
Expand Down Expand Up @@ -70,7 +69,7 @@ CREATE TABLE PatchFeature (
std::ostringstream oss;
oss << "An error occured opening sqlite file '" << dbname << "'. The error was '"
<< sqlite3_errmsg(dbh) << "'.";
Surge::UserInteractions::promptError(oss.str(), "Surge Patch Database Error");
storage->reportError(oss.str(), "Surge Patch Database Error");
dbh = nullptr;
}
char *emsg;
Expand Down
3 changes: 1 addition & 2 deletions src/common/SurgePatch.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,6 @@
#include "DebugHelpers.h"
#include "StringOps.h"
#include "SkinModel.h"
#include "UserInteractions.h"
#include "UserDefaults.h"
#include "version.h"

Expand Down Expand Up @@ -1109,7 +1108,7 @@ void SurgePatch::load_xml(const void *data, int datasize, bool is_preset)
<< ". Features of the patch will not be available in your "
<< "session. You can always find the latest Surge at "
"https://surge-synthesizer.github.io/";
Surge::UserInteractions::promptError(oss.str(), "Surge Patch Version Mismatch");
storage->reportError(oss.str(), "Surge Patch Version Mismatch");
}

TiXmlElement *meta = TINYXML_SAFE_TO_ELEMENT(patch->FirstChild("meta"));
Expand Down
44 changes: 28 additions & 16 deletions src/common/SurgeStorage.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,6 @@

#include "DspUtilities.h"
#include "SurgeStorage.h"
#include "UserInteractions.h"
#include <set>
#include <numeric>
#include <cctype>
Expand Down Expand Up @@ -450,7 +449,7 @@ SurgeStorage::SurgeStorage(std::string suppliedDataPath) : otherscene_clients(0)
if (!snapshotloader.LoadFile(snapshotmenupath)) // load snapshots (& config-stuff)
{
Surge::UserInteractions::promptError("Cannot find 'configuration.xml' in path '" +
reportError("Cannot find 'configuration.xml' in path '" +
datapath + "'. Please reinstall surge.",
"Surge is not properly installed.");
}
Expand All @@ -462,9 +461,9 @@ SurgeStorage::SurgeStorage(std::string suppliedDataPath) : otherscene_clients(0)
"\n";
if (!snapshotloader.Parse(cxmlData.c_str()))
{
Surge::UserInteractions::promptError("Cannot parse 'configuration.xml' in path '" +
datapath + "'. Please reinstall surge.",
"Surge is not properly installed.");
reportError("Cannot parse 'configuration.xml' in path '" + datapath +
"'. Please reinstall surge.",
"Surge is not properly installed.");
}

load_midi_controllers();
Expand Down Expand Up @@ -494,7 +493,7 @@ SurgeStorage::SurgeStorage(std::string suppliedDataPath) : otherscene_clients(0)
oss << "Unable to load 'windows.wt'. from memory. "
<< "This is a usually fatal internal software error in Surge XT which should"
<< " never occur!";
Surge::UserInteractions::promptError(oss.str(), "Surge Resources Loading Error");
reportError(oss.str(), "Surge Resources Loading Error");
}

// Tunings Library Support
Expand Down Expand Up @@ -529,7 +528,7 @@ SurgeStorage::SurgeStorage(std::string suppliedDataPath) : otherscene_clients(0)
TiXmlElement *pdoc = TINYXML_SAFE_TO_ELEMENT(doc.FirstChild("param-doc"));
if (!pdoc)
{
Surge::UserInteractions::promptError(
reportError(
"Unknown top element in paramdocumentation.xml - not a parameter documentation "
"XML file!",
"Error");
Expand Down Expand Up @@ -778,7 +777,7 @@ void SurgeStorage::refreshPatchOrWTListAddDir(bool userDir, string subdir,
{
std::ostringstream oss;
oss << "Experienced file system error when building patches. " << e.what();
Surge::UserInteractions::promptError(oss.str(), "FileSystem Error");
reportError(oss.str(), "FileSystem Error");
}

/*
Expand Down Expand Up @@ -872,7 +871,7 @@ void SurgeStorage::refresh_wtlist()
std::ostringstream ss;
ss << "Surge was unable to load wavetables from '" << datapath
<< "'. Please reinstall Surge!";
Surge::UserInteractions::promptError(ss.str(), "Surge Installation Error");
reportError(ss.str(), "Surge Installation Error");
}

firstThirdPartyWTCategory = wt_category.size();
Expand Down Expand Up @@ -1031,7 +1030,7 @@ void SurgeStorage::load_wt(string filename, Wavetable *wt, OscillatorStorage *os
std::ostringstream oss;
oss << "Unable to load file with extension " << extension
<< "! Surge only supports .wav and .wt wavetable files!";
Surge::UserInteractions::promptError(oss.str(), "Error");
reportError(oss.str(), "Error");
}

if (osc && loaded)
Expand Down Expand Up @@ -1092,7 +1091,7 @@ bool SurgeStorage::load_wt_wt(string filename, Wavetable *wt)
<< " If you would like, please attach the wavetable which caused this message to a new "
"GitHub issue at "
<< " https://github.com/surge-synthesizer/surge/";
Surge::UserInteractions::promptError(oss.str(), "Wavetable Loading Error");
reportError(oss.str(), "Wavetable Loading Error");
}
return wasBuilt;
}
Expand Down Expand Up @@ -1145,7 +1144,7 @@ bool SurgeStorage::load_wt_wt_mem(const char *data, size_t dataSize, Wavetable *
<< " If you would like, please attach the wavetable which caused this message to a new "
"GitHub issue at "
<< " https://github.com/surge-synthesizer/surge/";
Surge::UserInteractions::promptError(oss.str(), "Wavetable Loading Error");
reportError(oss.str(), "Wavetable Loading Error");
}
return wasBuilt;
}
Expand Down Expand Up @@ -1884,7 +1883,7 @@ void SurgeStorage::rescanUserMidiMappings()
{
std::ostringstream oss;
oss << "Experienced file system error when loading MIDI settings. " << e.what();
Surge::UserInteractions::promptError(oss.str(), "FileSystem Error");
reportError(oss.str(), "FileSystem Error");
}
}

Expand All @@ -1902,8 +1901,8 @@ void SurgeStorage::loadMidiMappingByName(std::string name)
if (!sm)
{
// Invalid XML Document. Show an error?
Surge::UserInteractions::promptError(
"Unable to locate surge-midi element in XML. Not a valid MIDI mapping!", "Surge MIDI");
reportError("Unable to locate surge-midi element in XML. Not a valid MIDI mapping!",
"Surge MIDI");
return;
}

Expand Down Expand Up @@ -1995,7 +1994,7 @@ void SurgeStorage::storeMidiMappingToName(std::string name)
{
std::ostringstream oss;
oss << "Unable to save MIDI settings to '" << fn << "'!";
Surge::UserInteractions::promptError(oss.str(), "Error");
reportError(oss.str(), "Error");
}
}

Expand Down Expand Up @@ -2049,6 +2048,19 @@ void SurgeStorage::toggleTuningToCache()
}
}

void SurgeStorage::reportError(const std::string &msg, const std::string &title)
{
std::cout << "Surge Error [" << title << "]\n" << msg << std::endl;
if (errorListeners.empty())
{
std::lock_guard<std::mutex> g(preListenerErrorMutex);
preListenerErrors.emplace_back(msg, title);
}

for (auto l : errorListeners)
l->onSurgeError(msg, title);
}

namespace Surge
{
namespace Storage
Expand Down
40 changes: 39 additions & 1 deletion src/common/SurgeStorage.h
Original file line number Diff line number Diff line change
Expand Up @@ -38,6 +38,7 @@

#include "Tunings.h"
#include "PatchDB.h"
#include <unordered_set>

#if WINDOWS
#define PATH_SEPARATOR '\\'
Expand Down Expand Up @@ -867,6 +868,43 @@ class alignas(16) SurgeStorage

SurgeStorage(std::string suppliedDataPath = "");

// With XT surgestorage can now keep a cache of errors it reports to the user
void reportError(const std::string &msg, const std::string &title);
struct ErrorListener
{
// This can be called from any thread. Beware. But it is called only
// when an error occurs so if you want to be sloppy and just lock thats OK
virtual void onSurgeError(const std::string &msg, const std::string &title) = 0;
};
std::unordered_set<ErrorListener *> errorListeners;
std::mutex preListenerErrorMutex; // this mutex is ONLY locked in the error path and
// when registering a listener (from the UI thread)
std::vector<std::pair<std::string, std::string>> preListenerErrors;
void addErrorListener(ErrorListener *l)
{
errorListeners.insert(l);
std::lock_guard<std::mutex> g(preListenerErrorMutex);
for (auto p : preListenerErrors)
l->onSurgeError(p.first, p.second);
preListenerErrors.clear();
}
void removeErrorListener(ErrorListener *l) { errorListeners.erase(l); }

enum OkCancel
{
OK,
CANCEL
};
std::function<OkCancel(const std::string &msg, const std::string &title, OkCancel def)>
okCancelProvider =
[](const std::string &, const std::string &, OkCancel def) { return def; };
void clearOkCancelProvider()
{
okCancelProvider = [](const std::string &, const std::string &, OkCancel def) {
return def;
};
}

static constexpr int tuning_table_size = 512;
float table_pitch alignas(16)[tuning_table_size];
float table_pitch_inv alignas(16)[tuning_table_size];
Expand Down Expand Up @@ -920,7 +958,7 @@ class alignas(16) SurgeStorage
bool load_wt_wt_mem(const char *data, const size_t dataSize, Wavetable *wt);
// void load_wt_wav(std::string filename, Wavetable* wt);
bool load_wt_wav_portable(std::string filename, Wavetable *wt);
void export_wt_wav_portable(std::string fbase, Wavetable *wt);
std::string export_wt_wav_portable(std::string fbase, Wavetable *wt);
void clipboard_copy(int type, int scene, int entry);
void clipboard_paste(int type, int scene, int entry);
int get_clipboard_type();
Expand Down
4 changes: 2 additions & 2 deletions src/common/SurgeSynthesizer.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -3853,7 +3853,7 @@ void SurgeSynthesizer::loadFromDawExtraState()
}
catch (Tunings::TuningError &e)
{
Surge::UserInteractions::promptError(e.what(), "Unable to restore tuning!");
storage.reportError(e.what(), "Unable to restore tuning!");
storage.retuneTo12TETScale();
}
}
Expand All @@ -3879,7 +3879,7 @@ void SurgeSynthesizer::loadFromDawExtraState()
}
catch (Tunings::TuningError &e)
{
Surge::UserInteractions::promptError(e.what(), "Unable to restore mapping!");
storage.reportError(e.what(), "Unable to restore mapping!");
storage.remapToConcertCKeyboard();
}
}
Expand Down
1 change: 0 additions & 1 deletion src/common/SurgeSynthesizer.h
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,6 @@
#include "SurgeVoice.h"
#include "effect/Effect.h"
#include "BiquadFilter.h"
#include "UserInteractions.h"

struct QuadFilterChainState;

Expand Down
Loading

0 comments on commit 4ca0fa8

Please sign in to comment.