Browse Source

Projucer: Refactored module scanning code and added AvailableModuleList class for asynchronous scanning

tags/2021-05-28
ed 7 years ago
parent
commit
f77c995b4d
19 changed files with 478 additions and 408 deletions
  1. +29
    -1
      extras/Projucer/Source/Application/Windows/jucer_GlobalPathsWindowComponent.h
  2. +36
    -2
      extras/Projucer/Source/Application/jucer_Application.cpp
  3. +9
    -0
      extras/Projucer/Source/Application/jucer_Application.h
  4. +1
    -1
      extras/Projucer/Source/Application/jucer_CommandLine.cpp
  5. +6
    -6
      extras/Projucer/Source/LiveBuildEngine/jucer_CompileEngineClient.cpp
  6. +97
    -85
      extras/Projucer/Source/Project/UI/Sidebar/jucer_ModuleTreeItems.h
  7. +11
    -11
      extras/Projucer/Source/Project/UI/jucer_ModulesInformationComponent.h
  8. +106
    -202
      extras/Projucer/Source/Project/jucer_Module.cpp
  9. +41
    -27
      extras/Projucer/Source/Project/jucer_Module.h
  10. +103
    -41
      extras/Projucer/Source/Project/jucer_Project.cpp
  11. +9
    -2
      extras/Projucer/Source/Project/jucer_Project.h
  12. +1
    -1
      extras/Projucer/Source/ProjectSaving/jucer_ProjectExport_Android.h
  13. +1
    -1
      extras/Projucer/Source/ProjectSaving/jucer_ProjectExport_CodeBlocks.h
  14. +2
    -2
      extras/Projucer/Source/ProjectSaving/jucer_ProjectExport_Make.h
  15. +1
    -1
      extras/Projucer/Source/ProjectSaving/jucer_ProjectExport_Xcode.h
  16. +15
    -15
      extras/Projucer/Source/ProjectSaving/jucer_ProjectExporter.cpp
  17. +3
    -3
      extras/Projucer/Source/ProjectSaving/jucer_ProjectSaver.h
  18. +1
    -1
      extras/Projucer/Source/Utility/Helpers/jucer_TranslationHelpers.h
  19. +6
    -6
      extras/Projucer/Source/Wizards/jucer_NewProjectWizard.h

+ 29
- 1
extras/Projucer/Source/Application/Windows/jucer_GlobalPathsWindowComponent.h View File

@@ -59,6 +59,12 @@ public:
else if (os == TargetOS::windows) osSelector.setSelectedId (2);
else if (os == TargetOS::linux) osSelector.setSelectedId (3);
addChildComponent (rescanJUCEPathButton);
rescanJUCEPathButton.onClick = [] { ProjucerApplication::getApp().rescanJUCEPathModules(); };
addChildComponent (rescanUserPathButton);
rescanUserPathButton.onClick = [] { ProjucerApplication::getApp().rescanUserPathModules(); };
updateFilePathPropertyComponents();
}
@@ -85,6 +91,7 @@ public:
int labelIndex = 0;
bool isFirst = true;
bool showRescanButtons = (rescanJUCEPathButton.isVisible() && rescanUserPathButton.isVisible());
for (auto* pathComp : pathPropertyComponents)
{
@@ -99,7 +106,20 @@ public:
if (isFirst)
b.removeFromTop (20);
pathComp->setBounds (b.removeFromTop (pathComp->getPreferredHeight()));
auto compBounds = b.removeFromTop (pathComp->getPreferredHeight());
if (showRescanButtons)
{
auto propName = pathComp->getName();
if (propName == "JUCE Modules")
rescanJUCEPathButton.setBounds (compBounds.removeFromRight (75).reduced (5, 0));
else if (propName == "User Modules")
rescanUserPathButton.setBounds (compBounds.removeFromRight (75).reduced (5, 0));
}
pathComp->setBounds (compBounds);
b.removeFromTop (5);
}
@@ -124,6 +144,8 @@ public:
private:
OwnedArray<Label> pathPropertyLabels;
OwnedArray<PropertyComponent> pathPropertyComponents;
TextButton rescanJUCEPathButton { "Re-scan" },
rescanUserPathButton { "Re-scan" };
ComboBox osSelector;
InfoButton info;
@@ -228,6 +250,9 @@ private:
addAndMakeVisible (pathPropertyComponents.add (new FilePathPropertyComponent (settings.getStoredPath (Ids::androidStudioExePath),
"Android Studio " + exeLabel, false)));
rescanJUCEPathButton.setVisible (true);
rescanUserPathButton.setVisible (true);
}
else
{
@@ -267,6 +292,9 @@ private:
addAndMakeVisible (pathPropertyComponents.add (new TextPropertyComponent (settings.getFallbackPathForOS (Ids::vst3Path, selectedOS),
"Custom VST3 SDK", maxChars, false)));
rescanJUCEPathButton.setVisible (false);
rescanUserPathButton.setVisible (false);
}
resized();


+ 36
- 2
extras/Projucer/Source/Application/jucer_Application.cpp View File

@@ -81,11 +81,11 @@ void ProjucerApplication::initialise (const String& commandLine)
+ "MHz Cores: " + String (SystemStats::getNumCpus())
+ " " + String (SystemStats::getMemorySizeInMegabytes()) + "MB");
initialiseBasics();
isRunningCommandLine = commandLine.isNotEmpty()
&& ! commandLine.startsWith ("-NSDocumentRevisionsDebugMode");
initialiseBasics();
licenseController.reset (new LicenseController);
licenseController->addLicenseStatusChangedCallback (this);
@@ -136,6 +136,9 @@ void ProjucerApplication::initialiseBasics()
ImageCache::setCacheTimeout (30 * 1000);
icons.reset (new Icons());
tooltipWindow.setMillisecondsBeforeTipAppears (1200);
rescanJUCEPathModules();
rescanUserPathModules();
}
bool ProjucerApplication::initialiseLogger (const char* filePrefix)
@@ -1415,6 +1418,37 @@ void ProjucerApplication::showSetJUCEPathAlert()
}
void ProjucerApplication::rescanJUCEPathModules()
{
File jucePath (getAppSettings().getStoredPath (Ids::defaultJuceModulePath).toString());
if (isRunningCommandLine)
jucePathModuleList.scanPaths ({ jucePath });
else
jucePathModuleList.scanPathsAsync ({ jucePath });
}
static Array<File> getSanitisedUserModulePaths()
{
Array<File> paths;
for (auto p : StringArray::fromTokens (getAppSettings().getStoredPath (Ids::defaultUserModulePath).toString(), ";", {}))
{
p = p.replace ("~", File::getSpecialLocation (File::userHomeDirectory).getFullPathName());
paths.add (File::createFileWithoutCheckingPath (p.trim()));
}
return paths;
}
void ProjucerApplication::rescanUserPathModules()
{
if (isRunningCommandLine)
userPathsModuleList.scanPaths (getSanitisedUserModulePaths());
else
userPathsModuleList.scanPathsAsync (getSanitisedUserModulePaths());
}
void ProjucerApplication::selectEditorColourSchemeWithName (const String& schemeName)
{
auto& appearanceSettings = getAppSettings().appearance;


+ 9
- 0
extras/Projucer/Source/Application/jucer_Application.h View File

@@ -139,6 +139,13 @@ public:
//==============================================================================
void setAnalyticsEnabled (bool);
//==============================================================================
void rescanJUCEPathModules();
void rescanUserPathModules();
AvailableModuleList& getJUCEPathModuleList() { return jucePathModuleList; }
AvailableModuleList& getUserPathsModuleList() { return userPathsModuleList; }
//==============================================================================
ProjucerLookAndFeel lookAndFeel;
@@ -204,6 +211,8 @@ private:
void showSetJUCEPathAlert();
std::unique_ptr<AlertWindow> pathAlert;
AvailableModuleList jucePathModuleList, userPathsModuleList;
//==============================================================================
void setColourScheme (int index, bool saveSetting);


+ 1
- 1
extras/Projucer/Source/Application/jucer_CommandLine.cpp View File

@@ -206,7 +206,7 @@ namespace
<< "Name: " << proj.project->getProjectNameString() << std::endl
<< "UID: " << proj.project->getProjectUIDString() << std::endl;
EnabledModuleList& modules = proj.project->getModules();
EnabledModuleList& modules = proj.project->getEnabledModules();
if (int numModules = modules.getNumModules())
{


+ 6
- 6
extras/Projucer/Source/LiveBuildEngine/jucer_CompileEngineClient.cpp View File

@@ -370,13 +370,13 @@ private:
scanProjectItem (proj.getMainGroup(), compileUnits, userFiles);
{
auto isVSTHost = project.getModules().isModuleEnabled ("juce_audio_processors")
auto isVSTHost = project.getEnabledModules().isModuleEnabled ("juce_audio_processors")
&& (project.isConfigFlagEnabled ("JUCE_PLUGINHOST_VST3") || project.isConfigFlagEnabled ("JUCE_PLUGINHOST_VST"));
auto isPluginProject = proj.getProjectType().isAudioPlugin();
OwnedArray<LibraryModule> modules;
proj.getModules().createRequiredModules (modules);
proj.getEnabledModules().createRequiredModules (modules);
for (Project::ExporterIterator exporter (proj); exporter.next();)
{
@@ -384,7 +384,7 @@ private:
{
for (auto* m : modules)
{
auto localModuleFolder = proj.getModules().shouldCopyModuleFilesLocally (m->moduleInfo.getID()).getValue()
auto localModuleFolder = proj.getEnabledModules().shouldCopyModuleFilesLocally (m->moduleInfo.getID()).getValue()
? proj.getLocalModuleFolder (m->moduleInfo.getID())
: m->moduleInfo.getFolder();
@@ -435,7 +435,7 @@ private:
static bool areAnyModulesMissing (Project& project)
{
OwnedArray<LibraryModule> modules;
project.getModules().createRequiredModules (modules);
project.getEnabledModules().createRequiredModules (modules);
for (auto* module : modules)
if (! module->getFolder().isDirectory())
@@ -458,7 +458,7 @@ private:
StringArray paths;
paths.addArray (getSearchPathsFromString (project.getCompileEngineSettings().getSystemHeaderPathString()));
auto isVSTHost = project.getModules().isModuleEnabled ("juce_audio_processors")
auto isVSTHost = project.getEnabledModules().isModuleEnabled ("juce_audio_processors")
&& (project.isConfigFlagEnabled ("JUCE_PLUGINHOST_VST3")
|| project.isConfigFlagEnabled ("JUCE_PLUGINHOST_VST"));
@@ -468,7 +468,7 @@ private:
paths.add (customVst3Path);
OwnedArray<LibraryModule> modules;
project.getModules().createRequiredModules (modules);
project.getEnabledModules().createRequiredModules (modules);
for (auto* module : modules)
{


+ 97
- 85
extras/Projucer/Source/Project/UI/Sidebar/jucer_ModuleTreeItems.h View File

@@ -34,10 +34,10 @@ public:
ModuleItem (Project& p, const String& modID)
: project (p), moduleID (modID)
{
missingDependencies = project.getModules().getExtraDependenciesNeeded (moduleID).size() > 0;
cppStandardHigherThanProject = project.getModules().doesModuleHaveHigherCppStandardThanProject (moduleID);
missingDependencies = project.getEnabledModules().getExtraDependenciesNeeded (moduleID).size() > 0;
cppStandardHigherThanProject = project.getEnabledModules().doesModuleHaveHigherCppStandardThanProject (moduleID);
moduleInfo = project.getModules().getModuleInfo (moduleID);
moduleInfo = project.getEnabledModules().getModuleInfo (moduleID);
}
bool canBeSelected() const override { return true; }
@@ -57,7 +57,7 @@ public:
void deleteItem() override
{
closeSettingsPage();
project.getModules().removeModule (moduleID);
project.getEnabledModules().removeModule (moduleID);
}
Icon getIcon() const override
@@ -101,7 +101,7 @@ public:
bool checkCppStandard()
{
auto oldVal = cppStandardHigherThanProject;
cppStandardHigherThanProject = project.getModules().doesModuleHaveHigherCppStandardThanProject (moduleID);
cppStandardHigherThanProject = project.getEnabledModules().doesModuleHaveHigherCppStandardThanProject (moduleID);
if (oldVal != cppStandardHigherThanProject)
return true;
@@ -137,7 +137,7 @@ private:
{
public:
ModuleSettingsPanel (Project& p, const String& modID, TreeView* tree)
: group (p.getModules().getModuleInfo (modID).getID(),
: group (p.getEnabledModules().getModuleInfo (modID).getID(),
Icon (getIcons().singleModule, Colours::transparentBlack)),
project (p),
modulesTree (tree),
@@ -149,7 +149,7 @@ private:
void refresh()
{
auto& modules = project.getModules();
auto& modules = project.getEnabledModules();
setEnabled (modules.isModuleEnabled (moduleID));
@@ -284,7 +284,7 @@ private:
void refresh() override
{
info = project.getModules().getModuleInfo (moduleID);
info = project.getEnabledModules().getModuleInfo (moduleID);
repaint();
}
@@ -337,7 +337,7 @@ private:
MissingDependenciesComponent (Project& p, const String& modID)
: PropertyComponent ("Dependencies", 100),
project (p), moduleID (modID),
missingDependencies (project.getModules().getExtraDependenciesNeeded (modID))
missingDependencies (project.getEnabledModules().getExtraDependenciesNeeded (modID))
{
addAndMakeVisible (fixButton);
fixButton.setColour (TextButton::buttonColourId, Colours::red);
@@ -359,28 +359,14 @@ private:
void fixDependencies()
{
ModuleList list;
list.scanGlobalJuceModulePath();
if (! tryToFix (list))
if (! tryToFix())
{
list.scanGlobalUserModulePath();
AlertWindow::showMessageBoxAsync (AlertWindow::WarningIcon,
"Adding Missing Dependencies",
"Couldn't locate some of these modules - you'll need to find their "
"folders manually and add them to the list.");
if (! tryToFix (list))
{
list.scanProjectExporterModulePaths (project);
if (! tryToFix (list))
{
AlertWindow::showMessageBoxAsync (AlertWindow::WarningIcon,
"Adding Missing Dependencies",
"Couldn't locate some of these modules - you'll need to find their "
"folders manually and add them to the list.");
return;
}
}
return;
}
refreshAndReselectItem();
@@ -397,18 +383,21 @@ private:
StringArray missingDependencies;
TextButton fixButton { "Add Required Modules" };
bool tryToFix (ModuleList& list)
bool tryToFix()
{
auto& modules = project.getModules();
auto copyLocally = modules.areMostModulesCopiedLocally();
auto useGlobalPath = modules.areMostModulesUsingGlobalPath();
auto& enabledModules = project.getEnabledModules();
auto copyLocally = enabledModules.areMostModulesCopiedLocally();
auto useGlobalPath = enabledModules.areMostModulesUsingGlobalPath();
StringArray missing;
for (auto missingModule : missingDependencies)
{
if (auto* info = list.getModuleWithID (missingModule))
modules.addModule (info->moduleFolder, copyLocally, useGlobalPath, false);
auto mod = project.getModuleWithID (missingModule);
if (mod.second != File())
enabledModules.addModule (mod.second, copyLocally, useGlobalPath, false);
else
missing.add (missingModule);
}
@@ -477,22 +466,28 @@ private:
//==============================================================================
class EnabledModulesItem : public ProjectTreeItemBase,
private Value::Listener,
private Timer
private AvailableModuleList::Listener
{
public:
EnabledModulesItem (Project& p)
: project (p),
moduleListTree (p.getModules().state)
moduleListTree (p.getEnabledModules().state)
{
moduleListTree.addListener (this);
projectCppStandardValue.referTo (project.getProjectValue (Ids::cppLanguageStandard));
defaultJuceModulePathValue.referTo (getAppSettings().getStoredPath (Ids::defaultJuceModulePath));
defaultUserModulePathValue.referTo (getAppSettings().getStoredPath (Ids::defaultUserModulePath));
projectCppStandardValue.addListener (this);
defaultJuceModulePathValue.addListener (this);
defaultUserModulePathValue.addListener (this);
ProjucerApplication::getApp().getJUCEPathModuleList().addListener (this);
ProjucerApplication::getApp().getUserPathsModuleList().addListener (this);
project.getExporterPathsModuleList().addListener (this);
}
~EnabledModulesItem()
{
ProjucerApplication::getApp().getJUCEPathModuleList().removeListener (this);
ProjucerApplication::getApp().getUserPathsModuleList().removeListener (this);
project.getExporterPathsModuleList().removeListener (this);
}
int getItemHeight() const override { return 22; }
@@ -542,51 +537,63 @@ public:
}
for (int i = 0; i < modules.size(); ++i)
project.getModules().addModule (modules.getReference(i).moduleFolder,
project.getModules().areMostModulesCopiedLocally(),
project.getModules().areMostModulesUsingGlobalPath(),
project.getEnabledModules().addModule (modules.getReference(i).moduleFolder,
project.getEnabledModules().areMostModulesCopiedLocally(),
project.getEnabledModules().areMostModulesUsingGlobalPath(),
true);
}
void addSubItems() override
{
for (int i = 0; i < project.getModules().getNumModules(); ++i)
addSubItem (new ModuleItem (project, project.getModules().getModuleID (i)));
for (int i = 0; i < project.getEnabledModules().getNumModules(); ++i)
addSubItem (new ModuleItem (project, project.getEnabledModules().getModuleID (i)));
}
void showPopupMenu() override
{
auto& modules = project.getModules();
PopupMenu knownModules, jucePathModules, userPathModules, exporterPathsModules;
auto& enabledModules = project.getEnabledModules();
PopupMenu allModules;
ModuleList list;
int index = 100;
list.scanGlobalJuceModulePath();
// JUCE path
PopupMenu jucePathModules;
int index = 100;
for (auto m : list.getIDs())
jucePathModules.addItem (index++, m, ! modules.isModuleEnabled (m));
for (auto& mod : ProjucerApplication::getApp().getJUCEPathModuleList().getAllModules())
jucePathModules.addItem (index++, mod.first, ! enabledModules.isModuleEnabled (mod.first));
knownModules.addSubMenu ("Global JUCE modules path", jucePathModules);
jucePathModules.addSeparator();
jucePathModules.addItem (-1, "Re-scan path");
list.scanGlobalUserModulePath();
allModules.addSubMenu ("Global JUCE modules path", jucePathModules);
// User path
index = 200;
for (auto m : list.getIDs())
userPathModules.addItem (index++, m, ! modules.isModuleEnabled (m));
PopupMenu userPathModules;
knownModules.addSubMenu ("Global user modules path", userPathModules);
for (auto& mod : ProjucerApplication::getApp().getUserPathsModuleList().getAllModules())
userPathModules.addItem (index++, mod.first, ! enabledModules.isModuleEnabled (mod.first));
list.scanProjectExporterModulePaths (project);
userPathModules.addSeparator();
userPathModules.addItem (-2, "Re-scan path");
allModules.addSubMenu ("Global user modules path", userPathModules);
// Exporter path
index = 300;
for (auto m : list.getIDs())
exporterPathsModules.addItem (index++, m, ! modules.isModuleEnabled (m));
PopupMenu exporterPathModules;
for (auto& mod : project.getExporterPathsModuleList().getAllModules())
exporterPathModules.addItem (index++, mod.first, ! enabledModules.isModuleEnabled (mod.first));
knownModules.addSubMenu ("Exporter paths", exporterPathsModules);
exporterPathModules.addSeparator();
exporterPathModules.addItem (-3, "Re-scan path");
allModules.addSubMenu ("Exporter paths", exporterPathModules);
PopupMenu menu;
menu.addSubMenu ("Add a module", knownModules);
menu.addSubMenu ("Add a module", allModules);
menu.addSeparator();
menu.addItem (1001, "Add a module from a specified folder...");
@@ -595,35 +602,39 @@ public:
void handlePopupMenuResult (int resultCode) override
{
auto& modules = project.getModules();
if (resultCode == 1001)
{
modules.addModuleFromUserSelectedFile();
project.getEnabledModules().addModuleFromUserSelectedFile();
}
else if (resultCode < 0)
{
if (resultCode == -1) ProjucerApplication::getApp().rescanJUCEPathModules();
else if (resultCode == -2) ProjucerApplication::getApp().rescanUserPathModules();
else if (resultCode == -3) project.rescanExporterPathModules();
}
else if (resultCode > 0)
{
ModuleList list;
std::vector<ModuleIDAndFolder> list;
int offset = -1;
if (resultCode < 200)
{
list.scanGlobalJuceModulePath();
list = ProjucerApplication::getApp().getJUCEPathModuleList().getAllModules();
offset = 100;
}
else if (resultCode < 300)
{
list.scanGlobalUserModulePath();
list = ProjucerApplication::getApp().getUserPathsModuleList().getAllModules();
offset = 200;
}
else if (resultCode < 400)
{
list.scanProjectExporterModulePaths (project);
list = project.getExporterPathsModuleList().getAllModules();
offset = 300;
}
if (offset != -1)
modules.addModuleInteractive (list.getIDs() [resultCode - offset]);
project.getEnabledModules().addModuleInteractive (list[(size_t) (resultCode - offset)].first);
}
}
@@ -641,7 +652,7 @@ public:
private:
Project& project;
ValueTree moduleListTree;
Value projectCppStandardValue, defaultJuceModulePathValue, defaultUserModulePathValue;
Value projectCppStandardValue;
//==============================================================================
void valueChanged (Value& v) override
@@ -660,25 +671,26 @@ private:
}
}
}
else if (v == defaultJuceModulePathValue || v == defaultUserModulePathValue)
{
auto juceModulePathChanged = (v == defaultJuceModulePathValue);
}
for (int i = 0; i < getNumSubItems(); ++i)
if (auto* moduleItem = dynamic_cast<ModuleItem*> (getSubItem (i)))
moduleItem->refreshModuleInfoIfCurrentlyShowing (juceModulePathChanged);
void removeDuplicateModules()
{
auto jucePathModuleList = ProjucerApplication::getApp().getJUCEPathModuleList().getAllModules();
// coalesce changes using a timer in case the value is changing rapidly
startTimer (750);
}
auto& userPathModules = ProjucerApplication::getApp().getUserPathsModuleList();
userPathModules.removeDuplicates (jucePathModuleList);
auto& exporterPathModules = project.getExporterPathsModuleList();
exporterPathModules.removeDuplicates (jucePathModuleList);
exporterPathModules.removeDuplicates (userPathModules.getAllModules());
}
//==============================================================================
void timerCallback() override
void availableModulesChanged() override
{
stopTimer();
removeDuplicateModules();
refreshSubItems();
}
//==============================================================================
JUCE_DECLARE_NON_COPYABLE_WITH_LEAK_DETECTOR (EnabledModulesItem)
};

+ 11
- 11
extras/Projucer/Source/Project/UI/jucer_ModulesInformationComponent.h View File

@@ -35,7 +35,7 @@ class ModulesInformationComponent : public Component,
public:
ModulesInformationComponent (Project& p)
: project (p),
modulesValueTree (p.getModules().state)
modulesValueTree (p.getEnabledModules().state)
{
listHeader = new ListBoxHeader ( { "Module", "Version", "Make Local Copy", "Paths" },
{ 0.25f, 0.2f, 0.2f, 0.35f } );
@@ -106,7 +106,7 @@ public:
int getNumRows() override
{
return project.getModules().getNumModules();
return project.getEnabledModules().getNumModules();
}
void paintListBoxItem (int rowNumber, Graphics& g, int width, int height, bool rowIsSelected) override
@@ -123,26 +123,26 @@ public:
g.setColour (rowIsSelected ? findColour (defaultHighlightedTextColourId) : findColour (widgetTextColourId));
//======================================================================
auto moduleID = project.getModules().getModuleID (rowNumber);
auto moduleID = project.getEnabledModules().getModuleID (rowNumber);
g.drawFittedText (moduleID, bounds.removeFromLeft (roundToInt (listHeader->getProportionAtIndex (0) * width)), Justification::centredLeft, 1);
//======================================================================
auto version = project.getModules().getModuleInfo (moduleID).getVersion();
auto version = project.getEnabledModules().getModuleInfo (moduleID).getVersion();
if (version.isEmpty())
version = "?";
g.drawFittedText (version, bounds.removeFromLeft (roundToInt (listHeader->getProportionAtIndex (1) * width)), Justification::centredLeft, 1);
//======================================================================
auto copyLocally = project.getModules().shouldCopyModuleFilesLocally (moduleID).getValue() ? "Yes" : "No";
auto copyLocally = project.getEnabledModules().shouldCopyModuleFilesLocally (moduleID).getValue() ? "Yes" : "No";
g.drawFittedText (copyLocally, bounds.removeFromLeft (roundToInt (listHeader->getProportionAtIndex (2) * width)), Justification::centredLeft, 1);
//======================================================================
String pathText;
if (project.getModules().shouldUseGlobalPath (moduleID))
if (project.getEnabledModules().shouldUseGlobalPath (moduleID))
{
pathText = "Global";
}
@@ -161,7 +161,7 @@ public:
void listBoxItemDoubleClicked (int row, const MouseEvent&) override
{
auto moduleID = project.getModules().getModuleID (row);
auto moduleID = project.getEnabledModules().getModuleID (row);
if (moduleID.isNotEmpty())
if (auto* pcc = findParentComponentOfClass<ProjectContentComponent>())
@@ -170,7 +170,7 @@ public:
void deleteKeyPressed (int row) override
{
project.getModules().removeModule (project.getModules().getModuleID (row));
project.getEnabledModules().removeModule (project.getEnabledModules().getModuleID (row));
}
void lookAndFeelChanged() override
@@ -224,7 +224,7 @@ private:
auto res = m.showAt (&setCopyModeButton);
if (res != 0)
project.getModules().setLocalCopyModeForAllModules (res == 1);
project.getEnabledModules().setLocalCopyModeForAllModules (res == 1);
}
void showGlobalPathsMenu()
@@ -243,7 +243,7 @@ private:
{
auto enableGlobalPaths = (res % 2 == 1);
auto& moduleList = project.getModules();
auto& moduleList = project.getEnabledModules();
if (res < 3)
{
@@ -271,7 +271,7 @@ private:
pastePathsID
};
auto& moduleList = project.getModules();
auto& moduleList = project.getEnabledModules();
auto moduleToCopy = moduleList.getModuleID (list.getSelectedRow());
if (moduleToCopy.isNotEmpty())


+ 106
- 202
extras/Projucer/Source/Project/jucer_Module.cpp View File

@@ -25,10 +25,9 @@
*/
#include "../Application/jucer_Headers.h"
#include "jucer_Module.h"
#include "../ProjectSaving/jucer_ProjectSaver.h"
#include "../ProjectSaving/jucer_ProjectExport_Xcode.h"
#include "../Application/jucer_ProjucerAnalytics.h"
#include "../Application/jucer_Application.h"
//==============================================================================
static var parseModuleDesc (const StringArray& lines)
@@ -113,195 +112,154 @@ StringArray ModuleDescription::getDependencies() const
}
//==============================================================================
ModuleList::ModuleList()
{
}
ModuleList::ModuleList (const ModuleList& other)
{
operator= (other);
}
ModuleList& ModuleList::operator= (const ModuleList& other)
{
modules.clear();
modules.addCopiesOf (other.modules);
return *this;
}
const ModuleDescription* ModuleList::getModuleWithID (const String& moduleID) const
{
for (auto* m : modules)
if (m->getID() == moduleID)
return m;
return nullptr;
}
void ModuleList::sort()
{
std::sort (modules.begin(), modules.end(), [] (const ModuleDescription* m1, const ModuleDescription* m2)
{
return m1->getID().compareIgnoreCase (m2->getID()) < 0;
});
}
StringArray ModuleList::getIDs() const
{
StringArray results;
for (auto* m : modules)
results.add (m->getID());
results.sort (true);
return results;
}
bool ModuleList::tryToAddModuleFromFolder (const File& path)
static bool tryToAddModuleFromFolder (const File& path, ModuleIDAndFolderList& list)
{
ModuleDescription m (path);
if (m.isValid())
{
getPreviousModuleDirectories().addIfNotAlreadyThere (path.getParentDirectory());
modules.add (new ModuleDescription (m));
list.push_back ({ m.getID(), path });
return true;
}
return false;
}
void ModuleList::addAllModulesInFolder (const File& path)
static bool addAllModulesInSubfoldersRecursively (const File& path, int depth, ModuleIDAndFolderList& list)
{
if (! tryToAddModuleFromFolder (path))
if (depth > 0)
{
for (DirectoryIterator iter (path, false, "*", File::findDirectories); iter.next();)
tryToAddModuleFromFolder (iter.getFile().getLinkedTarget());
}
}
{
if (auto* job = ThreadPoolJob::getCurrentThreadPoolJob())
if (job->shouldExit())
return false;
Array<File>& ModuleList::getPreviousModuleDirectories()
{
static Array<File> previous;
return previous;
}
auto childPath = iter.getFile().getLinkedTarget();
File ModuleList::tryToFindModulePathFromPrevious (const String& id)
{
for (auto& f : getPreviousModuleDirectories())
{
auto modulePath = f.getChildFile (id);
if (ModuleDescription (modulePath).isValid())
return modulePath;
if (! tryToAddModuleFromFolder (childPath, list))
if (! addAllModulesInSubfoldersRecursively (childPath, depth - 1, list))
return false;
}
}
return {};
return true;
}
//==============================================================================
static File getModuleFolderFromPathIfItExists (const String& path, const String& moduleID)
static bool addAllModulesInFolder (const File& path, ModuleIDAndFolderList& list)
{
if (path.isNotEmpty())
{
ModuleList list;
list.addAllModulesInFolder (path);
bool exitedBeforeCompletion = false;
if (auto* desc = list.getModuleWithID (moduleID))
return desc->getFolder();
if (! tryToAddModuleFromFolder (path, list))
{
int subfolders = 3;
exitedBeforeCompletion = addAllModulesInSubfoldersRecursively (path, subfolders, list);
}
return {};
return exitedBeforeCompletion;
}
static Array<File> getAllPossibleModulePathsFromExporters (Project& project, bool onlyThisOS)
static void sort (ModuleIDAndFolderList& listToSort)
{
StringArray paths;
std::sort (listToSort.begin(), listToSort.end(), [] (const ModuleIDAndFolder& m1, const ModuleIDAndFolder& m2)
{
return m1.first.compareIgnoreCase (m2.first) < 0;
});
}
for (Project::ExporterIterator exporter (project); exporter.next();)
//==============================================================================
struct ModuleScannerJob : public ThreadPoolJob
{
ModuleScannerJob (const Array<File>& paths, std::function<void (const ModuleIDAndFolderList&)>&& callback)
: ThreadPoolJob ("ModuleScannerJob"),
pathsToScan (paths),
completionCallback (std::move (callback))
{
if (onlyThisOS && ! exporter->mayCompileOnCurrentOS())
continue;
auto& modules = project.getModules();
auto n = modules.getNumModules();
for (int i = 0; i < n; ++i)
{
auto id = modules.getModuleID (i);
}
if (modules.shouldUseGlobalPath (id))
continue;
JobStatus runJob() override
{
ModuleIDAndFolderList list;
auto path = exporter->getPathForModuleString (id);
for (auto& p : pathsToScan)
if (! addAllModulesInFolder (p, list))
return jobNeedsRunningAgain;
if (path.isNotEmpty())
paths.addIfNotAlreadyThere (path);
}
sort (list);
completionCallback (list);
auto oldPath = exporter->getLegacyModulePath();
if (oldPath.isNotEmpty())
paths.addIfNotAlreadyThere (oldPath);
return jobHasFinished;
}
Array<File> files;
Array<File> pathsToScan;
std::function<void (const ModuleIDAndFolderList&)> completionCallback;
};
for (auto& path : paths)
{
auto f = project.resolveFilename (path);
AvailableModuleList::AvailableModuleList()
{
}
if (f.isDirectory())
{
files.addIfNotAlreadyThere (f);
ThreadPoolJob* AvailableModuleList::createScannerJob (const Array<File>& paths)
{
return new ModuleScannerJob (paths, [this] (ModuleIDAndFolderList scannedModuleList)
{
{
const ScopedLock swapLock (lock);
moduleList.swap (scannedModuleList);
}
if (f.getChildFile ("modules").isDirectory())
files.addIfNotAlreadyThere (f.getChildFile ("modules"));
}
}
MessageManager::callAsync ([this] { listeners.call ([] (Listener& l) { l.availableModulesChanged(); }); });
});
}
return files;
void AvailableModuleList::removePendingAndAddJob (ThreadPoolJob* jobToAdd)
{
scanPool.removeAllJobs (false, 100);
scanPool.addJob (jobToAdd, true);
}
void ModuleList::scanProjectExporterModulePaths (Project& project)
void AvailableModuleList::scanPaths (const Array<File>& paths)
{
modules.clear();
auto* job = createScannerJob (paths);
for (auto& m : getAllPossibleModulePathsFromExporters (project, false))
addAllModulesInFolder (m);
removePendingAndAddJob (job);
scanPool.waitForJobToFinish (job, -1);
}
sort();
void AvailableModuleList::scanPathsAsync (const Array<File>& paths)
{
removePendingAndAddJob (createScannerJob (paths));
}
void ModuleList::scanGlobalJuceModulePath()
ModuleIDAndFolderList AvailableModuleList::getAllModules() const
{
modules.clear();
const ScopedLock readLock (lock);
auto& settings = getAppSettings();
return moduleList;
}
auto path = settings.getStoredPath (Ids::defaultJuceModulePath).toString();
ModuleIDAndFolder AvailableModuleList::getModuleWithID (const String& id) const
{
const ScopedLock readLock (lock);
if (path.isNotEmpty())
addAllModulesInFolder ({ path });
for (auto& mod : moduleList)
if (mod.first == id)
return mod;
sort();
return {};
}
void ModuleList::scanGlobalUserModulePath()
void AvailableModuleList::removeDuplicates (const ModuleIDAndFolderList& other)
{
modules.clear();
const ScopedLock readLock (lock);
auto paths = StringArray::fromTokens (getAppSettings().getStoredPath (Ids::defaultUserModulePath).toString(), ";", {});
for (auto p : paths)
for (auto& m : other)
{
p = p.replace ("~", File::getSpecialLocation (File::userHomeDirectory).getFullPathName());
auto pos = std::find (moduleList.begin(), moduleList.end(), m);
auto f = File::createFileWithoutCheckingPath (p.trim());
if (f.exists())
addAllModulesInFolder (f);
if (pos != moduleList.end())
moduleList.erase (pos);
}
sort();
}
//==============================================================================
@@ -314,7 +272,7 @@ LibraryModule::LibraryModule (const ModuleDescription& d)
void LibraryModule::writeIncludes (ProjectSaver& projectSaver, OutputStream& out)
{
auto& project = projectSaver.project;
auto& modules = project.getModules();
auto& modules = project.getEnabledModules();
auto id = getID();
@@ -382,7 +340,7 @@ void LibraryModule::addSettingsForModuleToExporter (ProjectExporter& exporter, P
{
Array<File> compiled;
auto& modules = project.getModules();
auto& modules = project.getEnabledModules();
auto id = getID();
auto localModuleFolder = modules.shouldCopyModuleFilesLocally (id).getValue() ? project.getLocalModuleFolder (id)
@@ -649,7 +607,7 @@ EnabledModuleList::EnabledModuleList (Project& p, const ValueTree& s)
ModuleDescription EnabledModuleList::getModuleInfo (const String& moduleID)
{
return ModuleDescription (findFolderForModule (moduleID));
return ModuleDescription (project.getModuleWithID (moduleID).second);
}
bool EnabledModuleList::isModuleEnabled (const String& moduleID) const
@@ -681,48 +639,6 @@ Value EnabledModuleList::shouldShowAllModuleFilesInProject (const String& module
.getPropertyAsValue (Ids::showAllCode, getUndoManager());
}
File EnabledModuleList::findFolderForModule (const String& moduleID)
{
if (shouldUseGlobalPath (moduleID))
{
if (isJUCEModule (moduleID))
return File (getAppSettings().getStoredPath (Ids::defaultJuceModulePath).toString()).getChildFile (moduleID);
{
auto previous = ModuleList::tryToFindModulePathFromPrevious (moduleID);
if (previous != File())
return previous;
}
ModuleList list;
list.scanGlobalUserModulePath();
if (auto* desc = list.getModuleWithID (moduleID))
return desc->getFolder();
}
else
{
for (auto p : getAllPossibleModulePathsFromExporters (project, true))
{
auto f = getModuleFolderFromPathIfItExists (p.getFullPathName(), moduleID);
if (f != File())
return f;
}
for (auto p : getAllPossibleModulePathsFromExporters (project, false))
{
auto f = getModuleFolderFromPathIfItExists (p.getFullPathName(), moduleID);
if (f != File())
return f;
}
}
return {};
}
struct ModuleTreeSorter
{
static int compareElements (const ValueTree& m1, const ValueTree& m2)
@@ -754,7 +670,7 @@ void EnabledModuleList::addModule (const File& moduleFolder, bool copyLocally, b
if (! isModuleEnabled (moduleID))
{
ValueTree module (Ids::MODULE);
module.setProperty (Ids::ID, moduleID, nullptr);
module.setProperty (Ids::ID, moduleID, getUndoManager());
state.appendChild (module, getUndoManager());
sortAlphabetically();
@@ -769,6 +685,9 @@ void EnabledModuleList::addModule (const File& moduleFolder, bool copyLocally, b
for (Project::ExporterIterator exporter (project); exporter.next();)
exporter->getPathForModuleValue (moduleID) = path.toUnixStyle();
if (! useGlobalPath)
project.rescanExporterPathModules (false);
if (sendAnalyticsEvent)
{
StringPairArray data;
@@ -808,7 +727,7 @@ StringArray EnabledModuleList::getAllModules() const
static void getDependencies (Project& project, const String& moduleID, StringArray& dependencies)
{
auto info = project.getModules().getModuleInfo (moduleID);
auto info = project.getEnabledModules().getModuleInfo (moduleID);
for (auto uid : info.getDependencies())
{
@@ -877,7 +796,7 @@ bool EnabledModuleList::areMostModulesCopiedLocally() const
void EnabledModuleList::setLocalCopyModeForAllModules (bool copyLocally)
{
for (auto i = getNumModules(); --i >= 0;)
shouldCopyModuleFilesLocally (project.getModules().getModuleID (i)) = copyLocally;
shouldCopyModuleFilesLocally (project.getEnabledModules().getModuleID (i)) = copyLocally;
}
File EnabledModuleList::findDefaultModulesFolder (Project& project)
@@ -887,12 +806,9 @@ File EnabledModuleList::findDefaultModulesFolder (Project& project)
if (globalPath != File())
return globalPath;
ModuleList available;
available.scanProjectExporterModulePaths (project);
for (auto i = available.modules.size(); --i >= 0;)
for (auto& exporterPathModule : project.getExporterPathsModuleList().getAllModules())
{
auto f = available.modules.getUnchecked(i)->getFolder();
auto f = exporterPathModule.second;
if (f.isDirectory())
return f.getParentDirectory();
@@ -916,27 +832,15 @@ void EnabledModuleList::addModuleFromUserSelectedFile()
void EnabledModuleList::addModuleInteractive (const String& moduleID)
{
ModuleList list;
auto f = project.getModuleWithID (moduleID).second;
list.scanGlobalJuceModulePath();
if (auto* info = list.getModuleWithID (moduleID))
if (f != File())
{
addModule (info->moduleFolder, areMostModulesCopiedLocally(), areMostModulesUsingGlobalPath(), true);
addModule (f, areMostModulesCopiedLocally(), areMostModulesUsingGlobalPath(), true);
return;
}
list.scanGlobalUserModulePath();
if (auto* info = list.getModuleWithID (moduleID))
{
addModule (info->moduleFolder, areMostModulesCopiedLocally(), areMostModulesUsingGlobalPath(), true);
return;
}
list.scanProjectExporterModulePaths (project);
if (auto* info = list.getModuleWithID (moduleID))
addModule (info->moduleFolder, areMostModulesCopiedLocally(), false, true);
else
addModuleFromUserSelectedFile();
addModuleFromUserSelectedFile();
}
void EnabledModuleList::addModuleOfferingToCopy (const File& f, bool isFromUserSpecifiedFolder)


+ 41
- 27
extras/Projucer/Source/Project/jucer_Module.h View File

@@ -64,31 +64,6 @@ struct ModuleDescription
URL url;
};
//==============================================================================
struct ModuleList
{
ModuleList();
ModuleList (const ModuleList&);
ModuleList& operator= (const ModuleList&);
const ModuleDescription* getModuleWithID (const String& moduleID) const;
StringArray getIDs() const;
void sort();
bool tryToAddModuleFromFolder (const File&);
void addAllModulesInFolder (const File&);
static Array<File>& getPreviousModuleDirectories();
static File tryToFindModulePathFromPrevious (const String&);
void scanProjectExporterModulePaths (Project&);
void scanGlobalJuceModulePath();
void scanGlobalUserModulePath();
OwnedArray<ModuleDescription> modules;
};
//==============================================================================
class LibraryModule
{
@@ -135,6 +110,47 @@ private:
void addBrowseableCode (ProjectExporter&, const Array<File>& compiled, const File& localModuleFolder) const;
};
//==============================================================================
using ModuleIDAndFolder = std::pair<String, File>;
using ModuleIDAndFolderList = std::vector<ModuleIDAndFolder>;
class AvailableModuleList
{
public:
AvailableModuleList();
void scanPaths (const Array<File>&);
void scanPathsAsync (const Array<File>&);
ModuleIDAndFolderList getAllModules() const;
ModuleIDAndFolder getModuleWithID (const String&) const;
void removeDuplicates (const ModuleIDAndFolderList& other);
//==============================================================================
struct Listener
{
virtual ~Listener() {}
virtual void availableModulesChanged() = 0;
};
void addListener (Listener* listenerToAdd) { listeners.add (listenerToAdd); }
void removeListener (Listener* listenerToRemove) { listeners.remove (listenerToRemove); }
private:
ThreadPoolJob* createScannerJob (const Array<File>&);
void removePendingAndAddJob (ThreadPoolJob*);
ThreadPool scanPool { 1 };
ModuleIDAndFolderList moduleList;
ListenerList<Listener> listeners;
CriticalSection lock;
JUCE_DECLARE_NON_COPYABLE_WITH_LEAK_DETECTOR (AvailableModuleList)
};
//==============================================================================
class EnabledModuleList
{
@@ -182,7 +198,5 @@ public:
private:
UndoManager* getUndoManager() const { return project.getUndoManagerFor (state); }
File findFolderForModule (const String& moduleID);
JUCE_DECLARE_NON_COPYABLE_WITH_LEAK_DETECTOR (EnabledModuleList)
};

+ 103
- 41
extras/Projucer/Source/Project/jucer_Project.cpp View File

@@ -64,7 +64,7 @@ Project::Project (const File& f)
parsedPreprocessorDefs = parsePreprocessorDefs (preprocessorDefsValue.get());
getModules().sortAlphabetically();
getEnabledModules().sortAlphabetically();
projectRoot.addListener (this);
@@ -488,45 +488,33 @@ static int getBuiltJuceVersion()
+ JUCE_BUILDNUMBER;
}
static bool isAnyModuleNewerThanProjucer (const OwnedArray<ModuleDescription>& modules)
static bool isModuleNewerThanProjucer (const ModuleDescription& module)
{
for (auto i = modules.size(); --i >= 0;)
{
auto* m = modules.getUnchecked(i);
if (m->getID().startsWith ("juce_")
&& getJuceVersion (m->getVersion()) > getBuiltJuceVersion())
return true;
}
if (module.getID().startsWith ("juce_")
&& getJuceVersion (module.getVersion()) > getBuiltJuceVersion())
return true;
return false;
}
void Project::warnAboutOldProjucerVersion()
{
ModuleList available;
available.scanGlobalJuceModulePath();
if (! isAnyModuleNewerThanProjucer (available.modules))
available.scanGlobalUserModulePath();
if (! isAnyModuleNewerThanProjucer (available.modules))
available.scanProjectExporterModulePaths (*this);
if (! isAnyModuleNewerThanProjucer (available.modules))
return;
// Projucer is out of date!
if (ProjucerApplication::getApp().isRunningCommandLine)
std::cout << "WARNING! This version of the Projucer is out-of-date!" << std::endl;
else
AlertWindow::showMessageBoxAsync (AlertWindow::WarningIcon,
"Projucer",
"This version of the Projucer is out-of-date!"
"\n\n"
"Always make sure that you're running the very latest version, "
"preferably compiled directly from the JUCE repository that you're working with!");
for (auto& juceModule : ProjucerApplication::getApp().getJUCEPathModuleList().getAllModules())
{
if (isModuleNewerThanProjucer ({ juceModule.second }))
{
// Projucer is out of date!
if (ProjucerApplication::getApp().isRunningCommandLine)
std::cout << "WARNING! This version of the Projucer is out-of-date!" << std::endl;
else
AlertWindow::showMessageBoxAsync (AlertWindow::WarningIcon,
"Projucer",
"This version of the Projucer is out-of-date!"
"\n\n"
"Always make sure that you're running the very latest version, "
"preferably compiled directly from the JUCE repository that you're working with!");
}
}
}
//==============================================================================
@@ -564,7 +552,7 @@ Result Project::loadDocument (const File& file)
registerRecentFile (file);
enabledModulesList.reset();
enabledModuleList.reset();
projectRoot = newTree;
initialiseProjectValues();
@@ -586,6 +574,9 @@ Result Project::loadDocument (const File& file)
compileEngineSettings.reset (new CompileEngineSettings (projectRoot));
exporterPathsModuleList.reset (new AvailableModuleList());
rescanExporterPathModules (! ProjucerApplication::getApp().isRunningCommandLine);
return Result::ok();
}
@@ -1744,17 +1735,17 @@ String Project::getIAAPluginName()
//==============================================================================
bool Project::isAUPluginHost()
{
return getModules().isModuleEnabled ("juce_audio_processors") && isConfigFlagEnabled ("JUCE_PLUGINHOST_AU");
return getEnabledModules().isModuleEnabled ("juce_audio_processors") && isConfigFlagEnabled ("JUCE_PLUGINHOST_AU");
}
bool Project::isVSTPluginHost()
{
return getModules().isModuleEnabled ("juce_audio_processors") && isConfigFlagEnabled ("JUCE_PLUGINHOST_VST");
return getEnabledModules().isModuleEnabled ("juce_audio_processors") && isConfigFlagEnabled ("JUCE_PLUGINHOST_VST");
}
bool Project::isVST3PluginHost()
{
return getModules().isModuleEnabled ("juce_audio_processors") && isConfigFlagEnabled ("JUCE_PLUGINHOST_VST3");
return getEnabledModules().isModuleEnabled ("juce_audio_processors") && isConfigFlagEnabled ("JUCE_PLUGINHOST_VST3");
}
//==============================================================================
@@ -1875,12 +1866,83 @@ Array<var> Project::getDefaultRTASCategories() const noexcept
}
//==============================================================================
EnabledModuleList& Project::getModules()
EnabledModuleList& Project::getEnabledModules()
{
if (enabledModuleList == nullptr)
enabledModuleList.reset (new EnabledModuleList (*this, projectRoot.getOrCreateChildWithName (Ids::MODULES, nullptr)));
return *enabledModuleList;
}
static Array<File> getAllPossibleModulePathsFromExporters (Project& project)
{
StringArray paths;
for (Project::ExporterIterator exporter (project); exporter.next();)
{
auto& modules = project.getEnabledModules();
auto n = modules.getNumModules();
for (int i = 0; i < n; ++i)
{
auto id = modules.getModuleID (i);
if (modules.shouldUseGlobalPath (id))
continue;
auto path = exporter->getPathForModuleString (id);
if (path.isNotEmpty())
paths.addIfNotAlreadyThere (path);
}
auto oldPath = exporter->getLegacyModulePath();
if (oldPath.isNotEmpty())
paths.addIfNotAlreadyThere (oldPath);
}
Array<File> files;
for (auto& path : paths)
{
auto f = project.resolveFilename (path);
if (f.isDirectory())
{
files.addIfNotAlreadyThere (f);
if (f.getChildFile ("modules").isDirectory())
files.addIfNotAlreadyThere (f.getChildFile ("modules"));
}
}
return files;
}
AvailableModuleList& Project::getExporterPathsModuleList()
{
return *exporterPathsModuleList;
}
void Project::rescanExporterPathModules (bool async)
{
if (async)
exporterPathsModuleList->scanPathsAsync (getAllPossibleModulePathsFromExporters (*this));
else
exporterPathsModuleList->scanPaths (getAllPossibleModulePathsFromExporters (*this));
}
ModuleIDAndFolder Project::getModuleWithID (const String& id)
{
if (enabledModulesList == nullptr)
enabledModulesList.reset (new EnabledModuleList (*this, projectRoot.getOrCreateChildWithName (Ids::MODULES, nullptr)));
const auto& list = (isJUCEModule (id) ? ProjucerApplication::getApp().getJUCEPathModuleList().getAllModules()
: ProjucerApplication::getApp().getUserPathsModuleList().getAllModules());
for (auto& m : list)
if (m.first == id)
return m;
return *enabledModulesList;
return exporterPathsModuleList->getModuleWithID (id);
}
//==============================================================================


+ 9
- 2
extras/Projucer/Source/Project/jucer_Project.h View File

@@ -31,6 +31,7 @@
class ProjectExporter;
class LibraryModule;
class EnabledModuleList;
class AvailableModuleList;
class ProjectContentComponent;
class CompileEngineSettings;
@@ -351,7 +352,12 @@ public:
bool isConfigFlagEnabled (const String& name, bool defaultIsEnabled = false) const;
//==============================================================================
EnabledModuleList& getModules();
EnabledModuleList& getEnabledModules();
AvailableModuleList& getExporterPathsModuleList();
void rescanExporterPathModules (bool async = false);
std::pair<String, File> getModuleWithID (const String&);
//==============================================================================
String getFileTemplate (const String& templateName);
@@ -412,6 +418,8 @@ private:
//==============================================================================
std::unique_ptr<CompileEngineSettings> compileEngineSettings;
std::unique_ptr<EnabledModuleList> enabledModuleList;
std::unique_ptr<AvailableModuleList> exporterPathsModuleList;
//==============================================================================
bool shouldWriteLegacyPluginFormatSettings = false;
@@ -440,7 +448,6 @@ private:
//==============================================================================
friend class Item;
std::unique_ptr<EnabledModuleList> enabledModulesList;
bool isSaving = false;
Time modificationTime;
StringPairArray parsedPreprocessorDefs;


+ 1
- 1
extras/Projucer/Source/ProjectSaving/jucer_ProjectExport_Android.h View File

@@ -1788,7 +1788,7 @@ private:
void createOpenGlFeatureElement (XmlElement& manifest) const
{
if (project.getModules().isModuleEnabled ("juce_opengl"))
if (project.getEnabledModules().isModuleEnabled ("juce_opengl"))
{
XmlElement* glVersion = nullptr;


+ 1
- 1
extras/Projucer/Source/ProjectSaving/jucer_ProjectExport_CodeBlocks.h View File

@@ -312,7 +312,7 @@ private:
static String guiExtrasModule ("juce_gui_extra");
if (project.getModules().isModuleEnabled (guiExtrasModule)
if (project.getEnabledModules().isModuleEnabled (guiExtrasModule)
&& project.isConfigFlagEnabled ("JUCE_WEB_BROWSER", true))
{
result.add ("webkit2gtk-4.0");


+ 2
- 2
extras/Projucer/Source/ProjectSaving/jucer_ProjectExport_Make.h View File

@@ -608,7 +608,7 @@ private:
{
static String guiExtrasModule ("juce_gui_extra");
return (project.getModules().isModuleEnabled (guiExtrasModule)
return (project.getEnabledModules().isModuleEnabled (guiExtrasModule)
&& project.isConfigFlagEnabled ("JUCE_WEB_BROWSER", true));
}
@@ -616,7 +616,7 @@ private:
{
static String juceCoreModule ("juce_core");
return (project.getModules().isModuleEnabled (juceCoreModule)
return (project.getEnabledModules().isModuleEnabled (juceCoreModule)
&& project.isConfigFlagEnabled ("JUCE_LOAD_CURL_SYMBOLS_LAZILY", false));
}


+ 1
- 1
extras/Projucer/Source/ProjectSaving/jucer_ProjectExport_Xcode.h View File

@@ -1506,7 +1506,7 @@ public:
paths.addArray (config.getHeaderSearchPaths());
paths.addArray (getTargetExtraHeaderSearchPaths());
if (owner.project.getModules().isModuleEnabled ("juce_audio_plugin_client"))
if (owner.project.getEnabledModules().isModuleEnabled ("juce_audio_plugin_client"))
{
// Needed to compile .r files
paths.add (owner.getModuleFolderRelativeToProject ("juce_audio_plugin_client")


+ 15
- 15
extras/Projucer/Source/ProjectSaving/jucer_ProjectExporter.cpp View File

@@ -544,7 +544,7 @@ String ProjectExporter::getPathForModuleString (const String& moduleID) const
auto exporterPath = settings.getChildWithName (Ids::MODULEPATHS)
.getChildWithProperty (Ids::ID, moduleID) [Ids::path].toString();
if (exporterPath.isEmpty() || project.getModules().shouldUseGlobalPath (moduleID))
if (exporterPath.isEmpty() || project.getEnabledModules().shouldUseGlobalPath (moduleID))
{
auto id = isJUCEModule (moduleID) ? Ids::defaultJuceModulePath
: Ids::defaultUserModulePath;
@@ -573,17 +573,17 @@ TargetOS::OS ProjectExporter::getTargetOSForExporter() const
{
auto targetOS = TargetOS::unknown;
if (isWindows()) targetOS = TargetOS::windows;
else if (isOSX() || isiOS()) targetOS = TargetOS::osx;
else if (isLinux()) targetOS = TargetOS::linux;
else if (isAndroid()) targetOS = TargetOS::getThisOS();
if (isWindows()) targetOS = TargetOS::windows;
else if (isOSX() || isiOS()) targetOS = TargetOS::osx;
else if (isLinux()) targetOS = TargetOS::linux;
else if (isAndroid() || isCLion()) targetOS = TargetOS::getThisOS();
return targetOS;
}
RelativePath ProjectExporter::getModuleFolderRelativeToProject (const String& moduleID) const
{
if (project.getModules().shouldCopyModuleFilesLocally (moduleID).getValue())
if (project.getEnabledModules().shouldCopyModuleFilesLocally (moduleID).getValue())
return RelativePath (project.getRelativePathForFile (project.getLocalModuleFolder (moduleID)),
RelativePath::projectFolder);
@@ -602,7 +602,7 @@ String ProjectExporter::getLegacyModulePath() const
RelativePath ProjectExporter::getLegacyModulePath (const String& moduleID) const
{
if (project.getModules().state.getChildWithProperty (Ids::ID, moduleID) ["useLocalCopy"])
if (project.getEnabledModules().state.getChildWithProperty (Ids::ID, moduleID) ["useLocalCopy"])
return RelativePath (project.getRelativePathForFile (project.getGeneratedCodeFolder()
.getChildFile ("modules")
.getChildFile (moduleID)), RelativePath::projectFolder);
@@ -625,9 +625,9 @@ void ProjectExporter::updateOldModulePaths()
if (oldPath.isNotEmpty())
{
for (int i = project.getModules().getNumModules(); --i >= 0;)
for (int i = project.getEnabledModules().getNumModules(); --i >= 0;)
{
auto modID = project.getModules().getModuleID(i);
auto modID = project.getEnabledModules().getModuleID(i);
getPathForModuleValue (modID) = getLegacyModulePath (modID).getParentDirectory().toUnixStyle();
}
@@ -650,9 +650,9 @@ void ProjectExporter::createDefaultModulePaths()
{
if (areCompatibleExporters (*this, *exporter))
{
for (int i = project.getModules().getNumModules(); --i >= 0;)
for (int i = project.getEnabledModules().getNumModules(); --i >= 0;)
{
auto modID = project.getModules().getModuleID (i);
auto modID = project.getEnabledModules().getModuleID (i);
getPathForModuleValue (modID) = exporter->getPathForModuleValue (modID).getValue();
}
@@ -664,9 +664,9 @@ void ProjectExporter::createDefaultModulePaths()
{
if (exporter->canLaunchProject())
{
for (int i = project.getModules().getNumModules(); --i >= 0;)
for (int i = project.getEnabledModules().getNumModules(); --i >= 0;)
{
auto modID = project.getModules().getModuleID (i);
auto modID = project.getEnabledModules().getModuleID (i);
getPathForModuleValue (modID) = exporter->getPathForModuleValue (modID).getValue();
}
@@ -674,9 +674,9 @@ void ProjectExporter::createDefaultModulePaths()
}
}
for (int i = project.getModules().getNumModules(); --i >= 0;)
for (int i = project.getEnabledModules().getNumModules(); --i >= 0;)
{
auto modID = project.getModules().getModuleID (i);
auto modID = project.getEnabledModules().getModuleID (i);
getPathForModuleValue (modID) = "../../juce";
}
}


+ 3
- 3
extras/Projucer/Source/ProjectSaving/jucer_ProjectSaver.h View File

@@ -82,7 +82,7 @@ public:
project.setFile (projectFile);
OwnedArray<LibraryModule> modules;
project.getModules().createRequiredModules (modules);
project.getEnabledModules().createRequiredModules (modules);
checkModuleValidity (modules);
@@ -148,7 +148,7 @@ public:
Result saveContentNeededForLiveBuild()
{
OwnedArray<LibraryModule> modules;
project.getModules().createRequiredModules (modules);
project.getEnabledModules().createRequiredModules (modules);
checkModuleValidity (modules);
@@ -390,7 +390,7 @@ private:
return;
}
if (project.getModules().getExtraDependenciesNeeded (module->getID()).size() > 0)
if (project.getEnabledModules().getExtraDependenciesNeeded (module->getID()).size() > 0)
{
addError ("At least one of your modules has missing dependencies!\n"
"Please go to the settings page of the highlighted modules and add the required dependencies.");


+ 1
- 1
extras/Projucer/Source/Utility/Helpers/jucer_TranslationHelpers.h View File

@@ -183,7 +183,7 @@ struct TranslationHelpers
scanFilesForTranslations (strings, project.getMainGroup());
OwnedArray<LibraryModule> modules;
project.getModules().createRequiredModules (modules);
project.getEnabledModules().createRequiredModules (modules);
for (int j = 0; j < modules.size(); ++j)
{


+ 6
- 6
extras/Projucer/Source/Wizards/jucer_NewProjectWizard.h View File

@@ -182,14 +182,14 @@ struct NewProjectWizard
void addDefaultModules (Project& project, bool useGlobalPath)
{
StringArray mods (getDefaultModules());
auto defaultModules = getDefaultModules();
ModuleList list;
list.addAllModulesInFolder (modulesFolder);
AvailableModuleList list;
list.scanPaths ({ modulesFolder });
for (int i = 0; i < mods.size(); ++i)
if (const ModuleDescription* info = list.getModuleWithID (mods[i]))
project.getModules().addModule (info->moduleFolder, false, useGlobalPath, false);
for (auto& mod : list.getAllModules())
if (defaultModules.contains (mod.first))
project.getEnabledModules().addModule (mod.second, false, useGlobalPath, false);
}
void addExporters (Project& project, WizardComp& wizardComp)


Loading…
Cancel
Save