diff options
Diffstat (limited to 'devtools/create_project')
21 files changed, 1262 insertions, 597 deletions
diff --git a/devtools/create_project/cmake.cpp b/devtools/create_project/cmake.cpp new file mode 100644 index 0000000000..1423e686be --- /dev/null +++ b/devtools/create_project/cmake.cpp @@ -0,0 +1,324 @@ +/* ScummVM - Graphic Adventure Engine + * + * ScummVM is the legal property of its developers, whose names + * are too numerous to list here. Please refer to the COPYRIGHT + * file distributed with this source distribution. + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. + * + */ + +#include "config.h" +#include "cmake.h" + +#include <algorithm> +#include <cstring> +#include <fstream> +#include <iterator> + +namespace CreateProjectTool { + +CMakeProvider::CMakeProvider(StringList &global_warnings, std::map<std::string, StringList> &project_warnings, const int version) + : ProjectProvider(global_warnings, project_warnings, version) { +} + +const CMakeProvider::Library *CMakeProvider::getLibraryFromFeature(const char *feature) const { + static const Library s_libraries[] = { + { "sdl", "FindSDL", "SDL", "SDL_INCLUDE_DIR", "SDL_LIBRARY", 0 }, + { "sdl2", 0, "SDL2", "SDL2_INCLUDE_DIRS", "SDL2_LIBRARIES", 0 }, + { "freetype", "FindFreetype", "Freetype", "FREETYPE_INCLUDE_DIRS", "FREETYPE_LIBRARIES", 0 }, + { "libz", "FindZLIB", "ZLIB", "ZLIB_INCLUDE_DIRS", "ZLIB_LIBRARIES", 0 }, + { "png", "FindPNG", "PNG", "PNG_INCLUDE_DIRS", "PNG_LIBRARIES", 0 }, + { "jpeg", "FindJPEG", "JPEG", "JPEG_INCLUDE_DIRS", "JPEG_LIBRARIES", 0 }, + { "mpeg2", "FindMPEG2", "MPEG2", "MPEG2_INCLUDE_DIRS", "MPEG2_mpeg2_LIBRARY", 0 }, + { "flac", 0, 0, 0, 0, "FLAC" }, + { "mad", 0, 0, 0, 0, "mad" }, + { "vorbis", 0, 0, 0, 0, "vorbisfile vorbis ogg" }, + { "theora", 0, 0, 0, 0, "theoradec" }, + { "fluidsynth",0, 0, 0, 0, "fluidsynth" }, + { "faad", 0, 0, 0, 0, "faad" } + }; + + for (unsigned int i = 0; i < sizeof(s_libraries) / sizeof(s_libraries[0]); i++) { + if (std::strcmp(feature, s_libraries[i].feature) == 0) { + return &s_libraries[i]; + } + } + + return 0; +} + +void CMakeProvider::createWorkspace(const BuildSetup &setup) { + std::string filename = setup.outputDir + "/CMakeLists.txt"; + std::ofstream workspace(filename.c_str()); + if (!workspace) + error("Could not open \"" + filename + "\" for writing"); + + workspace << "cmake_minimum_required(VERSION 3.2)\n" + "project(" << setup.projectDescription << ")\n\n"; + + workspace << "# Define the engines and subengines\n"; + writeEngines(setup, workspace); + writeSubEngines(setup, workspace); + workspace << "# Generate options for the engines\n"; + writeEngineOptions(workspace); + + workspace << "include_directories(${" << setup.projectDescription << "_SOURCE_DIR} ${" << setup.projectDescription << "_SOURCE_DIR}/engines\n" + "$ENV{"<<LIBS_DEFINE<<"}/include)\n\n"; + + workspace << "# Libraries and features\n"; + writeFeatureLibSearch(workspace, setup.useSDL2 ? "sdl2" : "sdl"); + for (FeatureList::const_iterator i = setup.features.begin(), end = setup.features.end(); i != end; ++i) { + if (!i->enable || featureExcluded(i->name)) continue; + + writeFeatureLibSearch(workspace, i->name); + workspace << "add_definitions(-D" << i->define << ")\n"; + } + workspace << "\n"; + + writeWarnings(workspace); + writeDefines(setup, workspace); + workspace << "# Generate definitions for the engines\n"; + writeEngineDefinitions(workspace); + + workspace << "# Generate \"engines/plugins_table.h\"\n"; + writeGeneratePluginsTable(workspace); +} + +void CMakeProvider::writeFeatureLibSearch(std::ofstream &workspace, const char *feature) const { + const Library *library = getLibraryFromFeature(feature); + if (library) { + if (library->module) { + workspace << "Include(" << library->module << ")\n"; + } + if (library->package) { + workspace << "Find_Package(" << library->package << " REQUIRED)\n"; + } + if (library->includesVar) { + workspace << "include_directories(${" << library->includesVar << "})\n"; + } + } +} + +void CMakeProvider::writeEngines(const BuildSetup &setup, std::ofstream &workspace) const { + workspace << "set(ENGINES"; + for (EngineDescList::const_iterator i = setup.engines.begin(), end = setup.engines.end(); i != end; ++i) { + // We ignore all sub engines here because they require special handling. + if (!i->enable || isSubEngine(i->name, setup.engines)) { + continue; + } + + std::string engineName; + std::transform(i->name.begin(), i->name.end(), std::back_inserter(engineName), toupper); + + workspace << " " << engineName; + } + workspace << ")\n"; +} + +void CMakeProvider::writeSubEngines(const BuildSetup &setup, std::ofstream &workspace) const { + for (EngineDescList::const_iterator i = setup.engines.begin(), end = setup.engines.end(); i != end; ++i) { + // We ignore all sub engines here because they are handled in the inner loop + if (!i->enable || isSubEngine(i->name, setup.engines) || i->subEngines.empty()) { + continue; + } + + std::string engineName; + std::transform(i->name.begin(), i->name.end(), std::back_inserter(engineName), toupper); + + workspace << "set(SUB_ENGINES_" << engineName; + for (StringList::const_iterator j = i->subEngines.begin(), subEnd = i->subEngines.end(); j != subEnd; ++j) { + const EngineDesc &subEngine = findEngineDesc(*j, setup.engines); + if (!subEngine.enable) continue; + + std::string subEngineName; + std::transform(j->begin(), j->end(), std::back_inserter(subEngineName), toupper); + + workspace << " " << subEngineName; + } + workspace << ")\n"; + } + + workspace << "\n"; +} + +void CMakeProvider::createProjectFile(const std::string &name, const std::string &, const BuildSetup &setup, const std::string &moduleDir, + const StringList &includeList, const StringList &excludeList) { + + const std::string projectFile = setup.outputDir + "/CMakeLists.txt"; + std::ofstream project(projectFile.c_str(), std::ofstream::out | std::ofstream::app); + if (!project) + error("Could not open \"" + projectFile + "\" for writing"); + + if (name == setup.projectName) { + project << "add_executable(" << name << "\n"; + } else { + std::string engineName; + std::transform(name.begin(), name.end(), std::back_inserter(engineName), toupper); + + project << "if (ENABLE_" << engineName << ")\n"; + project << "add_library(" << name << "\n"; + } + + std::string modulePath; + if (!moduleDir.compare(0, setup.srcDir.size(), setup.srcDir)) { + modulePath = moduleDir.substr(setup.srcDir.size()); + if (!modulePath.empty() && modulePath.at(0) == '/') + modulePath.erase(0, 1); + } + + if (modulePath.size()) + addFilesToProject(moduleDir, project, includeList, excludeList, setup.filePrefix + '/' + modulePath); + else + addFilesToProject(moduleDir, project, includeList, excludeList, setup.filePrefix); + + + project << ")\n"; + if (name != setup.projectName) { + project << "endif()\n"; + } + + project << "# Libraries\n"; + if (name == setup.projectName) { + const Library *sdlLibrary = getLibraryFromFeature(setup.useSDL2 ? "sdl2" : "sdl"); + project << "target_link_libraries(" << name << " ${" << sdlLibrary->librariesVar << "})\n"; + + for (FeatureList::const_iterator i = setup.features.begin(), end = setup.features.end(); i != end; ++i) { + if (!i->enable || featureExcluded(i->name)) continue; + + const Library *library = getLibraryFromFeature(i->name); + if (!library) continue; + + if (library->librariesVar) { + project << "target_link_libraries(" << name << " ${" << library->librariesVar << "})\n"; + } else { + project << "target_link_libraries(" << name << " " << library->libraries << ")\n"; + } + } + project << "if (WIN32)\n"; + project << " target_sources(" << name << " PUBLIC dists/" << name << ".rc)\n"; + project << " target_link_libraries(" << name << " winmm)\n"; + project << "endif()\n"; + project << "\n"; + + project << "# Engines libraries handling\n"; + writeEnginesLibrariesHandling(setup, project); + + project << "set_property(TARGET " << name << " PROPERTY CXX_STANDARD 11)\n"; + project << "set_property(TARGET " << name << " PROPERTY CXX_STANDARD_REQUIRED ON)\n"; + } +} + +void CMakeProvider::writeWarnings(std::ofstream &output) const { + output << "SET (CMAKE_CXX_FLAGS \"${CMAKE_CXX_FLAGS}"; + for (StringList::const_iterator i = _globalWarnings.begin(); i != _globalWarnings.end(); ++i) { + output << " " << *i; + } + output << "\")\n"; +} + +void CMakeProvider::writeDefines(const BuildSetup &setup, std::ofstream &output) const { + output << "if (WIN32)\n"; + output << " add_definitions(-DWIN32)\n"; + output << "else()\n"; + output << " add_definitions(-DPOSIX)\n"; + output << "endif()\n"; + + output << "if (CMAKE_SIZEOF_VOID_P MATCHES 8)\n"; + output << " add_definitions(-DSCUMM_64BITS)\n"; + output << "endif()\n"; + + output << "add_definitions(-DSDL_BACKEND)\n\n"; +} + +void CMakeProvider::writeFileListToProject(const FileNode &dir, std::ofstream &projectFile, const int indentation, + const StringList &duplicate, const std::string &objPrefix, const std::string &filePrefix) { + + for (FileNode::NodeList::const_iterator i = dir.children.begin(); i != dir.children.end(); ++i) { + const FileNode *node = *i; + + if (!node->children.empty()) { + writeFileListToProject(*node, projectFile, indentation + 1, duplicate, objPrefix + node->name + '_', filePrefix + node->name + '/'); + } else { + std::string name, ext; + splitFilename(node->name, name, ext); + projectFile << "\t" << filePrefix + node->name << "\n"; + } + } +} + +const char *CMakeProvider::getProjectExtension() { + return ".txt"; +} + +void CMakeProvider::writeEngineOptions(std::ofstream &workspace) const { + workspace << "foreach(ENGINE IN LISTS ENGINES)\n"; + workspace << " OPTION(ENABLE_${ENGINE} \"Enable ${ENGINE}\" ON)\n"; + workspace << "endforeach(ENGINE)\n\n"; +} + +void CMakeProvider::writeGeneratePluginsTable(std::ofstream &workspace) const { + workspace << "file(REMOVE \"engines/plugins_table.h\")\n"; + workspace << "file(APPEND \"engines/plugins_table.h\" \"/* This file is automatically generated by CMake */\\n\")\n"; + workspace << "foreach(ENGINE IN LISTS ENGINES)\n"; + workspace << " if (ENABLE_${ENGINE})\n"; + workspace << " file(APPEND \"engines/plugins_table.h\" \"#if PLUGIN_ENABLED_STATIC(${ENGINE})\\n\")\n"; + workspace << " file(APPEND \"engines/plugins_table.h\" \"LINK_PLUGIN(${ENGINE})\\n\")\n"; + workspace << " file(APPEND \"engines/plugins_table.h\" \"#endif\\n\")\n"; + workspace << " endif()\n"; + workspace << "endforeach()\n\n"; +} + +void CMakeProvider::writeEnginesLibrariesHandling(const BuildSetup &setup, std::ofstream &workspace) const { + workspace << "foreach(ENGINE IN LISTS ENGINES)\n"; + workspace << " if (ENABLE_${ENGINE})\n"; + workspace << " string(TOLOWER ${ENGINE} ENGINE_LIB)\n\n"; + workspace << " # Enable C++11\n"; + workspace << " set_property(TARGET ${ENGINE_LIB} PROPERTY CXX_STANDARD 11)\n"; + workspace << " set_property(TARGET ${ENGINE_LIB} PROPERTY CXX_STANDARD_REQUIRED ON)\n\n"; + workspace << " # Link against the engine\n"; + workspace << " target_link_libraries("<< setup.projectName <<" ${ENGINE_LIB})\n"; + workspace << " endif()\n"; + workspace << "endforeach()\n\n"; +} + +void CMakeProvider::writeEngineDefinitions(std::ofstream &workspace) const { + workspace << "foreach(ENGINE IN LISTS ENGINES)\n"; + workspace << " if (ENABLE_${ENGINE})\n"; + workspace << " add_definitions(-DENABLE_${ENGINE})\n"; + workspace << " foreach(SUB_ENGINE IN LISTS SUB_ENGINES_${ENGINE})\n"; + workspace << " add_definitions(-DENABLE_${SUB_ENGINE})\n";; + workspace << " endforeach(SUB_ENGINE)\n"; + workspace << " endif()\n"; + workspace << "endforeach()\n\n"; +} + +bool CMakeProvider::featureExcluded(const char *name) const { + return std::strcmp(name, "nasm") == 0 || + std::strcmp(name, "updates") == 0 ; // NASM is not supported for now +} + +const EngineDesc &CMakeProvider::findEngineDesc(const std::string &name, const EngineDescList &engines) const { + for (EngineDescList::const_iterator i = engines.begin(), end = engines.end(); i != end; ++i) { + if (i->name == name) { + return *i; + } + + } + + error("Unable to find requested engine"); +} + +} // End of CreateProjectTool namespace diff --git a/devtools/create_project/cmake.h b/devtools/create_project/cmake.h new file mode 100644 index 0000000000..ec7ff565c9 --- /dev/null +++ b/devtools/create_project/cmake.h @@ -0,0 +1,85 @@ +/* ScummVM - Graphic Adventure Engine + * + * ScummVM is the legal property of its developers, whose names + * are too numerous to list here. Please refer to the COPYRIGHT + * file distributed with this source distribution. + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software + * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. + * + */ + +#ifndef TOOLS_CREATE_PROJECT_CMAKE_H +#define TOOLS_CREATE_PROJECT_CMAKE_H + +#include "create_project.h" + +namespace CreateProjectTool { + +/** + * A ProjectProvider used to generate CMake project descriptions + * + * Generated CMake projects are minimal, and will only work with GCC. + */ +class CMakeProvider : public ProjectProvider { +public: + CMakeProvider(StringList &global_warnings, std::map<std::string, StringList> &project_warnings, const int version = 0); + +protected: + + void createWorkspace(const BuildSetup &setup); + + void createOtherBuildFiles(const BuildSetup &) {} + + void addResourceFiles(const BuildSetup &setup, StringList &includeList, StringList &excludeList) {} + + void createProjectFile(const std::string &name, const std::string &uuid, const BuildSetup &setup, const std::string &moduleDir, + const StringList &includeList, const StringList &excludeList); + + void writeFileListToProject(const FileNode &dir, std::ofstream &projectFile, const int indentation, + const StringList &duplicate, const std::string &objPrefix, const std::string &filePrefix); + + const char *getProjectExtension(); + +private: + /** + * CMake properties for a library required by a feature + */ + struct Library { + const char *feature; + const char *module; + const char *package; + const char *includesVar; + const char *librariesVar; + const char *libraries; + }; + + const Library *getLibraryFromFeature(const char *feature) const; + + void writeWarnings(std::ofstream &output) const; + void writeDefines(const BuildSetup &setup, std::ofstream &output) const; + void writeEngines(const BuildSetup &setup, std::ofstream &workspace) const; + void writeSubEngines(const BuildSetup &setup, std::ofstream &workspace) const; + void writeEngineOptions(std::ofstream &workspace) const; + void writeGeneratePluginsTable(std::ofstream &workspace) const; + void writeEnginesLibrariesHandling(const BuildSetup &setup, std::ofstream &workspace) const; + void writeEngineDefinitions(std::ofstream &workspace) const; + void writeFeatureLibSearch(std::ofstream &workspace, const char *feature) const; + bool featureExcluded(const char *name) const; + const EngineDesc &findEngineDesc(const std::string &name, const EngineDescList &engines) const; +}; + +} // End of CreateProjectTool namespace + +#endif // TOOLS_CREATE_PROJECT_CMAKE_H diff --git a/devtools/create_project/cmake/CMakeLists.txt b/devtools/create_project/cmake/CMakeLists.txt new file mode 100644 index 0000000000..2646b89d2d --- /dev/null +++ b/devtools/create_project/cmake/CMakeLists.txt @@ -0,0 +1,23 @@ +cmake_minimum_required(VERSION 3.2) +project(create_project) + + +set(SOURCE_FILES + ../cmake.cpp + ../cmake.h + ../codeblocks.cpp + ../codeblocks.h + ../create_project.cpp + ../create_project.h + ../msbuild.cpp + ../msbuild.h + ../msvc.cpp + ../msvc.h + ../visualstudio.cpp + ../visualstudio.h + ../xcode.cpp + ../xcode.h + ) + +add_executable(create_project ${SOURCE_FILES}) + diff --git a/devtools/create_project/codeblocks.cpp b/devtools/create_project/codeblocks.cpp index 442a2b0025..e9dc8bf234 100644 --- a/devtools/create_project/codeblocks.cpp +++ b/devtools/create_project/codeblocks.cpp @@ -200,6 +200,11 @@ void CodeBlocksProvider::createProjectFile(const std::string &name, const std::s } +void CodeBlocksProvider::addResourceFiles(const BuildSetup &setup, StringList &includeList, StringList &excludeList) { + includeList.push_back(setup.srcDir + "/icons/" + setup.projectName + ".ico"); + includeList.push_back(setup.srcDir + "/dists/" + setup.projectName + ".rc"); +} + void CodeBlocksProvider::writeWarnings(const std::string &name, std::ofstream &output) const { // Global warnings diff --git a/devtools/create_project/codeblocks.h b/devtools/create_project/codeblocks.h index f65604d925..5baa21c242 100644 --- a/devtools/create_project/codeblocks.h +++ b/devtools/create_project/codeblocks.h @@ -37,6 +37,8 @@ protected: void createOtherBuildFiles(const BuildSetup &) {} + void addResourceFiles(const BuildSetup &setup, StringList &includeList, StringList &excludeList); + void createProjectFile(const std::string &name, const std::string &uuid, const BuildSetup &setup, const std::string &moduleDir, const StringList &includeList, const StringList &excludeList); diff --git a/devtools/create_project/create_project.cpp b/devtools/create_project/create_project.cpp index 0aba511491..7e2cad0901 100644 --- a/devtools/create_project/create_project.cpp +++ b/devtools/create_project/create_project.cpp @@ -31,6 +31,7 @@ #include "config.h" #include "create_project.h" +#include "cmake.h" #include "codeblocks.h" #include "msvc.h" #include "visualstudio.h" @@ -53,7 +54,7 @@ #define USE_WIN32_API #endif -#ifdef USE_WIN32_API +#if (defined(_WIN32) || defined(WIN32)) #include <windows.h> #else #include <sstream> @@ -83,10 +84,18 @@ std::string unifyPath(const std::string &path); * @param exe Name of the executable. */ void displayHelp(const char *exe); + +/** + * Build a list of options to enable or disable GCC warnings + * + * @param globalWarnings Resulting list of warnings + */ +void addGCCWarnings(StringList &globalWarnings); } // End of anonymous namespace enum ProjectType { kProjectNone, + kProjectCMake, kProjectCodeBlocks, kProjectMSVC, kProjectXcode @@ -125,7 +134,6 @@ int main(int argc, char *argv[]) { ProjectType projectType = kProjectNone; int msvcVersion = 12; - bool useSDL2 = false; // Parse command line arguments using std::cout; @@ -142,6 +150,14 @@ int main(int argc, char *argv[]) { return 0; + } else if (!std::strcmp(argv[i], "--cmake")) { + if (projectType != kProjectNone) { + std::cerr << "ERROR: You cannot pass more than one project type!\n"; + return -1; + } + + projectType = kProjectCMake; + } else if (!std::strcmp(argv[i], "--codeblocks")) { if (projectType != kProjectNone) { std::cerr << "ERROR: You cannot pass more than one project type!\n"; @@ -269,7 +285,7 @@ int main(int argc, char *argv[]) { } else if (!std::strcmp(argv[i], "--tests")) { setup.tests = true; } else if (!std::strcmp(argv[i], "--sdl2")) { - useSDL2 = true; + setup.useSDL2 = true; } else { std::cerr << "ERROR: Unknown parameter \"" << argv[i] << "\"\n"; return -1; @@ -335,19 +351,51 @@ int main(int argc, char *argv[]) { StringList featureDefines = getFeatureDefines(setup.features); setup.defines.splice(setup.defines.begin(), featureDefines); - // Windows only has support for the SDL backend, so we hardcode it here (along with winmm) - if (projectType != kProjectXcode) { + if (projectType == kProjectXcode) { + setup.defines.push_back("POSIX"); + // Define both MACOSX, and IPHONE, but only one of them will be associated to the + // correct target by the Xcode project provider. + // This define will help catching up target dependend files, like "browser_osx.mm" + // The suffix ("_osx", or "_ios") will be used by the project provider to filter out + // the files, according to the target. + setup.defines.push_back("MACOSX"); + setup.defines.push_back("IPHONE"); + } else if (projectType == kProjectMSVC || projectType == kProjectCodeBlocks) { + // Windows only has support for the SDL backend, so we hardcode it here (along with winmm) setup.defines.push_back("WIN32"); } else { + // As a last resort, select the backend files to build based on the platform used to build create_project. + // This is broken when cross compiling. +#if defined(_WIN32) || defined(WIN32) + setup.defines.push_back("WIN32"); +#else setup.defines.push_back("POSIX"); - setup.defines.push_back("MACOSX"); // This will break iOS, but allows OS X to catch up on browser_osx. +#endif } + + bool updatesEnabled = false; + for (FeatureList::const_iterator i = setup.features.begin(); i != setup.features.end(); ++i) { + if (i->enable && !strcmp(i->name, "updates")) + updatesEnabled = true; + } + if (updatesEnabled) { + setup.defines.push_back("USE_SPARKLE"); + if (projectType != kProjectXcode) + setup.libraries.push_back("winsparkle"); + else + setup.libraries.push_back("sparkle"); + } + setup.defines.push_back("SDL_BACKEND"); - if (!useSDL2) { - cout << "\nLinking to SDL 1.2\n\n"; + if (!setup.useSDL2) { + cout << "\nBuilding against SDL 1.2\n\n"; setup.libraries.push_back("sdl"); } else { - cout << "\nLinking to SDL 2.0\n\n"; + cout << "\nBuilding against SDL 2.0\n\n"; + // TODO: This also defines USE_SDL2 in the preprocessor, we don't do + // this in our configure/make based build system. Adapt create_project + // to replicate this behavior. + setup.defines.push_back("USE_SDL2"); setup.libraries.push_back("sdl2"); } setup.libraries.push_back("winmm"); @@ -374,49 +422,25 @@ int main(int argc, char *argv[]) { std::cerr << "ERROR: No project type has been specified!\n"; return -1; + case kProjectCMake: + if (setup.devTools || setup.tests) { + std::cerr << "ERROR: Building tools or tests is not supported for the CMake project type!\n"; + return -1; + } + + addGCCWarnings(globalWarnings); + + provider = new CreateProjectTool::CMakeProvider(globalWarnings, projectWarnings); + + break; + case kProjectCodeBlocks: if (setup.devTools || setup.tests) { std::cerr << "ERROR: Building tools or tests is not supported for the CodeBlocks project type!\n"; return -1; } - //////////////////////////////////////////////////////////////////////////// - // Code::Blocks is using GCC behind the scenes, so we need to pass a list - // of options to enable or disable warnings - //////////////////////////////////////////////////////////////////////////// - // - // -Wall - // enable all warnings - // - // -Wno-long-long -Wno-multichar -Wno-unknown-pragmas -Wno-reorder - // disable annoying and not-so-useful warnings - // - // -Wpointer-arith -Wcast-qual -Wcast-align - // -Wshadow -Wimplicit -Wnon-virtual-dtor -Wwrite-strings - // enable even more warnings... - // - // -fno-rtti -fno-exceptions -fcheck-new - // disable RTTI and exceptions, and enable checking of pointers returned - // by "new" - // - //////////////////////////////////////////////////////////////////////////// - - globalWarnings.push_back("-Wall"); - globalWarnings.push_back("-Wno-long-long"); - globalWarnings.push_back("-Wno-multichar"); - globalWarnings.push_back("-Wno-unknown-pragmas"); - globalWarnings.push_back("-Wno-reorder"); - globalWarnings.push_back("-Wpointer-arith"); - globalWarnings.push_back("-Wcast-qual"); - globalWarnings.push_back("-Wcast-align"); - globalWarnings.push_back("-Wshadow"); - globalWarnings.push_back("-Wimplicit"); - globalWarnings.push_back("-Wnon-virtual-dtor"); - globalWarnings.push_back("-Wwrite-strings"); - // The following are not warnings at all... We should consider adding them to - // a different list of parameters. - globalWarnings.push_back("-fno-exceptions"); - globalWarnings.push_back("-fcheck-new"); + addGCCWarnings(globalWarnings); provider = new CreateProjectTool::CodeBlocksProvider(globalWarnings, projectWarnings); @@ -630,6 +654,7 @@ void displayHelp(const char *exe) { " Additionally there are the following switches for changing various settings:\n" "\n" "Project specific settings:\n" + " --cmake build CMake project files\n" " --codeblocks build Code::Blocks project files\n" " --msvc build Visual Studio project files\n" " --xcode build XCode project files\n" @@ -684,6 +709,41 @@ void displayHelp(const char *exe) { cout.setf(std::ios_base::right, std::ios_base::adjustfield); } +void addGCCWarnings(StringList &globalWarnings) { + //////////////////////////////////////////////////////////////////////////// + // + // -Wall + // enable all warnings + // + // -Wno-long-long -Wno-multichar -Wno-unknown-pragmas -Wno-reorder + // disable annoying and not-so-useful warnings + // + // -Wpointer-arith -Wcast-qual -Wcast-align + // -Wshadow -Wimplicit -Wnon-virtual-dtor -Wwrite-strings + // enable even more warnings... + // + // -fno-exceptions -fcheck-new + // disable exceptions, and enable checking of pointers returned by "new" + // + //////////////////////////////////////////////////////////////////////////// + + globalWarnings.push_back("-Wall"); + globalWarnings.push_back("-Wno-long-long"); + globalWarnings.push_back("-Wno-multichar"); + globalWarnings.push_back("-Wno-unknown-pragmas"); + globalWarnings.push_back("-Wno-reorder"); + globalWarnings.push_back("-Wpointer-arith"); + globalWarnings.push_back("-Wcast-qual"); + globalWarnings.push_back("-Wcast-align"); + globalWarnings.push_back("-Wshadow"); + globalWarnings.push_back("-Wnon-virtual-dtor"); + globalWarnings.push_back("-Wwrite-strings"); + // The following are not warnings at all... We should consider adding them to + // a different list of parameters. + globalWarnings.push_back("-fno-exceptions"); + globalWarnings.push_back("-fcheck-new"); +} + /** * Parse the configure.engine file of a given engine directory and return a * list of all defined engines. @@ -929,16 +989,17 @@ TokenList tokenize(const std::string &input, char separator) { namespace { const Feature s_features[] = { // Libraries - { "libz", "USE_ZLIB", "zlib", true, "zlib (compression) support" }, - { "mad", "USE_MAD", "libmad", true, "libmad (MP3) support" }, - { "vorbis", "USE_VORBIS", "libvorbisfile_static libvorbis_static libogg_static", true, "Ogg Vorbis support" }, - { "flac", "USE_FLAC", "libFLAC_static win_utf8_io_static", true, "FLAC support" }, - { "png", "USE_PNG", "libpng", true, "libpng support" }, - { "faad", "USE_FAAD", "libfaad", false, "AAC support" }, - { "mpeg2", "USE_MPEG2", "libmpeg2", false, "MPEG-2 support" }, - { "theora", "USE_THEORADEC", "libtheora_static", true, "Theora decoding support" }, - {"freetype", "USE_FREETYPE2", "freetype", true, "FreeType support" }, - { "jpeg", "USE_JPEG", "jpeg-static", true, "libjpeg support" }, + { "libz", "USE_ZLIB", "zlib", true, "zlib (compression) support" }, + { "mad", "USE_MAD", "libmad", true, "libmad (MP3) support" }, + { "vorbis", "USE_VORBIS", "libvorbisfile_static libvorbis_static libogg_static", true, "Ogg Vorbis support" }, + { "flac", "USE_FLAC", "libFLAC_static win_utf8_io_static", true, "FLAC support" }, + { "png", "USE_PNG", "libpng16", true, "libpng support" }, + { "faad", "USE_FAAD", "libfaad", false, "AAC support" }, + { "mpeg2", "USE_MPEG2", "libmpeg2", false, "MPEG-2 support" }, + { "theora", "USE_THEORADEC", "libtheora_static", true, "Theora decoding support" }, + { "freetype", "USE_FREETYPE2", "freetype", true, "FreeType support" }, + { "jpeg", "USE_JPEG", "jpeg-static", true, "libjpeg support" }, + {"fluidsynth", "USE_FLUIDSYNTH", "libfluidsynth", true, "FluidSynth support" }, // Feature flags { "bink", "USE_BINK", "", true, "Bink video support" }, @@ -947,12 +1008,14 @@ const Feature s_features[] = { { "16bit", "USE_RGB_COLOR", "", true, "16bit color support" }, { "mt32emu", "USE_MT32EMU", "", true, "integrated MT-32 emulator" }, { "nasm", "USE_NASM", "", true, "IA-32 assembly support" }, // This feature is special in the regard, that it needs additional handling. - { "opengl", "USE_OPENGL", "opengl32", true, "OpenGL support" }, + { "opengl", "USE_OPENGL", "", true, "OpenGL support" }, + { "opengles", "USE_GLES", "", true, "forced OpenGL ES mode" }, { "taskbar", "USE_TASKBAR", "", true, "Taskbar integration support" }, { "translation", "USE_TRANSLATION", "", true, "Translation support" }, { "vkeybd", "ENABLE_VKEYBD", "", false, "Virtual keyboard support"}, { "keymapper", "ENABLE_KEYMAPPER", "", false, "Keymapper support"}, { "eventrecorder", "ENABLE_EVENTRECORDER", "", false, "Event recorder support"}, + { "updates", "USE_UPDATES", "", false, "Updates support"}, { "langdetect", "USE_DETECTLANG", "", true, "System language detection support" } // This feature actually depends on "translation", there // is just no current way of properly detecting this... }; @@ -1050,6 +1113,12 @@ void splitFilename(const std::string &fileName, std::string &name, std::string & ext = (dot == std::string::npos) ? std::string() : fileName.substr(dot + 1); } +std::string basename(const std::string &fileName) { + const std::string::size_type slash = fileName.find_last_of('/'); + if (slash == std::string::npos) return fileName; + return fileName.substr(slash + 1); +} + bool producesObjectFile(const std::string &fileName) { std::string n, ext; splitFilename(fileName, n, ext); @@ -1143,7 +1212,7 @@ bool compareNodes(const FileNode *l, const FileNode *r) { FileList listDirectory(const std::string &dir) { FileList result; -#ifdef USE_WIN32_API +#if defined(_WIN32) || defined(WIN32) WIN32_FIND_DATA fileInformation; HANDLE fileHandle = FindFirstFile((dir + "/*").c_str(), &fileInformation); @@ -1334,8 +1403,7 @@ void ProjectProvider::createProject(BuildSetup &setup) { createModuleList(setup.srcDir + "/image", setup.defines, setup.testDirs, in, ex); // Resource files - in.push_back(setup.srcDir + "/icons/" + setup.projectName + ".ico"); - in.push_back(setup.srcDir + "/dists/" + setup.projectName + ".rc"); + addResourceFiles(setup, in, ex); // Various text files in.push_back(setup.srcDir + "/AUTHORS"); diff --git a/devtools/create_project/create_project.h b/devtools/create_project/create_project.h index 459342a67d..1e417d485b 100644 --- a/devtools/create_project/create_project.h +++ b/devtools/create_project/create_project.h @@ -23,8 +23,8 @@ #ifndef TOOLS_CREATE_PROJECT_H #define TOOLS_CREATE_PROJECT_H -#ifndef __has_feature // Optional of course. - #define __has_feature(x) 0 // Compatibility with non-clang compilers. +#ifndef __has_feature // Optional of course. +#define __has_feature(x) 0 // Compatibility with non-clang compilers. #endif #include <map> @@ -229,15 +229,17 @@ struct BuildSetup { StringList testDirs; ///< List of all folders containing tests bool devTools; ///< Generate project files for the tools - bool tests; ///< Generate project files for the tests + bool tests; ///< Generate project files for the tests bool runBuildEvents; ///< Run build events as part of the build (generate revision number and copy engine/theme data & needed files to the build folder bool createInstaller; ///< Create NSIS installer after the build + bool useSDL2; ///< Whether to use SDL2 or not. BuildSetup() { devTools = false; tests = false; runBuildEvents = false; createInstaller = false; + useSDL2 = false; } }; @@ -316,6 +318,17 @@ std::string convertPathToWin(const std::string &path); void splitFilename(const std::string &fileName, std::string &name, std::string &ext); /** + * Returns the basename of a path. + * examples: + * a/b/c/d.ext -> d.ext + * d.ext -> d.ext + * + * @param fileName Filename + * @return The basename + */ +std::string basename(const std::string &fileName); + +/** * Checks whether the given file will produce an object file or not. * * @param fileName Name of the file. @@ -419,6 +432,13 @@ protected: virtual void createOtherBuildFiles(const BuildSetup &setup) = 0; /** + * Add resources to the project + * + * @param setup Description of the desired build setup. + */ + virtual void addResourceFiles(const BuildSetup &setup, StringList &includeList, StringList &excludeList) = 0; + + /** * Create a project file for the specified list of files. * * @param name Name of the project file. diff --git a/devtools/create_project/module.mk b/devtools/create_project/module.mk index 0db070fa7c..bb7bdcc9b0 100644 --- a/devtools/create_project/module.mk +++ b/devtools/create_project/module.mk @@ -2,6 +2,7 @@ MODULE := devtools/create_project MODULE_OBJS := \ + cmake.o \ create_project.o \ codeblocks.o \ msvc.o \ diff --git a/devtools/create_project/msbuild.cpp b/devtools/create_project/msbuild.cpp index a326bd721a..2c6a89543f 100644 --- a/devtools/create_project/msbuild.cpp +++ b/devtools/create_project/msbuild.cpp @@ -319,12 +319,6 @@ void MSBuildProvider::outputProjectSettings(std::ofstream &project, const std::s for (StringList::const_iterator i = setup.libraries.begin(); i != setup.libraries.end(); ++i) libraries += *i + ".lib;"; - if (_version == 14) { - std::string debug = isRelease ? "" : "d"; - libraries += "libvcruntime" + debug + ".lib;"; - libraries += "libucrt" + debug + ".lib;"; - } - project << "\t\t<Link>\n" "\t\t\t<OutputFile>$(OutDir)" << ((setup.devTools || setup.tests) ? name : setup.projectName) << ".exe</OutputFile>\n" "\t\t\t<AdditionalDependencies>" << libraries << "%(AdditionalDependencies)</AdditionalDependencies>\n" @@ -370,17 +364,17 @@ void MSBuildProvider::outputGlobalPropFile(const BuildSetup &setup, std::ofstrea "<Project DefaultTargets=\"Build\" ToolsVersion=\"" << (_version >= 12 ? _version : 4) << ".0\" xmlns=\"http://schemas.microsoft.com/developer/msbuild/2003\">\n" "\t<PropertyGroup>\n" "\t\t<_PropertySheetDisplayName>" << setup.projectDescription << "_Global</_PropertySheetDisplayName>\n" - "\t\t<ExecutablePath>$(" << LIBS_DEFINE << ")\\bin;$(ExecutablePath)</ExecutablePath>\n" - "\t\t<LibraryPath>$(" << LIBS_DEFINE << ")\\lib\\" << (bits == 32 ? "x86" : "x64") << ";$(LibraryPath)</LibraryPath>\n" - "\t\t<IncludePath>$(" << LIBS_DEFINE << ")\\include;$(" << LIBS_DEFINE << ")\\include\\SDL;$(IncludePath)</IncludePath>\n" + "\t\t<ExecutablePath>$(" << LIBS_DEFINE << ")\\bin;$(" << LIBS_DEFINE << ")\\bin\\" << (bits == 32 ? "x86" : "x64") << ";$(ExecutablePath)</ExecutablePath>\n" + "\t\t<LibraryPath>$(" << LIBS_DEFINE << ")\\lib\\" << (bits == 32 ? "x86" : "x64") << ";$(" << LIBS_DEFINE << ")\\lib\\" << (bits == 32 ? "x86" : "x64") << "\\$(Configuration);$(LibraryPath)</LibraryPath>\n" + "\t\t<IncludePath>$(" << LIBS_DEFINE << ")\\include;$(" << LIBS_DEFINE << ")\\include\\" << (setup.useSDL2 ? "SDL2" : "SDL") << ";$(IncludePath)</IncludePath>\n" "\t\t<OutDir>$(Configuration)" << bits << "\\</OutDir>\n" - "\t\t<IntDir>$(Configuration)" << bits << "/$(ProjectName)\\</IntDir>\n" + "\t\t<IntDir>$(Configuration)" << bits << "\\$(ProjectName)\\</IntDir>\n" "\t</PropertyGroup>\n" "\t<ItemDefinitionGroup>\n" "\t\t<ClCompile>\n" "\t\t\t<DisableLanguageExtensions>true</DisableLanguageExtensions>\n" "\t\t\t<DisableSpecificWarnings>" << warnings << ";%(DisableSpecificWarnings)</DisableSpecificWarnings>\n" - "\t\t\t<AdditionalIncludeDirectories>$(" << LIBS_DEFINE << ")\\include;.;" << prefix << ";" << prefix << "\\engines;" << (setup.tests ? prefix + "\\test\\cxxtest;" : "") << "$(TargetDir);%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>\n" + "\t\t\t<AdditionalIncludeDirectories>.;" << prefix << ";" << prefix << "\\engines;" << (setup.tests ? prefix + "\\test\\cxxtest;" : "") << "$(TargetDir);%(AdditionalIncludeDirectories)</AdditionalIncludeDirectories>\n" "\t\t\t<PreprocessorDefinitions>" << definesList << "%(PreprocessorDefinitions)</PreprocessorDefinitions>\n" "\t\t\t<ExceptionHandling>" << ((setup.devTools || setup.tests) ? "Sync" : "") << "</ExceptionHandling>\n"; @@ -437,10 +431,14 @@ void MSBuildProvider::createBuildProp(const BuildSetup &setup, bool isRelease, b "\t\t\t<StringPooling>true</StringPooling>\n" "\t\t\t<BufferSecurityCheck>false</BufferSecurityCheck>\n" "\t\t\t<DebugInformationFormat></DebugInformationFormat>\n" - "\t\t\t<RuntimeLibrary>MultiThreaded</RuntimeLibrary>\n" + "\t\t\t<RuntimeLibrary>MultiThreadedDLL</RuntimeLibrary>\n" "\t\t\t<EnablePREfast>" << (configuration == "Analysis" ? "true" : "false") << "</EnablePREfast>\n" "\t\t</ClCompile>\n" + "\t\t<Lib>\n" + "\t\t\t<LinkTimeCodeGeneration>true</LinkTimeCodeGeneration>\n" + "\t\t</Lib>\n" "\t\t<Link>\n" + "\t\t\t<LinkTimeCodeGeneration>UseLinkTimeCodeGeneration</LinkTimeCodeGeneration>\n" "\t\t\t<IgnoreSpecificDefaultLibraries>%(IgnoreSpecificDefaultLibraries)</IgnoreSpecificDefaultLibraries>\n" "\t\t\t<SetChecksum>true</SetChecksum>\n"; } else { @@ -448,11 +446,17 @@ void MSBuildProvider::createBuildProp(const BuildSetup &setup, bool isRelease, b "\t\t\t<PreprocessorDefinitions>WIN32;" << (configuration == "LLVM" ? "_CRT_SECURE_NO_WARNINGS;" : "") << "%(PreprocessorDefinitions)</PreprocessorDefinitions>\n" "\t\t\t<MinimalRebuild>true</MinimalRebuild>\n" "\t\t\t<BasicRuntimeChecks>EnableFastChecks</BasicRuntimeChecks>\n" - "\t\t\t<RuntimeLibrary>MultiThreadedDebug</RuntimeLibrary>\n" + "\t\t\t<RuntimeLibrary>MultiThreadedDebugDLL</RuntimeLibrary>\n" "\t\t\t<FunctionLevelLinking>true</FunctionLevelLinking>\n" - "\t\t\t<TreatWarningAsError>false</TreatWarningAsError>\n" - "\t\t\t<DebugInformationFormat>" << (isWin32 ? "EditAndContinue" : "ProgramDatabase") << "</DebugInformationFormat>\n" // For x64 format Edit and continue is not supported, thus we default to Program Database - "\t\t\t<EnablePREfast>" << (configuration == "Analysis" ? "true" : "false") << "</EnablePREfast>\n"; + "\t\t\t<TreatWarningAsError>false</TreatWarningAsError>\n"; + if (_version >= 14) { + // Since MSVC 2015 Edit and Continue is support for x64 too. + properties << "\t\t\t<DebugInformationFormat>" << "EditAndContinue" << "</DebugInformationFormat>\n"; + } else { + // Older MSVC versions did not support Edit and Continue for x64, thus we do not use it. + properties << "\t\t\t<DebugInformationFormat>" << (isWin32 ? "EditAndContinue" : "ProgramDatabase") << "</DebugInformationFormat>\n"; + } + properties << "\t\t\t<EnablePREfast>" << (configuration == "Analysis" ? "true" : "false") << "</EnablePREfast>\n"; if (configuration == "LLVM") { // FIXME The LLVM cl wrapper does not seem to work properly with the $(TargetDir) path so we hard-code the build folder until the issue is resolved @@ -463,8 +467,7 @@ void MSBuildProvider::createBuildProp(const BuildSetup &setup, bool isRelease, b properties << "\t\t</ClCompile>\n" "\t\t<Link>\n" "\t\t\t<GenerateDebugInformation>true</GenerateDebugInformation>\n" - "\t\t\t<ImageHasSafeExceptionHandlers>false</ImageHasSafeExceptionHandlers>\n" - "\t\t\t<IgnoreSpecificDefaultLibraries>libcmt.lib;%(IgnoreSpecificDefaultLibraries)</IgnoreSpecificDefaultLibraries>\n"; + "\t\t\t<ImageHasSafeExceptionHandlers>false</ImageHasSafeExceptionHandlers>\n"; } properties << "\t\t</Link>\n" diff --git a/devtools/create_project/msvc.cpp b/devtools/create_project/msvc.cpp index dbfbcc128d..e6b47fe724 100644 --- a/devtools/create_project/msvc.cpp +++ b/devtools/create_project/msvc.cpp @@ -130,6 +130,11 @@ void MSVCProvider::createOtherBuildFiles(const BuildSetup &setup) { createBuildProp(setup, false, true, "LLVM"); } +void MSVCProvider::addResourceFiles(const BuildSetup &setup, StringList &includeList, StringList &excludeList) { + includeList.push_back(setup.srcDir + "/icons/" + setup.projectName + ".ico"); + includeList.push_back(setup.srcDir + "/dists/" + setup.projectName + ".rc"); +} + void MSVCProvider::createGlobalProp(const BuildSetup &setup) { std::ofstream properties((setup.outputDir + '/' + setup.projectDescription + "_Global" + getPropertiesExtension()).c_str()); if (!properties) diff --git a/devtools/create_project/msvc.h b/devtools/create_project/msvc.h index e75e131bd1..178ba8e216 100644 --- a/devtools/create_project/msvc.h +++ b/devtools/create_project/msvc.h @@ -39,6 +39,8 @@ protected: void createOtherBuildFiles(const BuildSetup &setup); + void addResourceFiles(const BuildSetup &setup, StringList &includeList, StringList &excludeList); + /** * Create the global project properties. * diff --git a/devtools/create_project/msvc10/create_project.vcxproj b/devtools/create_project/msvc10/create_project.vcxproj index 80dfd5e8d3..700c4bb283 100644 --- a/devtools/create_project/msvc10/create_project.vcxproj +++ b/devtools/create_project/msvc10/create_project.vcxproj @@ -95,6 +95,7 @@ xcopy /Y "$(TargetPath)" "$(SolutionDir)\..\..\..\dists\iphone\"</Command> </PreBuildEvent> </ItemDefinitionGroup> <ItemGroup> + <ClCompile Include="..\cmake.cpp" /> <ClCompile Include="..\codeblocks.cpp" /> <ClCompile Include="..\create_project.cpp" /> <ClCompile Include="..\msbuild.cpp" /> @@ -103,6 +104,7 @@ xcopy /Y "$(TargetPath)" "$(SolutionDir)\..\..\..\dists\iphone\"</Command> <ClCompile Include="..\xcode.cpp" /> </ItemGroup> <ItemGroup> + <ClInclude Include="..\cmake.h" /> <ClInclude Include="..\codeblocks.h" /> <ClInclude Include="..\config.h" /> <ClInclude Include="..\create_project.h" /> diff --git a/devtools/create_project/msvc11/create_project.vcxproj b/devtools/create_project/msvc11/create_project.vcxproj index 8bbd25e9ba..09392a43e3 100644 --- a/devtools/create_project/msvc11/create_project.vcxproj +++ b/devtools/create_project/msvc11/create_project.vcxproj @@ -101,6 +101,7 @@ xcopy /Y "$(TargetPath)" "$(SolutionDir)\..\..\..\dists\iphone\"</Command> </PreBuildEvent> </ItemDefinitionGroup> <ItemGroup> + <ClCompile Include="..\cmake.cpp" /> <ClCompile Include="..\codeblocks.cpp" /> <ClCompile Include="..\create_project.cpp" /> <ClCompile Include="..\msbuild.cpp" /> @@ -109,6 +110,7 @@ xcopy /Y "$(TargetPath)" "$(SolutionDir)\..\..\..\dists\iphone\"</Command> <ClCompile Include="..\xcode.cpp" /> </ItemGroup> <ItemGroup> + <ClInclude Include="..\cmake.h" /> <ClInclude Include="..\codeblocks.h" /> <ClInclude Include="..\config.h" /> <ClInclude Include="..\create_project.h" /> diff --git a/devtools/create_project/msvc12/create_project.vcxproj b/devtools/create_project/msvc12/create_project.vcxproj index 6da1556547..3b38972e51 100644 --- a/devtools/create_project/msvc12/create_project.vcxproj +++ b/devtools/create_project/msvc12/create_project.vcxproj @@ -102,6 +102,7 @@ xcopy /Y "$(TargetPath)" "$(SolutionDir)\..\..\..\dists\iphone\"</Command> </PreBuildEvent> </ItemDefinitionGroup> <ItemGroup> + <ClCompile Include="..\cmake.cpp" /> <ClCompile Include="..\codeblocks.cpp" /> <ClCompile Include="..\create_project.cpp" /> <ClCompile Include="..\msbuild.cpp" /> @@ -110,6 +111,7 @@ xcopy /Y "$(TargetPath)" "$(SolutionDir)\..\..\..\dists\iphone\"</Command> <ClCompile Include="..\xcode.cpp" /> </ItemGroup> <ItemGroup> + <ClInclude Include="..\cmake.h" /> <ClInclude Include="..\codeblocks.h" /> <ClInclude Include="..\config.h" /> <ClInclude Include="..\create_project.h" /> diff --git a/devtools/create_project/msvc14/create_project.vcxproj b/devtools/create_project/msvc14/create_project.vcxproj index 3c0345f49c..839c834bb8 100644 --- a/devtools/create_project/msvc14/create_project.vcxproj +++ b/devtools/create_project/msvc14/create_project.vcxproj @@ -192,6 +192,7 @@ xcopy /Y "$(TargetPath)" "$(SolutionDir)\..\..\..\dists\iphone\"</Command> </PreBuildEvent> </ItemDefinitionGroup> <ItemGroup> + <ClCompile Include="..\cmake.cpp" /> <ClCompile Include="..\codeblocks.cpp" /> <ClCompile Include="..\create_project.cpp" /> <ClCompile Include="..\msbuild.cpp" /> @@ -200,6 +201,7 @@ xcopy /Y "$(TargetPath)" "$(SolutionDir)\..\..\..\dists\iphone\"</Command> <ClCompile Include="..\xcode.cpp" /> </ItemGroup> <ItemGroup> + <ClInclude Include="..\cmake.h" /> <ClInclude Include="..\codeblocks.h" /> <ClInclude Include="..\config.h" /> <ClInclude Include="..\create_project.h" /> diff --git a/devtools/create_project/msvc9/create_project.vcproj b/devtools/create_project/msvc9/create_project.vcproj index dc914248fb..eaa72099cc 100644 --- a/devtools/create_project/msvc9/create_project.vcproj +++ b/devtools/create_project/msvc9/create_project.vcproj @@ -170,6 +170,10 @@ > </File> <File + RelativePath="..\cmake.cpp" + > + </File> + <File RelativePath="..\codeblocks.cpp" > </File> @@ -200,6 +204,10 @@ > </File> <File + RelativePath="..\cmake.h" + > + </File> + <File RelativePath="..\codeblocks.h" > </File> diff --git a/devtools/create_project/scripts/postbuild.cmd b/devtools/create_project/scripts/postbuild.cmd index fcbd8c534a..31d2a94416 100644 --- a/devtools/create_project/scripts/postbuild.cmd +++ b/devtools/create_project/scripts/postbuild.cmd @@ -59,7 +59,7 @@ echo Invalid installer parameter. Should be "0" or "1" (was %~5)! goto done
:error_script:
-echo An error occured while running the installer script!
+echo An error occurred while running the installer script!
goto done
:done
diff --git a/devtools/create_project/scripts/prebuild.cmd b/devtools/create_project/scripts/prebuild.cmd index fbab426137..0efaab190c 100644 --- a/devtools/create_project/scripts/prebuild.cmd +++ b/devtools/create_project/scripts/prebuild.cmd @@ -27,7 +27,7 @@ echo Invalid target folder (%~2)! goto done
:error_script:
-echo An error occured while running the revision script!
+echo An error occurred while running the revision script!
:done
exit /B0
diff --git a/devtools/create_project/xcode.cpp b/devtools/create_project/xcode.cpp index babd530ad7..bfe7f522f0 100644 --- a/devtools/create_project/xcode.cpp +++ b/devtools/create_project/xcode.cpp @@ -26,58 +26,65 @@ #include <fstream> #include <algorithm> +#ifdef MACOSX +#include <sstream> +#include <iomanip> +#include <CommonCrypto/CommonCrypto.h> +#endif + namespace CreateProjectTool { #define DEBUG_XCODE_HASH 0 -#ifdef ENABLE_IOS #define IOS_TARGET 0 #define OSX_TARGET 1 -#define SIM_TARGET 2 -#else -#define OSX_TARGET 0 -#endif #define ADD_DEFINE(defines, name) \ defines.push_back(name); +#define REMOVE_DEFINE(defines, name) \ + { ValueList::iterator i = std::find(defines.begin(), defines.end(), name); if (i != defines.end()) defines.erase(i); } + +#define CONTAINS_DEFINE(defines, name) \ + (std::find(defines.begin(), defines.end(), name) != defines.end()) + #define ADD_SETTING(config, key, value) \ - config.settings[key] = Setting(value, "", SettingsNoQuote); + config._settings[key] = Setting(value, "", kSettingsNoQuote); #define ADD_SETTING_ORDER(config, key, value, order) \ - config.settings[key] = Setting(value, "", SettingsNoQuote, 0, order); + config.settings[key] = Setting(value, "", kSettingsNoQuote, 0, order); #define ADD_SETTING_ORDER_NOVALUE(config, key, comment, order) \ - config.settings[key] = Setting("", comment, SettingsNoValue, 0, order); + config._settings[key] = Setting("", comment, kSettingsNoValue, 0, order); #define ADD_SETTING_QUOTE(config, key, value) \ - config.settings[key] = Setting(value); + config._settings[key] = Setting(value); #define ADD_SETTING_QUOTE_VAR(config, key, value) \ - config.settings[key] = Setting(value, "", SettingsQuoteVariable); + config._settings[key] = Setting(value, "", kSettingsQuoteVariable); #define ADD_SETTING_LIST(config, key, values, flags, indent) \ - config.settings[key] = Setting(values, flags, indent); + config._settings[key] = Setting(values, flags, indent); #define REMOVE_SETTING(config, key) \ - config.settings.erase(key); + config._settings.erase(key); #define ADD_BUILD_FILE(id, name, fileRefId, comment) { \ Object *buildFile = new Object(this, id, name, "PBXBuildFile", "PBXBuildFile", comment); \ - buildFile->addProperty("fileRef", fileRefId, name, SettingsNoValue); \ + buildFile->addProperty("fileRef", fileRefId, name, kSettingsNoValue); \ _buildFile.add(buildFile); \ - _buildFile.flags = SettingsSingleItem; \ + _buildFile._flags = kSettingsSingleItem; \ } #define ADD_FILE_REFERENCE(id, name, properties) { \ Object *fileRef = new Object(this, id, name, "PBXFileReference", "PBXFileReference", name); \ - if (!properties.fileEncoding.empty()) fileRef->addProperty("fileEncoding", properties.fileEncoding, "", SettingsNoValue); \ - if (!properties.lastKnownFileType.empty()) fileRef->addProperty("lastKnownFileType", properties.lastKnownFileType, "", SettingsNoValue|SettingsQuoteVariable); \ - if (!properties.fileName.empty()) fileRef->addProperty("name", properties.fileName, "", SettingsNoValue|SettingsQuoteVariable); \ - if (!properties.filePath.empty()) fileRef->addProperty("path", properties.filePath, "", SettingsNoValue|SettingsQuoteVariable); \ - if (!properties.sourceTree.empty()) fileRef->addProperty("sourceTree", properties.sourceTree, "", SettingsNoValue); \ + if (!properties._fileEncoding.empty()) fileRef->addProperty("fileEncoding", properties._fileEncoding, "", kSettingsNoValue); \ + if (!properties._lastKnownFileType.empty()) fileRef->addProperty("lastKnownFileType", properties._lastKnownFileType, "", kSettingsNoValue|kSettingsQuoteVariable); \ + if (!properties._fileName.empty()) fileRef->addProperty("name", properties._fileName, "", kSettingsNoValue|kSettingsQuoteVariable); \ + if (!properties._filePath.empty()) fileRef->addProperty("path", properties._filePath, "", kSettingsNoValue|kSettingsQuoteVariable); \ + if (!properties._sourceTree.empty()) fileRef->addProperty("sourceTree", properties._sourceTree, "", kSettingsNoValue); \ _fileReference.add(fileRef); \ - _fileReference.flags = SettingsSingleItem; \ + _fileReference._flags = kSettingsSingleItem; \ } bool producesObjectFileOnOSX(const std::string &fileName) { @@ -92,12 +99,64 @@ bool producesObjectFileOnOSX(const std::string &fileName) { return false; } +bool targetIsIOS(const std::string &targetName) { + return targetName.length() > 4 && targetName.substr(targetName.length() - 4) == "-iOS"; +} + +bool shouldSkipFileForTarget(const std::string &fileID, const std::string &targetName, const std::string &fileName) { + // Rules: + // - if the parent directory is "backends/platform/ios7", the file belongs to the iOS target. + // - if the parent directory is "/sdl", the file belongs to the OS X target. + // - if the file has a suffix, like "_osx", or "_ios", the file belongs to one of the target. + // - if the file is an OS X icon file (icns), it belongs to the OS X target. + std::string name, ext; + splitFilename(fileName, name, ext); + if (targetIsIOS(targetName)) { + // iOS target: we skip all files with the "_osx" suffix + if (name.length() > 4 && name.substr(name.length() - 4) == "_osx") { + return true; + } + // We don't need SDL for the iOS target + static const std::string sdl_directory = "/sdl/"; + static const std::string surfacesdl_directory = "/surfacesdl/"; + static const std::string doublebufferdl_directory = "/doublebuffersdl/"; + if (fileID.find(sdl_directory) != std::string::npos + || fileID.find(surfacesdl_directory) != std::string::npos + || fileID.find(doublebufferdl_directory) != std::string::npos) { + return true; + } + if (ext == "icns") { + return true; + } + } + else { + // Ugly hack: explicitly remove the browser.cpp file. + // The problem is that we have only one project for two different targets, + // and the parsing of the "mk" files added this file for both targets... + if (fileID.length() > 12 && fileID.substr(fileID.length() - 12) == "/browser.cpp") { + return true; + } + // OS X target: we skip all files with the "_ios" suffix + if (name.length() > 4 && name.substr(name.length() - 4) == "_ios") { + return true; + } + // parent directory + const std::string directory = fileID.substr(0, fileID.length() - fileName.length()); + static const std::string iphone_directory = "backends/platform/ios7"; + if (directory.length() > iphone_directory.length() && directory.substr(directory.length() - iphone_directory.length()) == iphone_directory) { + return true; + } + } + return false; +} + XcodeProvider::Group::Group(XcodeProvider *objectParent, const std::string &groupName, const std::string &uniqueName, const std::string &path) : Object(objectParent, uniqueName, groupName, "PBXGroup", "", groupName) { - addProperty("name", name, "", SettingsNoValue|SettingsQuoteVariable); - addProperty("sourceTree", "<group>", "", SettingsNoValue|SettingsQuoteVariable); - + bool path_is_absolute = (path.length() > 0 && path.at(0) == '/'); + addProperty("name", _name, "", kSettingsNoValue | kSettingsQuoteVariable); + addProperty("sourceTree", path_is_absolute ? "<absolute>" : "<group>", "", kSettingsNoValue | kSettingsQuoteVariable); + if (path != "") { - addProperty("path", path, "", SettingsNoValue|SettingsQuoteVariable); + addProperty("path", path, "", kSettingsNoValue | kSettingsQuoteVariable); } _childOrder = 0; _treeName = uniqueName; @@ -106,43 +165,43 @@ XcodeProvider::Group::Group(XcodeProvider *objectParent, const std::string &grou void XcodeProvider::Group::ensureChildExists(const std::string &name) { std::map<std::string, Group*>::iterator it = _childGroups.find(name); if (it == _childGroups.end()) { - Group *child = new Group(parent, name, this->_treeName + '/' + name, name); + Group *child = new Group(_parent, name, this->_treeName + '/' + name, name); _childGroups[name] = child; addChildGroup(child); - parent->_groups.add(child); + _parent->_groups.add(child); } } void XcodeProvider::Group::addChildInternal(const std::string &id, const std::string &comment) { - if (properties.find("children") == properties.end()) { + if (_properties.find("children") == _properties.end()) { Property children; - children.hasOrder = true; - children.flags = SettingsAsList; - properties["children"] = children; + children._hasOrder = true; + children._flags = kSettingsAsList; + _properties["children"] = children; } - properties["children"].settings[id] = Setting("", comment + " in Sources", SettingsNoValue, 0, _childOrder++); + _properties["children"]._settings[id] = Setting("", comment + " in Sources", kSettingsNoValue, 0, _childOrder++); if (_childOrder == 1) { // Force children to use () even when there is only 1 child. // Also this enforces the use of "," after the single item, instead of ; (see writeProperty) - properties["children"].flags |= SettingsSingleItem; + _properties["children"]._flags |= kSettingsSingleItem; } else { - properties["children"].flags ^= SettingsSingleItem; + _properties["children"]._flags ^= kSettingsSingleItem; } } -void XcodeProvider::Group::addChildGroup(const Group* group) { - addChildInternal(parent->getHash(group->_treeName), group->_treeName); +void XcodeProvider::Group::addChildGroup(const Group *group) { + addChildInternal(_parent->getHash(group->_treeName), group->_treeName); } void XcodeProvider::Group::addChildFile(const std::string &name) { std::string id = "FileReference_" + _treeName + "/" + name; - addChildInternal(parent->getHash(id), name); + addChildInternal(_parent->getHash(id), name); FileProperty property = FileProperty(name, name, name, "\"<group>\""); - parent->addFileReference(id, name, property); + _parent->addFileReference(id, name, property); if (producesObjectFileOnOSX(name)) { - parent->addBuildFile(_treeName + "/" + name, name, parent->getHash(id), name + " in Sources"); + _parent->addBuildFile(_treeName + "/" + name, name, _parent->getHash(id), name + " in Sources"); } } @@ -151,14 +210,14 @@ void XcodeProvider::Group::addChildByHash(const std::string &hash, const std::st } XcodeProvider::Group *XcodeProvider::Group::getChildGroup(const std::string &name) { - std::map<std::string, Group*>::iterator it = _childGroups.find(name); + std::map<std::string, Group *>::iterator it = _childGroups.find(name); assert(it != _childGroups.end()); return it->second; } XcodeProvider::Group *XcodeProvider::touchGroupsForPath(const std::string &path) { if (_rootSourceGroup == NULL) { - assert (path == _projectRoot); + assert(path == _projectRoot); _rootSourceGroup = new Group(this, "Sources", path, path); _groups.add(_rootSourceGroup); return _rootSourceGroup; @@ -180,31 +239,31 @@ XcodeProvider::Group *XcodeProvider::touchGroupsForPath(const std::string &path) void XcodeProvider::addFileReference(const std::string &id, const std::string &name, FileProperty properties) { Object *fileRef = new Object(this, id, name, "PBXFileReference", "PBXFileReference", name); - if (!properties.fileEncoding.empty()) fileRef->addProperty("fileEncoding", properties.fileEncoding, "", SettingsNoValue); - if (!properties.lastKnownFileType.empty()) fileRef->addProperty("lastKnownFileType", properties.lastKnownFileType, "", SettingsNoValue|SettingsQuoteVariable); - if (!properties.fileName.empty()) fileRef->addProperty("name", properties.fileName, "", SettingsNoValue|SettingsQuoteVariable); - if (!properties.filePath.empty()) fileRef->addProperty("path", properties.filePath, "", SettingsNoValue|SettingsQuoteVariable); - if (!properties.sourceTree.empty()) fileRef->addProperty("sourceTree", properties.sourceTree, "", SettingsNoValue); + if (!properties._fileEncoding.empty()) fileRef->addProperty("fileEncoding", properties._fileEncoding, "", kSettingsNoValue); + if (!properties._lastKnownFileType.empty()) fileRef->addProperty("lastKnownFileType", properties._lastKnownFileType, "", kSettingsNoValue | kSettingsQuoteVariable); + if (!properties._fileName.empty()) fileRef->addProperty("name", properties._fileName, "", kSettingsNoValue | kSettingsQuoteVariable); + if (!properties._filePath.empty()) fileRef->addProperty("path", properties._filePath, "", kSettingsNoValue | kSettingsQuoteVariable); + if (!properties._sourceTree.empty()) fileRef->addProperty("sourceTree", properties._sourceTree, "", kSettingsNoValue); _fileReference.add(fileRef); - _fileReference.flags = SettingsSingleItem; + _fileReference._flags = kSettingsSingleItem; } void XcodeProvider::addProductFileReference(const std::string &id, const std::string &name) { Object *fileRef = new Object(this, id, name, "PBXFileReference", "PBXFileReference", name); - fileRef->addProperty("explicitFileType", "compiled.mach-o.executable", "", SettingsNoValue|SettingsQuoteVariable); - fileRef->addProperty("includeInIndex", "0", "", SettingsNoValue); - fileRef->addProperty("path", name, "", SettingsNoValue|SettingsQuoteVariable); - fileRef->addProperty("sourceTree", "BUILT_PRODUCTS_DIR", "", SettingsNoValue); + fileRef->addProperty("explicitFileType", "wrapper.application", "", kSettingsNoValue | kSettingsQuoteVariable); + fileRef->addProperty("includeInIndex", "0", "", kSettingsNoValue); + fileRef->addProperty("path", name, "", kSettingsNoValue | kSettingsQuoteVariable); + fileRef->addProperty("sourceTree", "BUILT_PRODUCTS_DIR", "", kSettingsNoValue); _fileReference.add(fileRef); - _fileReference.flags = SettingsSingleItem; + _fileReference._flags = kSettingsSingleItem; } void XcodeProvider::addBuildFile(const std::string &id, const std::string &name, const std::string &fileRefId, const std::string &comment) { Object *buildFile = new Object(this, id, name, "PBXBuildFile", "PBXBuildFile", comment); - buildFile->addProperty("fileRef", fileRefId, name, SettingsNoValue); + buildFile->addProperty("fileRef", fileRefId, name, kSettingsNoValue); _buildFile.add(buildFile); - _buildFile.flags = SettingsSingleItem; + _buildFile._flags = kSettingsSingleItem; } XcodeProvider::XcodeProvider(StringList &global_warnings, std::map<std::string, StringList> &project_warnings, const int version) @@ -212,28 +271,36 @@ XcodeProvider::XcodeProvider(StringList &global_warnings, std::map<std::string, _rootSourceGroup = NULL; } +void XcodeProvider::addResourceFiles(const BuildSetup &setup, StringList &includeList, StringList &excludeList) { + includeList.push_back(setup.srcDir + "/dists/ios7/Info.plist"); + + ValueList &resources = getResourceFiles(); + for (ValueList::iterator it = resources.begin(); it != resources.end(); ++it) { + includeList.push_back(setup.srcDir + "/" + *it); + } + + StringList td; + createModuleList(setup.srcDir + "/backends/platform/ios7", setup.defines, td, includeList, excludeList); +} + void XcodeProvider::createWorkspace(const BuildSetup &setup) { // Create project folder std::string workspace = setup.outputDir + '/' + PROJECT_NAME ".xcodeproj"; createDirectory(workspace); _projectRoot = setup.srcDir; touchGroupsForPath(_projectRoot); - + // Setup global objects setupDefines(setup); -#ifdef ENABLE_IOS - _targets.push_back(PROJECT_DESCRIPTION "-iPhone"); -#endif + _targets.push_back(PROJECT_DESCRIPTION "-iOS"); _targets.push_back(PROJECT_DESCRIPTION "-OS X"); -#ifdef ENABLE_IOS - _targets.push_back(PROJECT_DESCRIPTION "-Simulator"); -#endif setupCopyFilesBuildPhase(); - setupFrameworksBuildPhase(); + setupFrameworksBuildPhase(setup); setupNativeTarget(); setupProject(); setupResourcesBuildPhase(); - setupBuildConfiguration(); + setupBuildConfiguration(setup); + setupImageAssetCatalog(setup); } // We are done with constructing all the object graph and we got through every project, output the main project file @@ -274,10 +341,10 @@ void XcodeProvider::ouputMainProjectFile(const BuildSetup &setup) { // Header project << "// !$*UTF8*$!\n" "{\n" - "\t" << writeSetting("archiveVersion", "1", "", SettingsNoQuote) << ";\n" + "\t" << writeSetting("archiveVersion", "1", "", kSettingsNoQuote) << ";\n" "\tclasses = {\n" "\t};\n" - "\t" << writeSetting("objectVersion", "46", "", SettingsNoQuote) << ";\n" + "\t" << writeSetting("objectVersion", "46", "", kSettingsNoQuote) << ";\n" "\tobjects = {\n"; ////////////////////////////////////////////////////////////////////////// @@ -297,7 +364,7 @@ void XcodeProvider::ouputMainProjectFile(const BuildSetup &setup) { ////////////////////////////////////////////////////////////////////////// // Footer project << "\t};\n" - "\t" << writeSetting("rootObject", getHash("PBXProject"), "Project object", SettingsNoQuote) << ";\n" + "\t" << writeSetting("rootObject", getHash("PBXProject"), "Project object", kSettingsNoQuote) << ";\n" "}\n"; } @@ -333,24 +400,30 @@ void XcodeProvider::setupCopyFilesBuildPhase() { #define DEF_SYSFRAMEWORK(framework) properties[framework".framework"] = FileProperty("wrapper.framework", framework".framework", "System/Library/Frameworks/" framework ".framework", "SDKROOT"); \ ADD_SETTING_ORDER_NOVALUE(children, getHash(framework".framework"), framework".framework", fwOrder++); - -#define DEF_LOCALLIB_STATIC(lib) properties[lib".a"] = FileProperty("archive.ar", lib".a", "/opt/local/lib/" lib ".a", "\"<group>\""); \ + +#define DEF_SYSTBD(lib) properties[lib".tbd"] = FileProperty("sourcecode.text-based-dylib-definition", lib".tbd", "usr/lib/" lib ".tbd", "SDKROOT"); \ + ADD_SETTING_ORDER_NOVALUE(children, getHash(lib".tbd"), lib".tbd", fwOrder++); + +#define DEF_LOCALLIB_STATIC_PATH(path,lib,absolute) properties[lib".a"] = FileProperty("archive.ar", lib ".a", path, (absolute ? "\"<absolute>\"" : "\"<group>\"")); \ ADD_SETTING_ORDER_NOVALUE(children, getHash(lib".a"), lib".a", fwOrder++); +#define DEF_LOCALLIB_STATIC(lib) DEF_LOCALLIB_STATIC_PATH("/opt/local/lib/" lib ".a", lib, true) + + /** * Sets up the frameworks build phase. * * (each native target has different build rules) */ -void XcodeProvider::setupFrameworksBuildPhase() { - _frameworksBuildPhase.comment = "PBXFrameworksBuildPhase"; +void XcodeProvider::setupFrameworksBuildPhase(const BuildSetup &setup) { + _frameworksBuildPhase._comment = "PBXFrameworksBuildPhase"; // Just use a hardcoded id for the Frameworks-group Group *frameworksGroup = new Group(this, "Frameworks", "PBXGroup_CustomTemplate_Frameworks_", ""); Property children; - children.hasOrder = true; - children.flags = SettingsAsList; + children._hasOrder = true; + children._flags = kSettingsAsList; // Setup framework file properties std::map<std::string, FileProperty> properties; @@ -362,6 +435,8 @@ void XcodeProvider::setupFrameworksBuildPhase() { DEF_SYSFRAMEWORK("Carbon"); DEF_SYSFRAMEWORK("Cocoa"); DEF_SYSFRAMEWORK("CoreAudio"); + DEF_SYSFRAMEWORK("CoreMIDI"); + DEF_SYSFRAMEWORK("CoreGraphics"); DEF_SYSFRAMEWORK("CoreFoundation"); DEF_SYSFRAMEWORK("CoreMIDI"); DEF_SYSFRAMEWORK("Foundation"); @@ -370,8 +445,7 @@ void XcodeProvider::setupFrameworksBuildPhase() { DEF_SYSFRAMEWORK("QuartzCore"); DEF_SYSFRAMEWORK("QuickTime"); DEF_SYSFRAMEWORK("UIKit"); - // Optionals: - DEF_SYSFRAMEWORK("OpenGL"); + DEF_SYSTBD("libiconv"); // Local libraries DEF_LOCALLIB_STATIC("libFLAC"); @@ -380,64 +454,105 @@ void XcodeProvider::setupFrameworksBuildPhase() { DEF_LOCALLIB_STATIC("libfreetype"); // DEF_LOCALLIB_STATIC("libmpeg2"); - frameworksGroup->properties["children"] = children; + std::string absoluteOutputDir; +#ifdef POSIX + char *c_path = realpath(setup.outputDir.c_str(), NULL); + absoluteOutputDir = c_path; + absoluteOutputDir += "/lib"; + free(c_path); +#else + absoluteOutputDir = "lib"; +#endif + + DEF_LOCALLIB_STATIC_PATH(absoluteOutputDir + "/libFLAC.a", "libFLAC", true); + DEF_LOCALLIB_STATIC_PATH(absoluteOutputDir + "/libfreetype.a", "libfreetype", true); + DEF_LOCALLIB_STATIC_PATH(absoluteOutputDir + "/libogg.a", "libogg", true); + DEF_LOCALLIB_STATIC_PATH(absoluteOutputDir + "/libpng.a", "libpng", true); + DEF_LOCALLIB_STATIC_PATH(absoluteOutputDir + "/libvorbis.a", "libvorbis", true); + DEF_LOCALLIB_STATIC_PATH(absoluteOutputDir + "/libmad.a", "libmad", true); + DEF_LOCALLIB_STATIC_PATH(absoluteOutputDir + "/libfluidsynth.a", "libfluidsynth", true); + DEF_LOCALLIB_STATIC_PATH(absoluteOutputDir + "/libglib.a", "libglib", true); + DEF_LOCALLIB_STATIC_PATH(absoluteOutputDir + "/libffi.a", "libffi", true); + + frameworksGroup->_properties["children"] = children; _groups.add(frameworksGroup); // Force this to be added as a sub-group in the root. _rootSourceGroup->addChildGroup(frameworksGroup); - // Declare this here, as it's used across the three targets + // Declare this here, as it's used across all the targets int order = 0; -#ifdef ENABLE_IOS + ////////////////////////////////////////////////////////////////////////// - // iPhone + // ScummVM-iOS Object *framework_iPhone = new Object(this, "PBXFrameworksBuildPhase_" + _targets[IOS_TARGET], "PBXFrameworksBuildPhase", "PBXFrameworksBuildPhase", "", "Frameworks"); - framework_iPhone->addProperty("buildActionMask", "2147483647", "", SettingsNoValue); - framework_iPhone->addProperty("runOnlyForDeploymentPostprocessing", "0", "", SettingsNoValue); + framework_iPhone->addProperty("buildActionMask", "2147483647", "", kSettingsNoValue); + framework_iPhone->addProperty("runOnlyForDeploymentPostprocessing", "0", "", kSettingsNoValue); // List of frameworks - Property iPhone_files; - iPhone_files.hasOrder = true; - iPhone_files.flags = SettingsAsList; - - ValueList frameworks_iPhone; - frameworks_iPhone.push_back("CoreAudio.framework"); - frameworks_iPhone.push_back("CoreFoundation.framework"); - frameworks_iPhone.push_back("Foundation.framework"); - frameworks_iPhone.push_back("UIKit.framework"); - frameworks_iPhone.push_back("AudioToolbox.framework"); - frameworks_iPhone.push_back("QuartzCore.framework"); - frameworks_iPhone.push_back("libmad.a"); - //frameworks_iPhone.push_back("libmpeg2.a"); - frameworks_iPhone.push_back("libFLAC.a"); - frameworks_iPhone.push_back("libvorbisidec.a"); - frameworks_iPhone.push_back("OpenGLES.framework"); - - for (ValueList::iterator framework = frameworks_iPhone.begin(); framework != frameworks_iPhone.end(); framework++) { + Property iOS_files; + iOS_files._hasOrder = true; + iOS_files._flags = kSettingsAsList; + + ValueList frameworks_iOS; + frameworks_iOS.push_back("CoreAudio.framework"); + frameworks_iOS.push_back("CoreGraphics.framework"); + frameworks_iOS.push_back("CoreFoundation.framework"); + frameworks_iOS.push_back("Foundation.framework"); + frameworks_iOS.push_back("UIKit.framework"); + frameworks_iOS.push_back("AudioToolbox.framework"); + frameworks_iOS.push_back("QuartzCore.framework"); + frameworks_iOS.push_back("OpenGLES.framework"); + + if (CONTAINS_DEFINE(setup.defines, "USE_FLAC")) { + frameworks_iOS.push_back("libFLAC.a"); + } + if (CONTAINS_DEFINE(setup.defines, "USE_FREETYPE2")) { + frameworks_iOS.push_back("libfreetype.a"); + } + if (CONTAINS_DEFINE(setup.defines, "USE_PNG")) { + frameworks_iOS.push_back("libpng.a"); + } + if (CONTAINS_DEFINE(setup.defines, "USE_VORBIS")) { + frameworks_iOS.push_back("libogg.a"); + frameworks_iOS.push_back("libvorbis.a"); + } + if (CONTAINS_DEFINE(setup.defines, "USE_MAD")) { + frameworks_iOS.push_back("libmad.a"); + } + if (CONTAINS_DEFINE(setup.defines, "USE_FLUIDSYNTH")) { + frameworks_iOS.push_back("libfluidsynth.a"); + frameworks_iOS.push_back("libglib.a"); + frameworks_iOS.push_back("libffi.a"); + frameworks_iOS.push_back("CoreMIDI.framework"); + frameworks_iOS.push_back("libiconv.tbd"); + } + + for (ValueList::iterator framework = frameworks_iOS.begin(); framework != frameworks_iOS.end(); framework++) { std::string id = "Frameworks_" + *framework + "_iphone"; std::string comment = *framework + " in Frameworks"; - ADD_SETTING_ORDER_NOVALUE(iPhone_files, getHash(id), comment, order++); + ADD_SETTING_ORDER_NOVALUE(iOS_files, getHash(id), comment, order++); ADD_BUILD_FILE(id, *framework, getHash(*framework), comment); ADD_FILE_REFERENCE(*framework, *framework, properties[*framework]); } - framework_iPhone->properties["files"] = iPhone_files; + framework_iPhone->_properties["files"] = iOS_files; _frameworksBuildPhase.add(framework_iPhone); -#endif + ////////////////////////////////////////////////////////////////////////// // ScummVM-OS X Object *framework_OSX = new Object(this, "PBXFrameworksBuildPhase_" + _targets[OSX_TARGET], "PBXFrameworksBuildPhase", "PBXFrameworksBuildPhase", "", "Frameworks"); - framework_OSX->addProperty("buildActionMask", "2147483647", "", SettingsNoValue); - framework_OSX->addProperty("runOnlyForDeploymentPostprocessing", "0", "", SettingsNoValue); + framework_OSX->addProperty("buildActionMask", "2147483647", "", kSettingsNoValue); + framework_OSX->addProperty("runOnlyForDeploymentPostprocessing", "0", "", kSettingsNoValue); // List of frameworks Property osx_files; - osx_files.hasOrder = true; - osx_files.flags = SettingsAsList; + osx_files._hasOrder = true; + osx_files._flags = kSettingsAsList; ValueList frameworks_osx; frameworks_osx.push_back("CoreFoundation.framework"); @@ -452,8 +567,6 @@ void XcodeProvider::setupFrameworksBuildPhase() { frameworks_osx.push_back("IOKit.framework"); frameworks_osx.push_back("Cocoa.framework"); frameworks_osx.push_back("AudioUnit.framework"); - // Optionals: - frameworks_osx.push_back("OpenGL.framework"); order = 0; for (ValueList::iterator framework = frameworks_osx.begin(); framework != frameworks_osx.end(); framework++) { @@ -465,81 +578,40 @@ void XcodeProvider::setupFrameworksBuildPhase() { ADD_FILE_REFERENCE(*framework, *framework, properties[*framework]); } - framework_OSX->properties["files"] = osx_files; + framework_OSX->_properties["files"] = osx_files; _frameworksBuildPhase.add(framework_OSX); -#ifdef ENABLE_IOS - ////////////////////////////////////////////////////////////////////////// - // Simulator - Object *framework_simulator = new Object(this, "PBXFrameworksBuildPhase_" + _targets[SIM_TARGET], "PBXFrameworksBuildPhase", "PBXFrameworksBuildPhase", "", "Frameworks"); - - framework_simulator->addProperty("buildActionMask", "2147483647", "", SettingsNoValue); - framework_simulator->addProperty("runOnlyForDeploymentPostprocessing", "0", "", SettingsNoValue); - - // List of frameworks - Property simulator_files; - simulator_files.hasOrder = true; - simulator_files.flags = SettingsAsList; - - ValueList frameworks_simulator; - frameworks_simulator.push_back("CoreAudio.framework"); - frameworks_simulator.push_back("CoreFoundation.framework"); - frameworks_simulator.push_back("Foundation.framework"); - frameworks_simulator.push_back("UIKit.framework"); - frameworks_simulator.push_back("AudioToolbox.framework"); - frameworks_simulator.push_back("QuartzCore.framework"); - frameworks_simulator.push_back("OpenGLES.framework"); - - order = 0; - for (ValueList::iterator framework = frameworks_simulator.begin(); framework != frameworks_simulator.end(); framework++) { - std::string id = "Frameworks_" + *framework + "_simulator"; - std::string comment = *framework + " in Frameworks"; - - ADD_SETTING_ORDER_NOVALUE(simulator_files, getHash(id), comment, order++); - ADD_BUILD_FILE(id, *framework, getHash(*framework), comment); - ADD_FILE_REFERENCE(*framework, *framework, properties[*framework]); - } - - framework_simulator->properties["files"] = simulator_files; - - _frameworksBuildPhase.add(framework_simulator); -#endif } void XcodeProvider::setupNativeTarget() { - _nativeTarget.comment = "PBXNativeTarget"; + _nativeTarget._comment = "PBXNativeTarget"; // Just use a hardcoded id for the Products-group Group *productsGroup = new Group(this, "Products", "PBXGroup_CustomTemplate_Products_" , ""); // Output native target section for (unsigned int i = 0; i < _targets.size(); i++) { -#ifndef ENABLE_IOS - if (i != OSX_TARGET) { // TODO: Fix iOS-targets, for now just disable them. - continue; - } -#endif Object *target = new Object(this, "PBXNativeTarget_" + _targets[i], "PBXNativeTarget", "PBXNativeTarget", "", _targets[i]); - target->addProperty("buildConfigurationList", getHash("XCConfigurationList_" + _targets[i]), "Build configuration list for PBXNativeTarget \"" + _targets[i] + "\"", SettingsNoValue); + target->addProperty("buildConfigurationList", getHash("XCConfigurationList_" + _targets[i]), "Build configuration list for PBXNativeTarget \"" + _targets[i] + "\"", kSettingsNoValue); Property buildPhases; - buildPhases.hasOrder = true; - buildPhases.flags = SettingsAsList; - buildPhases.settings[getHash("PBXResourcesBuildPhase_" + _targets[i])] = Setting("", "Resources", SettingsNoValue, 0, 0); - buildPhases.settings[getHash("PBXSourcesBuildPhase_" + _targets[i])] = Setting("", "Sources", SettingsNoValue, 0, 1); - buildPhases.settings[getHash("PBXFrameworksBuildPhase_" + _targets[i])] = Setting("", "Frameworks", SettingsNoValue, 0, 2); - target->properties["buildPhases"] = buildPhases; + buildPhases._hasOrder = true; + buildPhases._flags = kSettingsAsList; + buildPhases._settings[getHash("PBXResourcesBuildPhase_" + _targets[i])] = Setting("", "Resources", kSettingsNoValue, 0, 0); + buildPhases._settings[getHash("PBXSourcesBuildPhase_" + _targets[i])] = Setting("", "Sources", kSettingsNoValue, 0, 1); + buildPhases._settings[getHash("PBXFrameworksBuildPhase_" + _targets[i])] = Setting("", "Frameworks", kSettingsNoValue, 0, 2); + target->_properties["buildPhases"] = buildPhases; - target->addProperty("buildRules", "", "", SettingsNoValue|SettingsAsList); + target->addProperty("buildRules", "", "", kSettingsNoValue | kSettingsAsList); - target->addProperty("dependencies", "", "", SettingsNoValue|SettingsAsList); + target->addProperty("dependencies", "", "", kSettingsNoValue | kSettingsAsList); - target->addProperty("name", _targets[i], "", SettingsNoValue|SettingsQuoteVariable); - target->addProperty("productName", PROJECT_NAME, "", SettingsNoValue); + target->addProperty("name", _targets[i], "", kSettingsNoValue | kSettingsQuoteVariable); + target->addProperty("productName", PROJECT_NAME, "", kSettingsNoValue); addProductFileReference("PBXFileReference_" PROJECT_DESCRIPTION ".app_" + _targets[i], PROJECT_DESCRIPTION ".app"); productsGroup->addChildByHash(getHash("PBXFileReference_" PROJECT_DESCRIPTION ".app_" + _targets[i]), PROJECT_DESCRIPTION ".app"); - target->addProperty("productReference", getHash("PBXFileReference_" PROJECT_DESCRIPTION ".app_" + _targets[i]), PROJECT_DESCRIPTION ".app", SettingsNoValue); - target->addProperty("productType", "com.apple.product-type.application", "", SettingsNoValue|SettingsQuoteVariable); + target->addProperty("productReference", getHash("PBXFileReference_" PROJECT_DESCRIPTION ".app_" + _targets[i]), PROJECT_DESCRIPTION ".app", kSettingsNoValue); + target->addProperty("productType", "com.apple.product-type.application", "", kSettingsNoValue | kSettingsQuoteVariable); _nativeTarget.add(target); } @@ -548,225 +620,155 @@ void XcodeProvider::setupNativeTarget() { } void XcodeProvider::setupProject() { - _project.comment = "PBXProject"; + _project._comment = "PBXProject"; Object *project = new Object(this, "PBXProject", "PBXProject", "PBXProject", "", "Project object"); - project->addProperty("buildConfigurationList", getHash("XCConfigurationList_scummvm"), "Build configuration list for PBXProject \"" PROJECT_NAME "\"", SettingsNoValue); - project->addProperty("compatibilityVersion", "Xcode 3.2", "", SettingsNoValue|SettingsQuoteVariable); - project->addProperty("developmentRegion", "English", "", SettingsNoValue); - project->addProperty("hasScannedForEncodings", "1", "", SettingsNoValue); + project->addProperty("buildConfigurationList", getHash("XCConfigurationList_scummvm"), "Build configuration list for PBXProject \"" PROJECT_NAME "\"", kSettingsNoValue); + project->addProperty("compatibilityVersion", "Xcode 3.2", "", kSettingsNoValue | kSettingsQuoteVariable); + project->addProperty("developmentRegion", "English", "", kSettingsNoValue); + project->addProperty("hasScannedForEncodings", "1", "", kSettingsNoValue); // List of known regions Property regions; - regions.flags = SettingsAsList; + regions._flags = kSettingsAsList; ADD_SETTING_ORDER_NOVALUE(regions, "English", "", 0); ADD_SETTING_ORDER_NOVALUE(regions, "Japanese", "", 1); ADD_SETTING_ORDER_NOVALUE(regions, "French", "", 2); ADD_SETTING_ORDER_NOVALUE(regions, "German", "", 3); - project->properties["knownRegions"] = regions; + project->_properties["knownRegions"] = regions; - project->addProperty("mainGroup", _rootSourceGroup->getHashRef(), "CustomTemplate", SettingsNoValue); - project->addProperty("projectDirPath", _projectRoot, "", SettingsNoValue|SettingsQuoteVariable); - project->addProperty("projectRoot", "", "", SettingsNoValue|SettingsQuoteVariable); + project->addProperty("mainGroup", _rootSourceGroup->getHashRef(), "CustomTemplate", kSettingsNoValue); + project->addProperty("productRefGroup", getHash("PBXGroup_CustomTemplate_Products_"), "" , kSettingsNoValue); + project->addProperty("projectDirPath", _projectRoot, "", kSettingsNoValue | kSettingsQuoteVariable); + project->addProperty("projectRoot", "", "", kSettingsNoValue | kSettingsQuoteVariable); // List of targets Property targets; - targets.flags = SettingsAsList; -#ifdef ENABLE_IOS - targets.settings[getHash("PBXNativeTarget_" + _targets[IOS_TARGET])] = Setting("", _targets[IOS_TARGET], SettingsNoValue, 0, 0); -#endif - targets.settings[getHash("PBXNativeTarget_" + _targets[OSX_TARGET])] = Setting("", _targets[OSX_TARGET], SettingsNoValue, 0, 1); -#ifdef ENABLE_IOS - targets.settings[getHash("PBXNativeTarget_" + _targets[SIM_TARGET])] = Setting("", _targets[SIM_TARGET], SettingsNoValue, 0, 2); -#endif - project->properties["targets"] = targets; -#ifndef ENABLE_IOS + targets._flags = kSettingsAsList; + targets._settings[getHash("PBXNativeTarget_" + _targets[IOS_TARGET])] = Setting("", _targets[IOS_TARGET], kSettingsNoValue, 0, 0); + targets._settings[getHash("PBXNativeTarget_" + _targets[OSX_TARGET])] = Setting("", _targets[OSX_TARGET], kSettingsNoValue, 0, 1); + project->_properties["targets"] = targets; + // Force list even when there is only a single target - project->properties["targets"].flags |= SettingsSingleItem; -#endif + project->_properties["targets"]._flags |= kSettingsSingleItem; _project.add(project); } +XcodeProvider::ValueList& XcodeProvider::getResourceFiles() const { + static ValueList files; + if (files.empty()) { + files.push_back("gui/themes/scummclassic.zip"); + files.push_back("gui/themes/scummmodern.zip"); + files.push_back("gui/themes/translations.dat"); + files.push_back("dists/engine-data/drascula.dat"); + files.push_back("dists/engine-data/hugo.dat"); + files.push_back("dists/engine-data/kyra.dat"); + files.push_back("dists/engine-data/lure.dat"); + files.push_back("dists/engine-data/mort.dat"); + files.push_back("dists/engine-data/neverhood.dat"); + files.push_back("dists/engine-data/queen.tbl"); + files.push_back("dists/engine-data/sky.cpt"); + files.push_back("dists/engine-data/teenagent.dat"); + files.push_back("dists/engine-data/tony.dat"); + files.push_back("dists/engine-data/toon.dat"); + files.push_back("dists/engine-data/wintermute.zip"); + files.push_back("dists/pred.dic"); + files.push_back("icons/scummvm.icns"); + } + return files; +} + void XcodeProvider::setupResourcesBuildPhase() { - _resourcesBuildPhase.comment = "PBXResourcesBuildPhase"; + _resourcesBuildPhase._comment = "PBXResourcesBuildPhase"; - // Setup resource file properties - std::map<std::string, FileProperty> properties; - properties["scummclassic.zip"] = FileProperty("archive.zip", "", "scummclassic.zip", "\"<group>\""); - properties["scummmodern.zip"] = FileProperty("archive.zip", "", "scummmodern.zip", "\"<group>\""); - - properties["kyra.dat"] = FileProperty("file", "", "kyra.dat", "\"<group>\""); - properties["lure.dat"] = FileProperty("file", "", "lure.dat", "\"<group>\""); - properties["queen.tbl"] = FileProperty("file", "", "queen.tbl", "\"<group>\""); - properties["sky.cpt"] = FileProperty("file", "", "sky.cpt", "\"<group>\""); - properties["drascula.dat"] = FileProperty("file", "", "drascula.dat", "\"<group>\""); - properties["hugo.dat"] = FileProperty("file", "", "hugo.dat", "\"<group>\""); - properties["teenagent.dat"] = FileProperty("file", "", "teenagent.dat", "\"<group>\""); - properties["toon.dat"] = FileProperty("file", "", "toon.dat", "\"<group>\""); - - properties["Default.png"] = FileProperty("image.png", "", "Default.png", "\"<group>\""); - properties["icon.png"] = FileProperty("image.png", "", "icon.png", "\"<group>\""); - properties["icon-72.png"] = FileProperty("image.png", "", "icon-72.png", "\"<group>\""); - properties["icon4.png"] = FileProperty("image.png", "", "icon4.png", "\"<group>\""); + ValueList &files_list = getResourceFiles(); // Same as for containers: a rule for each native target for (unsigned int i = 0; i < _targets.size(); i++) { Object *resource = new Object(this, "PBXResourcesBuildPhase_" + _targets[i], "PBXResourcesBuildPhase", "PBXResourcesBuildPhase", "", "Resources"); - resource->addProperty("buildActionMask", "2147483647", "", SettingsNoValue); + resource->addProperty("buildActionMask", "2147483647", "", kSettingsNoValue); // Add default files Property files; - files.hasOrder = true; - files.flags = SettingsAsList; - - ValueList files_list; - files_list.push_back("scummclassic.zip"); - files_list.push_back("scummmodern.zip"); - files_list.push_back("kyra.dat"); - files_list.push_back("lure.dat"); - files_list.push_back("queen.tbl"); - files_list.push_back("sky.cpt"); - files_list.push_back("Default.png"); - files_list.push_back("icon.png"); - files_list.push_back("icon-72.png"); - files_list.push_back("icon4.png"); - files_list.push_back("drascula.dat"); - files_list.push_back("hugo.dat"); - files_list.push_back("teenagent.dat"); - files_list.push_back("toon.dat"); + files._hasOrder = true; + files._flags = kSettingsAsList; int order = 0; for (ValueList::iterator file = files_list.begin(); file != files_list.end(); file++) { - std::string id = "PBXResources_" + *file; - std::string comment = *file + " in Resources"; - - ADD_SETTING_ORDER_NOVALUE(files, getHash(id), comment, order++); - // TODO Fix crash when adding build file for data - //ADD_BUILD_FILE(id, *file, comment); - ADD_FILE_REFERENCE(*file, *file, properties[*file]); - } - - // Add custom files depending on the target - if (_targets[i] == PROJECT_DESCRIPTION "-OS X") { - files.settings[getHash("PBXResources_" PROJECT_NAME ".icns")] = Setting("", PROJECT_NAME ".icns in Resources", SettingsNoValue, 0, 6); - - // Remove 2 iphone icon files - files.settings.erase(getHash("PBXResources_Default.png")); - files.settings.erase(getHash("PBXResources_icon.png")); + if (shouldSkipFileForTarget(*file, _targets[i], *file)) { + continue; + } + std::string resourceAbsolutePath = _projectRoot + "/" + *file; + std::string file_id = "FileReference_" + resourceAbsolutePath; + std::string base = basename(*file); + std::string comment = base + " in Resources"; + addBuildFile(resourceAbsolutePath, base, getHash(file_id), comment); + ADD_SETTING_ORDER_NOVALUE(files, getHash(resourceAbsolutePath), comment, order++); } - resource->properties["files"] = files; + resource->_properties["files"] = files; - resource->addProperty("runOnlyForDeploymentPostprocessing", "0", "", SettingsNoValue); + resource->addProperty("runOnlyForDeploymentPostprocessing", "0", "", kSettingsNoValue); _resourcesBuildPhase.add(resource); } } void XcodeProvider::setupSourcesBuildPhase() { - _sourcesBuildPhase.comment = "PBXSourcesBuildPhase"; - - // Setup source file properties - std::map<std::string, FileProperty> properties; + _sourcesBuildPhase._comment = "PBXSourcesBuildPhase"; // Same as for containers: a rule for each native target for (unsigned int i = 0; i < _targets.size(); i++) { + const std::string &targetName = _targets[i]; Object *source = new Object(this, "PBXSourcesBuildPhase_" + _targets[i], "PBXSourcesBuildPhase", "PBXSourcesBuildPhase", "", "Sources"); - source->addProperty("buildActionMask", "2147483647", "", SettingsNoValue); + source->addProperty("buildActionMask", "2147483647", "", kSettingsNoValue); Property files; - files.hasOrder = true; - files.flags = SettingsAsList; + files._hasOrder = true; + files._flags = kSettingsAsList; int order = 0; - for (std::vector<Object*>::iterator file = _buildFile.objects.begin(); file !=_buildFile.objects.end(); ++file) { - if (!producesObjectFileOnOSX((*file)->name)) { + for (std::vector<Object *>::iterator file = _buildFile._objects.begin(); file != _buildFile._objects.end(); ++file) { + const std::string &fileName = (*file)->_name; + if (shouldSkipFileForTarget((*file)->_id, targetName, fileName)) { + continue; + } + if (!producesObjectFileOnOSX(fileName)) { continue; } - std::string comment = (*file)->name + " in Sources"; - ADD_SETTING_ORDER_NOVALUE(files, getHash((*file)->id), comment, order++); + std::string comment = fileName + " in Sources"; + ADD_SETTING_ORDER_NOVALUE(files, getHash((*file)->_id), comment, order++); } - source->properties["files"] = files; + setupAdditionalSources(targetName, files, order); - source->addProperty("runOnlyForDeploymentPostprocessing", "0", "", SettingsNoValue); + source->_properties["files"] = files; + + source->addProperty("runOnlyForDeploymentPostprocessing", "0", "", kSettingsNoValue); _sourcesBuildPhase.add(source); } } // Setup all build configurations -void XcodeProvider::setupBuildConfiguration() { +void XcodeProvider::setupBuildConfiguration(const BuildSetup &setup) { - _buildConfiguration.comment = "XCBuildConfiguration"; - _buildConfiguration.flags = SettingsAsList; + _buildConfiguration._comment = "XCBuildConfiguration"; + _buildConfiguration._flags = kSettingsAsList; - ///**************************************** - // * iPhone - // ****************************************/ -#ifdef ENABLE_IOS - // Debug - Object *iPhone_Debug_Object = new Object(this, "XCBuildConfiguration_" PROJECT_DESCRIPTION "-iPhone_Debug", _targets[IOS_TARGET] /* ScummVM-iPhone */, "XCBuildConfiguration", "PBXNativeTarget", "Debug"); - Property iPhone_Debug; - ADD_SETTING_QUOTE(iPhone_Debug, "ARCHS", "$(ARCHS_UNIVERSAL_IPHONE_OS)"); - ADD_SETTING_QUOTE(iPhone_Debug, "CODE_SIGN_IDENTITY", "iPhone Developer"); - ADD_SETTING_QUOTE_VAR(iPhone_Debug, "CODE_SIGN_IDENTITY[sdk=iphoneos*]", "iPhone Developer"); - ADD_SETTING(iPhone_Debug, "COMPRESS_PNG_FILES", "NO"); - ADD_SETTING(iPhone_Debug, "COPY_PHASE_STRIP", "NO"); - ADD_SETTING_QUOTE(iPhone_Debug, "DEBUG_INFORMATION_FORMAT", "dwarf-with-dsym"); - ValueList iPhone_FrameworkSearchPaths; - iPhone_FrameworkSearchPaths.push_back("$(inherited)"); - iPhone_FrameworkSearchPaths.push_back("\"$(SDKROOT)$(SYSTEM_LIBRARY_DIR)/PrivateFrameworks\""); - ADD_SETTING_LIST(iPhone_Debug, "FRAMEWORK_SEARCH_PATHS", iPhone_FrameworkSearchPaths, SettingsAsList, 5); - ADD_SETTING(iPhone_Debug, "GCC_DYNAMIC_NO_PIC", "NO"); - ADD_SETTING(iPhone_Debug, "GCC_ENABLE_CPP_EXCEPTIONS", "NO"); - ADD_SETTING(iPhone_Debug, "GCC_ENABLE_FIX_AND_CONTINUE", "NO"); - ADD_SETTING(iPhone_Debug, "GCC_OPTIMIZATION_LEVEL", "0"); - ADD_SETTING(iPhone_Debug, "GCC_PRECOMPILE_PREFIX_HEADER", "NO"); - ADD_SETTING_QUOTE(iPhone_Debug, "GCC_PREFIX_HEADER", ""); - ADD_SETTING(iPhone_Debug, "GCC_THUMB_SUPPORT", "NO"); - ADD_SETTING(iPhone_Debug, "GCC_UNROLL_LOOPS", "YES"); - ValueList iPhone_HeaderSearchPaths; - iPhone_HeaderSearchPaths.push_back("$(SRCROOT)/engines/"); - iPhone_HeaderSearchPaths.push_back("$(SRCROOT)"); - iPhone_HeaderSearchPaths.push_back("include/"); - ADD_SETTING_LIST(iPhone_Debug, "HEADER_SEARCH_PATHS", iPhone_HeaderSearchPaths, SettingsAsList|SettingsQuoteVariable, 5); - ADD_SETTING(iPhone_Debug, "INFOPLIST_FILE", "Info.plist"); - ValueList iPhone_LibPaths; - iPhone_LibPaths.push_back("$(inherited)"); - iPhone_LibPaths.push_back("\"$(SRCROOT)/lib\""); - ADD_SETTING_LIST(iPhone_Debug, "LIBRARY_SEARCH_PATHS", iPhone_LibPaths, SettingsAsList, 5); - ADD_SETTING(iPhone_Debug, "ONLY_ACTIVE_ARCH", "YES"); - ADD_SETTING(iPhone_Debug, "PREBINDING", "NO"); - ADD_SETTING(iPhone_Debug, "PRODUCT_NAME", PROJECT_DESCRIPTION); - ADD_SETTING_QUOTE(iPhone_Debug, "PROVISIONING_PROFILE", "EF590570-5FAC-4346-9071-D609DE2B28D8"); - ADD_SETTING_QUOTE_VAR(iPhone_Debug, "PROVISIONING_PROFILE[sdk=iphoneos*]", ""); - ADD_SETTING(iPhone_Debug, "SDKROOT", "iphoneos4.0"); - ADD_SETTING_QUOTE(iPhone_Debug, "TARGETED_DEVICE_FAMILY", "1,2"); - - iPhone_Debug_Object->addProperty("name", "Debug", "", SettingsNoValue); - iPhone_Debug_Object->properties["buildSettings"] = iPhone_Debug; - - // Release - Object *iPhone_Release_Object = new Object(this, "XCBuildConfiguration_" PROJECT_DESCRIPTION "-iPhone_Release", _targets[IOS_TARGET] /* ScummVM-iPhone */, "XCBuildConfiguration", "PBXNativeTarget", "Release"); - Property iPhone_Release(iPhone_Debug); - ADD_SETTING(iPhone_Release, "GCC_OPTIMIZATION_LEVEL", "3"); - ADD_SETTING(iPhone_Release, "COPY_PHASE_STRIP", "YES"); - REMOVE_SETTING(iPhone_Release, "GCC_DYNAMIC_NO_PIC"); - ADD_SETTING(iPhone_Release, "WRAPPER_EXTENSION", "app"); - - iPhone_Release_Object->addProperty("name", "Release", "", SettingsNoValue); - iPhone_Release_Object->properties["buildSettings"] = iPhone_Release; - - _buildConfiguration.add(iPhone_Debug_Object); - _buildConfiguration.add(iPhone_Release_Object); + std::string projectOutputDirectory; +#ifdef POSIX + char *rp = realpath(setup.outputDir.c_str(), NULL); + projectOutputDirectory = rp; + free(rp); #endif + /**************************************** - * scummvm + * ScummVM - Project Level ****************************************/ // Debug @@ -774,7 +776,6 @@ void XcodeProvider::setupBuildConfiguration() { Property scummvm_Debug; ADD_SETTING(scummvm_Debug, "ALWAYS_SEARCH_USER_PATHS", "NO"); ADD_SETTING_QUOTE(scummvm_Debug, "USER_HEADER_SEARCH_PATHS", "$(SRCROOT) $(SRCROOT)/engines"); - ADD_SETTING_QUOTE(scummvm_Debug, "ARCHS", "$(ARCHS_STANDARD_32_BIT)"); ADD_SETTING_QUOTE(scummvm_Debug, "CODE_SIGN_IDENTITY", "Don't Code Sign"); ADD_SETTING_QUOTE_VAR(scummvm_Debug, "CODE_SIGN_IDENTITY[sdk=iphoneos*]", "Don't Code Sign"); ADD_SETTING_QUOTE(scummvm_Debug, "FRAMEWORK_SEARCH_PATHS", ""); @@ -784,10 +785,12 @@ void XcodeProvider::setupBuildConfiguration() { ADD_SETTING(scummvm_Debug, "GCC_INPUT_FILETYPE", "automatic"); ADD_SETTING(scummvm_Debug, "GCC_OPTIMIZATION_LEVEL", "0"); ValueList scummvm_defines(_defines); - ADD_DEFINE(scummvm_defines, "IPHONE"); - ADD_DEFINE(scummvm_defines, "XCODE"); - ADD_DEFINE(scummvm_defines, "IPHONE_OFFICIAL"); - ADD_SETTING_LIST(scummvm_Debug, "GCC_PREPROCESSOR_DEFINITIONS", scummvm_defines, SettingsNoQuote|SettingsAsList, 5); + REMOVE_DEFINE(scummvm_defines, "MACOSX"); + REMOVE_DEFINE(scummvm_defines, "IPHONE"); + REMOVE_DEFINE(scummvm_defines, "IPHONE_IOS7"); + REMOVE_DEFINE(scummvm_defines, "IPHONE_SANDBOXED"); + REMOVE_DEFINE(scummvm_defines, "SDL_BACKEND"); + ADD_SETTING_LIST(scummvm_Debug, "GCC_PREPROCESSOR_DEFINITIONS", scummvm_defines, kSettingsNoQuote | kSettingsAsList, 5); ADD_SETTING(scummvm_Debug, "GCC_THUMB_SUPPORT", "NO"); ADD_SETTING(scummvm_Debug, "GCC_USE_GCC3_PFE_SUPPORT", "NO"); ADD_SETTING(scummvm_Debug, "GCC_WARN_ABOUT_RETURN_TYPE", "YES"); @@ -796,16 +799,16 @@ void XcodeProvider::setupBuildConfiguration() { scummvm_HeaderPaths.push_back("include/"); scummvm_HeaderPaths.push_back("$(SRCROOT)/engines/"); scummvm_HeaderPaths.push_back("$(SRCROOT)"); - ADD_SETTING_LIST(scummvm_Debug, "HEADER_SEARCH_PATHS", scummvm_HeaderPaths, SettingsQuoteVariable|SettingsAsList, 5); + ADD_SETTING_LIST(scummvm_Debug, "HEADER_SEARCH_PATHS", scummvm_HeaderPaths, kSettingsQuoteVariable | kSettingsAsList, 5); ADD_SETTING_QUOTE(scummvm_Debug, "LIBRARY_SEARCH_PATHS", ""); ADD_SETTING(scummvm_Debug, "ONLY_ACTIVE_ARCH", "YES"); ADD_SETTING_QUOTE(scummvm_Debug, "OTHER_CFLAGS", ""); ADD_SETTING_QUOTE(scummvm_Debug, "OTHER_LDFLAGS", "-lz"); ADD_SETTING(scummvm_Debug, "PREBINDING", "NO"); - ADD_SETTING(scummvm_Debug, "SDKROOT", "macosx"); + ADD_SETTING(scummvm_Debug, "ENABLE_TESTABILITY", "YES"); - scummvm_Debug_Object->addProperty("name", "Debug", "", SettingsNoValue); - scummvm_Debug_Object->properties["buildSettings"] = scummvm_Debug; + scummvm_Debug_Object->addProperty("name", "Debug", "", kSettingsNoValue); + scummvm_Debug_Object->_properties["buildSettings"] = scummvm_Debug; // Release Object *scummvm_Release_Object = new Object(this, "XCBuildConfiguration_" PROJECT_NAME "_Release", PROJECT_NAME, "XCBuildConfiguration", "PBXProject", "Release"); @@ -814,24 +817,100 @@ void XcodeProvider::setupBuildConfiguration() { REMOVE_SETTING(scummvm_Release, "GCC_WARN_ABOUT_RETURN_TYPE"); REMOVE_SETTING(scummvm_Release, "GCC_WARN_UNUSED_VARIABLE"); REMOVE_SETTING(scummvm_Release, "ONLY_ACTIVE_ARCH"); + REMOVE_SETTING(scummvm_Release, "ENABLE_TESTABILITY"); - scummvm_Release_Object->addProperty("name", "Release", "", SettingsNoValue); - scummvm_Release_Object->properties["buildSettings"] = scummvm_Release; + scummvm_Release_Object->addProperty("name", "Release", "", kSettingsNoValue); + scummvm_Release_Object->_properties["buildSettings"] = scummvm_Release; _buildConfiguration.add(scummvm_Debug_Object); _buildConfiguration.add(scummvm_Release_Object); + ///**************************************** + // * ScummVM - iOS Target + // ****************************************/ + + // Debug + Object *iPhone_Debug_Object = new Object(this, "XCBuildConfiguration_" PROJECT_DESCRIPTION "-iPhone_Debug", _targets[IOS_TARGET] /* ScummVM-iPhone */, "XCBuildConfiguration", "PBXNativeTarget", "Debug"); + Property iPhone_Debug; + ADD_SETTING_QUOTE(iPhone_Debug, "CODE_SIGN_IDENTITY", "iPhone Developer"); + ADD_SETTING_QUOTE_VAR(iPhone_Debug, "CODE_SIGN_IDENTITY[sdk=iphoneos*]", "iPhone Developer"); + ADD_SETTING(iPhone_Debug, "COMPRESS_PNG_FILES", "NO"); + ADD_SETTING(iPhone_Debug, "COPY_PHASE_STRIP", "NO"); + ADD_SETTING_QUOTE(iPhone_Debug, "DEBUG_INFORMATION_FORMAT", "dwarf"); + ValueList iPhone_FrameworkSearchPaths; + iPhone_FrameworkSearchPaths.push_back("$(inherited)"); + iPhone_FrameworkSearchPaths.push_back("\"$(SDKROOT)$(SYSTEM_LIBRARY_DIR)/PrivateFrameworks\""); + ADD_SETTING_LIST(iPhone_Debug, "FRAMEWORK_SEARCH_PATHS", iPhone_FrameworkSearchPaths, kSettingsAsList, 5); + ADD_SETTING(iPhone_Debug, "GCC_DYNAMIC_NO_PIC", "NO"); + ADD_SETTING(iPhone_Debug, "GCC_ENABLE_CPP_EXCEPTIONS", "NO"); + ADD_SETTING(iPhone_Debug, "GCC_ENABLE_FIX_AND_CONTINUE", "NO"); + ADD_SETTING(iPhone_Debug, "GCC_OPTIMIZATION_LEVEL", "0"); + ADD_SETTING(iPhone_Debug, "GCC_PRECOMPILE_PREFIX_HEADER", "NO"); + ADD_SETTING(iPhone_Debug, "GCC_WARN_64_TO_32_BIT_CONVERSION", "NO"); + ADD_SETTING(iPhone_Debug, "WARNING_CFLAGS", "-Wno-multichar"); + ADD_SETTING_QUOTE(iPhone_Debug, "GCC_PREFIX_HEADER", ""); + ADD_SETTING(iPhone_Debug, "GCC_THUMB_SUPPORT", "NO"); + ADD_SETTING(iPhone_Debug, "GCC_UNROLL_LOOPS", "YES"); + ValueList iPhone_HeaderSearchPaths; + iPhone_HeaderSearchPaths.push_back("$(SRCROOT)/engines/"); + iPhone_HeaderSearchPaths.push_back("$(SRCROOT)"); + iPhone_HeaderSearchPaths.push_back("\"" + projectOutputDirectory + "\""); + iPhone_HeaderSearchPaths.push_back("\"" + projectOutputDirectory + "/include\""); + ADD_SETTING_LIST(iPhone_Debug, "HEADER_SEARCH_PATHS", iPhone_HeaderSearchPaths, kSettingsAsList | kSettingsQuoteVariable, 5); + ADD_SETTING_QUOTE(iPhone_Debug, "INFOPLIST_FILE", "$(SRCROOT)/dists/ios7/Info.plist"); + ValueList iPhone_LibPaths; + iPhone_LibPaths.push_back("$(inherited)"); + iPhone_LibPaths.push_back("\"" + projectOutputDirectory + "/lib\""); + ADD_SETTING_LIST(iPhone_Debug, "LIBRARY_SEARCH_PATHS", iPhone_LibPaths, kSettingsAsList, 5); + ADD_SETTING(iPhone_Debug, "ONLY_ACTIVE_ARCH", "YES"); + ADD_SETTING(iPhone_Debug, "PREBINDING", "NO"); + ADD_SETTING(iPhone_Debug, "PRODUCT_NAME", PROJECT_NAME); + ADD_SETTING(iPhone_Debug, "PRODUCT_BUNDLE_IDENTIFIER", "\"org.scummvm.${PRODUCT_NAME}\""); + ADD_SETTING(iPhone_Debug, "IPHONEOS_DEPLOYMENT_TARGET", "7.1"); + //ADD_SETTING_QUOTE(iPhone_Debug, "PROVISIONING_PROFILE", "EF590570-5FAC-4346-9071-D609DE2B28D8"); + ADD_SETTING_QUOTE_VAR(iPhone_Debug, "PROVISIONING_PROFILE[sdk=iphoneos*]", ""); + ADD_SETTING(iPhone_Debug, "SDKROOT", "iphoneos"); + ADD_SETTING_QUOTE(iPhone_Debug, "TARGETED_DEVICE_FAMILY", "1,2"); + ValueList scummvmIOS_defines; + ADD_DEFINE(scummvmIOS_defines, "\"$(inherited)\""); + ADD_DEFINE(scummvmIOS_defines, "IPHONE"); + ADD_DEFINE(scummvmIOS_defines, "IPHONE_IOS7"); + ADD_DEFINE(scummvmIOS_defines, "IPHONE_SANDBOXED"); + ADD_SETTING_LIST(iPhone_Debug, "GCC_PREPROCESSOR_DEFINITIONS", scummvmIOS_defines, kSettingsNoQuote | kSettingsAsList, 5); + ADD_SETTING(iPhone_Debug, "ASSETCATALOG_COMPILER_APPICON_NAME", "AppIcon"); + ADD_SETTING(iPhone_Debug, "ASSETCATALOG_COMPILER_LAUNCHIMAGE_NAME", "LaunchImage"); + + iPhone_Debug_Object->addProperty("name", "Debug", "", kSettingsNoValue); + iPhone_Debug_Object->_properties["buildSettings"] = iPhone_Debug; + + // Release + Object *iPhone_Release_Object = new Object(this, "XCBuildConfiguration_" PROJECT_DESCRIPTION "-iPhone_Release", _targets[IOS_TARGET] /* ScummVM-iPhone */, "XCBuildConfiguration", "PBXNativeTarget", "Release"); + Property iPhone_Release(iPhone_Debug); + ADD_SETTING(iPhone_Release, "GCC_OPTIMIZATION_LEVEL", "3"); + ADD_SETTING(iPhone_Release, "COPY_PHASE_STRIP", "YES"); + REMOVE_SETTING(iPhone_Release, "GCC_DYNAMIC_NO_PIC"); + ADD_SETTING(iPhone_Release, "WRAPPER_EXTENSION", "app"); + REMOVE_SETTING(iPhone_Release, "DEBUG_INFORMATION_FORMAT"); + ADD_SETTING_QUOTE(iPhone_Release, "DEBUG_INFORMATION_FORMAT", "dwarf-with-dsym"); + + iPhone_Release_Object->addProperty("name", "Release", "", kSettingsNoValue); + iPhone_Release_Object->_properties["buildSettings"] = iPhone_Release; + + _buildConfiguration.add(iPhone_Debug_Object); + _buildConfiguration.add(iPhone_Release_Object); + /**************************************** - * ScummVM-OS X + * ScummVM - OS X Target ****************************************/ // Debug Object *scummvmOSX_Debug_Object = new Object(this, "XCBuildConfiguration_" PROJECT_DESCRIPTION "-OSX_Debug", _targets[OSX_TARGET] /* ScummVM-OS X */, "XCBuildConfiguration", "PBXNativeTarget", "Debug"); Property scummvmOSX_Debug; - ADD_SETTING_QUOTE(scummvmOSX_Debug, "ARCHS", "$(NATIVE_ARCH)"); + ADD_SETTING(scummvmOSX_Debug, "COMBINE_HIDPI_IMAGES", "YES"); + ADD_SETTING(scummvmOSX_Debug, "SDKROOT", "macosx"); ADD_SETTING(scummvmOSX_Debug, "COMPRESS_PNG_FILES", "NO"); ADD_SETTING(scummvmOSX_Debug, "COPY_PHASE_STRIP", "NO"); - ADD_SETTING_QUOTE(scummvmOSX_Debug, "DEBUG_INFORMATION_FORMAT", "dwarf-with-dsym"); + ADD_SETTING_QUOTE(scummvmOSX_Debug, "DEBUG_INFORMATION_FORMAT", "dwarf"); ADD_SETTING_QUOTE(scummvmOSX_Debug, "FRAMEWORK_SEARCH_PATHS", ""); ADD_SETTING(scummvmOSX_Debug, "GCC_C_LANGUAGE_STANDARD", "c99"); ADD_SETTING(scummvmOSX_Debug, "GCC_ENABLE_CPP_EXCEPTIONS", "NO"); @@ -841,29 +920,33 @@ void XcodeProvider::setupBuildConfiguration() { ADD_SETTING(scummvmOSX_Debug, "GCC_OPTIMIZATION_LEVEL", "0"); ADD_SETTING(scummvmOSX_Debug, "GCC_PRECOMPILE_PREFIX_HEADER", "NO"); ADD_SETTING_QUOTE(scummvmOSX_Debug, "GCC_PREFIX_HEADER", ""); - ValueList scummvmOSX_defines(_defines); + ValueList scummvmOSX_defines; + ADD_DEFINE(scummvmOSX_defines, "\"$(inherited)\""); ADD_DEFINE(scummvmOSX_defines, "SDL_BACKEND"); ADD_DEFINE(scummvmOSX_defines, "MACOSX"); - ADD_SETTING_LIST(scummvmOSX_Debug, "GCC_PREPROCESSOR_DEFINITIONS", scummvmOSX_defines, SettingsNoQuote|SettingsAsList, 5); + ADD_SETTING_LIST(scummvmOSX_Debug, "GCC_PREPROCESSOR_DEFINITIONS", scummvmOSX_defines, kSettingsNoQuote | kSettingsAsList, 5); ADD_SETTING_QUOTE(scummvmOSX_Debug, "GCC_VERSION", ""); ValueList scummvmOSX_HeaderPaths; - scummvmOSX_HeaderPaths.push_back("/opt/local/include/SDL"); + if (setup.useSDL2) { + scummvmOSX_HeaderPaths.push_back("/opt/local/include/SDL2"); + } else { + scummvmOSX_HeaderPaths.push_back("/opt/local/include/SDL"); + } scummvmOSX_HeaderPaths.push_back("/opt/local/include"); scummvmOSX_HeaderPaths.push_back("/opt/local/include/freetype2"); scummvmOSX_HeaderPaths.push_back("include/"); scummvmOSX_HeaderPaths.push_back("$(SRCROOT)/engines/"); scummvmOSX_HeaderPaths.push_back("$(SRCROOT)"); - ADD_SETTING_LIST(scummvmOSX_Debug, "HEADER_SEARCH_PATHS", scummvmOSX_HeaderPaths, SettingsQuoteVariable|SettingsAsList, 5); + ADD_SETTING_LIST(scummvmOSX_Debug, "HEADER_SEARCH_PATHS", scummvmOSX_HeaderPaths, kSettingsQuoteVariable | kSettingsAsList, 5); ADD_SETTING_QUOTE(scummvmOSX_Debug, "INFOPLIST_FILE", "$(SRCROOT)/dists/macosx/Info.plist"); ValueList scummvmOSX_LibPaths; scummvmOSX_LibPaths.push_back("/sw/lib"); scummvmOSX_LibPaths.push_back("/opt/local/lib"); scummvmOSX_LibPaths.push_back("\"$(inherited)\""); scummvmOSX_LibPaths.push_back("\"\\\\\\\"$(SRCROOT)/lib\\\\\\\"\""); // mmmh, all those slashes, it's almost Christmas \o/ - ADD_SETTING_LIST(scummvmOSX_Debug, "LIBRARY_SEARCH_PATHS", scummvmOSX_LibPaths, SettingsNoQuote|SettingsAsList, 5); + ADD_SETTING_LIST(scummvmOSX_Debug, "LIBRARY_SEARCH_PATHS", scummvmOSX_LibPaths, kSettingsNoQuote | kSettingsAsList, 5); ADD_SETTING_QUOTE(scummvmOSX_Debug, "OTHER_CFLAGS", ""); ValueList scummvmOSX_LdFlags; - scummvmOSX_LdFlags.push_back("-lSDLmain"); scummvmOSX_LdFlags.push_back("-logg"); scummvmOSX_LdFlags.push_back("-lpng"); scummvmOSX_LdFlags.push_back("-ljpeg"); @@ -873,14 +956,20 @@ void XcodeProvider::setupBuildConfiguration() { scummvmOSX_LdFlags.push_back("-lvorbis"); scummvmOSX_LdFlags.push_back("-lmad"); scummvmOSX_LdFlags.push_back("-lFLAC"); - scummvmOSX_LdFlags.push_back("-lSDL"); + if (setup.useSDL2) { + scummvmOSX_LdFlags.push_back("-lSDL2main"); + scummvmOSX_LdFlags.push_back("-lSDL2"); + } else { + scummvmOSX_LdFlags.push_back("-lSDLmain"); + scummvmOSX_LdFlags.push_back("-lSDL"); + } scummvmOSX_LdFlags.push_back("-lz"); - ADD_SETTING_LIST(scummvmOSX_Debug, "OTHER_LDFLAGS", scummvmOSX_LdFlags, SettingsAsList, 5); + ADD_SETTING_LIST(scummvmOSX_Debug, "OTHER_LDFLAGS", scummvmOSX_LdFlags, kSettingsAsList, 5); ADD_SETTING(scummvmOSX_Debug, "PREBINDING", "NO"); - ADD_SETTING(scummvmOSX_Debug, "PRODUCT_NAME", PROJECT_DESCRIPTION); + ADD_SETTING(scummvmOSX_Debug, "PRODUCT_NAME", PROJECT_NAME); - scummvmOSX_Debug_Object->addProperty("name", "Debug", "", SettingsNoValue); - scummvmOSX_Debug_Object->properties["buildSettings"] = scummvmOSX_Debug; + scummvmOSX_Debug_Object->addProperty("name", "Debug", "", kSettingsNoValue); + scummvmOSX_Debug_Object->_properties["buildSettings"] = scummvmOSX_Debug; // Release Object *scummvmOSX_Release_Object = new Object(this, "XCBuildConfiguration_" PROJECT_DESCRIPTION "-OSX_Release", _targets[OSX_TARGET] /* ScummVM-OS X */, "XCBuildConfiguration", "PBXNativeTarget", "Release"); @@ -889,68 +978,51 @@ void XcodeProvider::setupBuildConfiguration() { REMOVE_SETTING(scummvmOSX_Release, "GCC_DYNAMIC_NO_PIC"); REMOVE_SETTING(scummvmOSX_Release, "GCC_OPTIMIZATION_LEVEL"); ADD_SETTING(scummvmOSX_Release, "WRAPPER_EXTENSION", "app"); + REMOVE_SETTING(scummvmOSX_Release, "DEBUG_INFORMATION_FORMAT"); + ADD_SETTING_QUOTE(scummvmOSX_Release, "DEBUG_INFORMATION_FORMAT", "dwarf-with-dsym"); - scummvmOSX_Release_Object->addProperty("name", "Release", "", SettingsNoValue); - scummvmOSX_Release_Object->properties["buildSettings"] = scummvmOSX_Release; + scummvmOSX_Release_Object->addProperty("name", "Release", "", kSettingsNoValue); + scummvmOSX_Release_Object->_properties["buildSettings"] = scummvmOSX_Release; _buildConfiguration.add(scummvmOSX_Debug_Object); _buildConfiguration.add(scummvmOSX_Release_Object); -#ifdef ENABLE_IOS - /**************************************** - * ScummVM-Simulator - ****************************************/ - - // Debug - Object *scummvmSimulator_Debug_Object = new Object(this, "XCBuildConfiguration_" PROJECT_DESCRIPTION "-Simulator_Debug", _targets[SIM_TARGET] /* ScummVM-Simulator */, "XCBuildConfiguration", "PBXNativeTarget", "Debug"); - Property scummvmSimulator_Debug(iPhone_Debug); - ADD_SETTING_QUOTE(scummvmSimulator_Debug, "FRAMEWORK_SEARCH_PATHS", "$(inherited)"); - ADD_SETTING_LIST(scummvmSimulator_Debug, "GCC_PREPROCESSOR_DEFINITIONS", scummvm_defines, SettingsNoQuote|SettingsAsList, 5); - ADD_SETTING(scummvmSimulator_Debug, "SDKROOT", "iphonesimulator3.2"); - ADD_SETTING_QUOTE(scummvmSimulator_Debug, "VALID_ARCHS", "i386 x86_64"); - REMOVE_SETTING(scummvmSimulator_Debug, "TARGETED_DEVICE_FAMILY"); - - scummvmSimulator_Debug_Object->addProperty("name", "Debug", "", SettingsNoValue); - scummvmSimulator_Debug_Object->properties["buildSettings"] = scummvmSimulator_Debug; - - // Release - Object *scummvmSimulator_Release_Object = new Object(this, "XCBuildConfiguration_" PROJECT_DESCRIPTION "-Simulator_Release", _targets[SIM_TARGET] /* ScummVM-Simulator */, "XCBuildConfiguration", "PBXNativeTarget", "Release"); - Property scummvmSimulator_Release(scummvmSimulator_Debug); - ADD_SETTING(scummvmSimulator_Release, "COPY_PHASE_STRIP", "YES"); - ADD_SETTING(scummvmSimulator_Release, "GCC_OPTIMIZATION_LEVEL", "3"); - REMOVE_SETTING(scummvmSimulator_Release, "GCC_DYNAMIC_NO_PIC"); - ADD_SETTING(scummvmSimulator_Release, "WRAPPER_EXTENSION", "app"); - - scummvmSimulator_Release_Object->addProperty("name", "Release", "", SettingsNoValue); - scummvmSimulator_Release_Object->properties["buildSettings"] = scummvmSimulator_Release; - - _buildConfiguration.add(scummvmSimulator_Debug_Object); - _buildConfiguration.add(scummvmSimulator_Release_Object); - ////////////////////////////////////////////////////////////////////////// - // Configuration List - _configurationList.comment = "XCConfigurationList"; - _configurationList.flags = SettingsAsList; -#endif // Warning: This assumes we have all configurations with a Debug & Release pair - for (std::vector<Object *>::iterator config = _buildConfiguration.objects.begin(); config != _buildConfiguration.objects.end(); config++) { + for (std::vector<Object *>::iterator config = _buildConfiguration._objects.begin(); config != _buildConfiguration._objects.end(); config++) { - Object *configList = new Object(this, "XCConfigurationList_" + (*config)->name, (*config)->name, "XCConfigurationList", "", "Build configuration list for " + (*config)->refType + " \"" + (*config)->name + "\""); + Object *configList = new Object(this, "XCConfigurationList_" + (*config)->_name, (*config)->_name, "XCConfigurationList", "", "Build configuration list for " + (*config)->_refType + " \"" + (*config)->_name + "\""); Property buildConfigs; - buildConfigs.flags = SettingsAsList; + buildConfigs._flags = kSettingsAsList; - buildConfigs.settings[getHash((*config)->id)] = Setting("", "Debug", SettingsNoValue, 0, 0); - buildConfigs.settings[getHash((*(++config))->id)] = Setting("", "Release", SettingsNoValue, 0, 1); + buildConfigs._settings[getHash((*config)->_id)] = Setting("", "Debug", kSettingsNoValue, 0, 0); + buildConfigs._settings[getHash((*(++config))->_id)] = Setting("", "Release", kSettingsNoValue, 0, 1); - configList->properties["buildConfigurations"] = buildConfigs; + configList->_properties["buildConfigurations"] = buildConfigs; - configList->addProperty("defaultConfigurationIsVisible", "0", "", SettingsNoValue); - configList->addProperty("defaultConfigurationName", "Release", "", SettingsNoValue); + configList->addProperty("defaultConfigurationIsVisible", "0", "", kSettingsNoValue); + configList->addProperty("defaultConfigurationName", "Release", "", kSettingsNoValue); _configurationList.add(configList); } } +void XcodeProvider::setupImageAssetCatalog(const BuildSetup &setup) { + const std::string filename = "Images.xcassets"; + const std::string absoluteCatalogPath = _projectRoot + "/dists/ios7/" + filename; + const std::string id = "FileReference_" + absoluteCatalogPath; + Group *group = touchGroupsForPath(absoluteCatalogPath); + group->addChildFile(filename); + addBuildFile(absoluteCatalogPath, filename, getHash(id), "Image Asset Catalog"); +} + +void XcodeProvider::setupAdditionalSources(std::string targetName, Property &files, int &order) { + if (targetIsIOS(targetName)) { + const std::string absoluteCatalogPath = _projectRoot + "/dists/ios7/Images.xcassets"; + ADD_SETTING_ORDER_NOVALUE(files, getHash(absoluteCatalogPath), "Image Asset Catalog", order++); + } +} + ////////////////////////////////////////////////////////////////////////// // Misc ////////////////////////////////////////////////////////////////////////// @@ -959,15 +1031,18 @@ void XcodeProvider::setupBuildConfiguration() { void XcodeProvider::setupDefines(const BuildSetup &setup) { for (StringList::const_iterator i = setup.defines.begin(); i != setup.defines.end(); ++i) { - if (*i == "HAVE_NASM") // Not supported on Mac (TODO: change how it's handled in main class or add it only in MSVC/CodeBlocks providers?) + if (*i == "HAVE_NASM") // Not supported on Mac (TODO: change how it's handled in main class or add it only in MSVC/CodeBlocks providers?) continue; ADD_DEFINE(_defines, *i); } // Add special defines for Mac support + REMOVE_DEFINE(_defines, "MACOSX"); + REMOVE_DEFINE(_defines, "IPHONE"); + REMOVE_DEFINE(_defines, "IPHONE_IOS7"); + REMOVE_DEFINE(_defines, "IPHONE_SANDBOXED"); + REMOVE_DEFINE(_defines, "SDL_BACKEND"); ADD_DEFINE(_defines, "CONFIG_H"); - ADD_DEFINE(_defines, "SCUMM_NEED_ALIGNMENT"); - ADD_DEFINE(_defines, "SCUMM_LITTLE_ENDIAN"); ADD_DEFINE(_defines, "UNIX"); ADD_DEFINE(_defines, "SCUMMVM"); } @@ -976,7 +1051,6 @@ void XcodeProvider::setupDefines(const BuildSetup &setup) { // Object hash ////////////////////////////////////////////////////////////////////////// -// TODO use md5 to compute a file hash (and fall back to standard key generation if not passed a file) std::string XcodeProvider::getHash(std::string key) { #if DEBUG_XCODE_HASH @@ -988,14 +1062,32 @@ std::string XcodeProvider::getHash(std::string key) { return hashIterator->second; // Generate a new key from the file hash and insert it into the dictionary +#ifdef MACOSX + std::string hash = md5(key); +#else std::string hash = newHash(); +#endif + _hashDictionnary[key] = hash; return hash; #endif } -bool isSeparator (char s) { return (s == '-'); } +bool isSeparator(char s) { return (s == '-'); } + +#ifdef MACOSX +std::string XcodeProvider::md5(std::string key) { + unsigned char md[CC_MD5_DIGEST_LENGTH]; + CC_MD5(key.c_str(), (CC_LONG) key.length(), md); + std::stringstream stream; + stream << std::hex << std::setfill('0') << std::setw(2); + for (int i=0; i<CC_MD5_DIGEST_LENGTH; i++) { + stream << (unsigned int) md[i]; + } + return stream.str(); +} +#endif std::string XcodeProvider::newHash() const { std::string hash = createUUID(); @@ -1018,10 +1110,10 @@ std::string replace(std::string input, const std::string find, std::string repla std::string::size_type findLen = find.length(); std::string::size_type replaceLen = replaceStr.length(); - if (findLen == 0 ) + if (findLen == 0) return input; - for (;(pos = input.find(find, pos)) != std::string::npos;) { + for (; (pos = input.find(find, pos)) != std::string::npos;) { input.replace(pos, findLen, replaceStr); pos += replaceLen; } @@ -1032,30 +1124,30 @@ std::string replace(std::string input, const std::string find, std::string repla std::string XcodeProvider::writeProperty(const std::string &variable, Property &prop, int flags) const { std::string output; - output += (flags & SettingsSingleItem ? "" : "\t\t\t") + variable + " = "; + output += (flags & kSettingsSingleItem ? "" : "\t\t\t") + variable + " = "; - if (prop.settings.size() > 1 || (prop.flags & SettingsSingleItem)) - output += (prop.flags & SettingsAsList) ? "(\n" : "{\n"; + if (prop._settings.size() > 1 || (prop._flags & kSettingsSingleItem)) + output += (prop._flags & kSettingsAsList) ? "(\n" : "{\n"; OrderedSettingList settings = prop.getOrderedSettingList(); for (OrderedSettingList::const_iterator setting = settings.begin(); setting != settings.end(); ++setting) { - if (settings.size() > 1 || (prop.flags & SettingsSingleItem)) - output += (flags & SettingsSingleItem ? " " : "\t\t\t\t"); + if (settings.size() > 1 || (prop._flags & kSettingsSingleItem)) + output += (flags & kSettingsSingleItem ? " " : "\t\t\t\t"); - output += writeSetting((*setting).first, (*setting).second); + output += writeSetting(setting->first, setting->second); - // The combination of SettingsAsList, and SettingsSingleItem should use "," and not ";" (i.e children + // The combination of kSettingsAsList, and kSettingsSingleItem should use "," and not ";" (i.e children // in PBXGroup, so we special case that case here. - if ((prop.flags & SettingsAsList) && (prop.settings.size() > 1 || (prop.flags & SettingsSingleItem))) { - output += (prop.settings.size() > 0) ? ",\n" : "\n"; + if ((prop._flags & kSettingsAsList) && (prop._settings.size() > 1 || (prop._flags & kSettingsSingleItem))) { + output += (prop._settings.size() > 0) ? ",\n" : "\n"; } else { output += ";"; - output += (flags & SettingsSingleItem ? " " : "\n"); + output += (flags & kSettingsSingleItem ? " " : "\n"); } } - if (prop.settings.size() > 1 || (prop.flags & SettingsSingleItem)) - output += (prop.flags & SettingsAsList) ? "\t\t\t);\n" : "\t\t\t};\n"; + if (prop._settings.size() > 1 || (prop._flags & kSettingsSingleItem)) + output += (prop._flags & kSettingsAsList) ? "\t\t\t);\n" : "\t\t\t};\n"; return output; } @@ -1068,32 +1160,31 @@ std::string XcodeProvider::writeSetting(const std::string &variable, std::string // XCode project generator pbuilder_pbx.cpp, writeSettings() (under LGPL 2.1) std::string XcodeProvider::writeSetting(const std::string &variable, const Setting &setting) const { std::string output; - const std::string quote = (setting.flags & SettingsNoQuote) ? "" : "\""; + const std::string quote = (setting._flags & kSettingsNoQuote) ? "" : "\""; const std::string escape_quote = quote.empty() ? "" : "\\" + quote; std::string newline = "\n"; // Get indent level - for (int i = 0; i < setting.indent; ++i) + for (int i = 0; i < setting._indent; ++i) newline += "\t"; // Setup variable - std::string var = (setting.flags & SettingsQuoteVariable) ? "\"" + variable + "\"" : variable; + std::string var = (setting._flags & kSettingsQuoteVariable) ? "\"" + variable + "\"" : variable; // Output a list - if (setting.flags & SettingsAsList) { - - output += var + ((setting.flags & SettingsNoValue) ? "(" : " = (") + newline; + if (setting._flags & kSettingsAsList) { + output += var + ((setting._flags & kSettingsNoValue) ? "(" : " = (") + newline; - for (unsigned int i = 0, count = 0; i < setting.entries.size(); ++i) { + for (unsigned int i = 0, count = 0; i < setting._entries.size(); ++i) { - std::string value = setting.entries.at(i).value; + std::string value = setting._entries.at(i)._value; if (!value.empty()) { if (count++ > 0) output += "," + newline; output += quote + replace(value, quote, escape_quote) + quote; - std::string comment = setting.entries.at(i).comment; + std::string comment = setting._entries.at(i)._comment; if (!comment.empty()) output += " /* " + comment + " */"; } @@ -1101,24 +1192,24 @@ std::string XcodeProvider::writeSetting(const std::string &variable, const Setti } // Add closing ")" on new line newline.resize(newline.size() - 1); - output += (setting.flags & SettingsNoValue) ? "\t\t\t)" : "," + newline + ")"; + output += (setting._flags & kSettingsNoValue) ? "\t\t\t)" : "," + newline + ")"; } else { output += var; - output += (setting.flags & SettingsNoValue) ? "" : " = " + quote; + output += (setting._flags & kSettingsNoValue) ? "" : " = " + quote; - for(unsigned int i = 0; i < setting.entries.size(); ++i) { - std::string value = setting.entries.at(i).value; - if(i) + for (unsigned int i = 0; i < setting._entries.size(); ++i) { + std::string value = setting._entries.at(i)._value; + if (i) output += " "; output += value; - std::string comment = setting.entries.at(i).comment; + std::string comment = setting._entries.at(i)._comment; if (!comment.empty()) output += " /* " + comment + " */"; } - output += (setting.flags & SettingsNoValue) ? "" : quote; + output += (setting._flags & kSettingsNoValue) ? "" : quote; } return output; } diff --git a/devtools/create_project/xcode.h b/devtools/create_project/xcode.h index 2686d14986..d495dd0dfd 100644 --- a/devtools/create_project/xcode.h +++ b/devtools/create_project/xcode.h @@ -40,6 +40,8 @@ protected: void createOtherBuildFiles(const BuildSetup &setup); + void addResourceFiles(const BuildSetup &setup, StringList &includeList, StringList &excludeList); + void createProjectFile(const std::string &name, const std::string &uuid, const BuildSetup &setup, const std::string &moduleDir, const StringList &includeList, const StringList &excludeList); @@ -47,24 +49,23 @@ protected: const StringList &duplicate, const std::string &objPrefix, const std::string &filePrefix); private: enum { - SettingsAsList = 0x01, - SettingsSingleItem = 0x02, - SettingsNoQuote = 0x04, - SettingsQuoteVariable = 0x08, - SettingsNoValue = 0x10 + kSettingsAsList = 0x01, + kSettingsSingleItem = 0x02, + kSettingsNoQuote = 0x04, + kSettingsQuoteVariable = 0x08, + kSettingsNoValue = 0x10 }; // File properties struct FileProperty { - std::string fileEncoding; - std::string lastKnownFileType; - std::string fileName; - std::string filePath; - std::string sourceTree; - - FileProperty(std::string fileType = "", std::string name = "", std::string path = "", std::string source = "") : - fileEncoding(""), lastKnownFileType(fileType), fileName(name), filePath(path), sourceTree(source) - { + std::string _fileEncoding; + std::string _lastKnownFileType; + std::string _fileName; + std::string _filePath; + std::string _sourceTree; + + FileProperty(std::string fileType = "", std::string name = "", std::string path = "", std::string source = "") + : _fileEncoding(""), _lastKnownFileType(fileType), _fileName(name), _filePath(path), _sourceTree(source) { } }; @@ -73,33 +74,33 @@ private: typedef std::vector<std::string> ValueList; struct Entry { - std::string value; - std::string comment; + std::string _value; + std::string _comment; - Entry(std::string val, std::string cmt) : value(val), comment(cmt) {} + Entry(std::string val, std::string cmt) : _value(val), _comment(cmt) {} }; typedef std::vector<Entry> EntryList; struct Setting { - EntryList entries; - int flags; - int indent; - int order; + EntryList _entries; + int _flags; + int _indent; + int _order; - explicit Setting(std::string value = "", std::string comment = "", int flgs = 0, int idt = 0, int ord = -1) : flags(flgs), indent(idt), order(ord) { - entries.push_back(Entry(value, comment)); + Setting(std::string value = "", std::string comment = "", int flgs = 0, int idt = 0, int ord = -1) : _flags(flgs), _indent(idt), _order(ord) { + _entries.push_back(Entry(value, comment)); } - explicit Setting(ValueList values, int flgs = 0, int idt = 0, int ord = -1) : flags(flgs), indent(idt), order(ord) { + Setting(ValueList values, int flgs = 0, int idt = 0, int ord = -1) : _flags(flgs), _indent(idt), _order(ord) { for (unsigned int i = 0; i < values.size(); i++) - entries.push_back(Entry(values[i], "")); + _entries.push_back(Entry(values[i], "")); } - explicit Setting(EntryList ents, int flgs = 0, int idt = 0, int ord = -1) : entries(ents), flags(flgs), indent(idt), order(ord) {} + Setting(EntryList ents, int flgs = 0, int idt = 0, int ord = -1) : _entries(ents), _flags(flgs), _indent(idt), _order(ord) {} void addEntry(std::string value, std::string comment = "") { - entries.push_back(Entry(value, comment)); + _entries.push_back(Entry(value, comment)); } }; @@ -107,46 +108,36 @@ private: typedef std::pair<std::string, Setting> SettingPair; typedef std::vector<SettingPair> OrderedSettingList; - static bool OrderSortPredicate(const SettingPair& s1, const SettingPair& s2) { - return s1.second.order < s2.second.order; + static bool OrderSortPredicate(const SettingPair &s1, const SettingPair &s2) { + return s1.second._order < s2.second._order; } struct Property { public: - SettingList settings; - int flags; - bool hasOrder; + SettingList _settings; + int _flags; + bool _hasOrder; - Property() : flags(0), hasOrder(false) {} + Property() : _flags(0), _hasOrder(false) {} // Constructs a simple Property - explicit Property(std::string name, std::string value = "", std::string comment = "", int flgs = 0, int indent = 0, bool order = false) : flags(flgs), hasOrder(order) { - Setting setting(value, comment, flags, indent); - - settings[name] = setting; - } - - Property(std::string name, ValueList values, int flgs = 0, int indent = 0, bool order = false) : flags(flgs), hasOrder(order) { - Setting setting(values, flags, indent); - - settings[name] = setting; + Property(std::string name, std::string value = "", std::string comment = "", int flgs = 0, int indent = 0, bool order = false) : _flags(flgs), _hasOrder(order) { + _settings[name] = Setting(value, comment, _flags, indent); } - // Copy constructor - Property(const Property &rhs) { - settings = rhs.settings; - flags = rhs.flags; + Property(std::string name, ValueList values, int flgs = 0, int indent = 0, bool order = false) : _flags(flgs), _hasOrder(order) { + _settings[name] = Setting(values, _flags, indent); } OrderedSettingList getOrderedSettingList() { OrderedSettingList list; // Prepare vector to sort - for (SettingList::const_iterator setting = settings.begin(); setting != settings.end(); ++setting) + for (SettingList::const_iterator setting = _settings.begin(); setting != _settings.end(); ++setting) list.push_back(SettingPair(setting->first, setting->second)); // Sort vector using setting order - if (hasOrder) + if (_hasOrder) std::sort(list.begin(), list.end(), OrderSortPredicate); return list; @@ -160,48 +151,48 @@ private: // be overkill since we only have to generate a single project struct Object { public: - std::string id; // Unique identifier for this object - std::string name; // Name (may not be unique - for ex. configuration entries) - std::string refType; // Type of object this references (if any) - std::string comment; // Main comment (empty for no comment) + std::string _id; // Unique identifier for this object + std::string _name; // Name (may not be unique - for ex. configuration entries) + std::string _refType; // Type of object this references (if any) + std::string _comment; // Main comment (empty for no comment) - PropertyList properties; // List of object properties, including output configuration + PropertyList _properties; // List of object properties, including output configuration // Constructs an object and add a default type property Object(XcodeProvider *objectParent, std::string objectId, std::string objectName, std::string objectType, std::string objectRefType = "", std::string objectComment = "") - : id(objectId), name(objectName), refType(objectRefType), comment(objectComment), parent(objectParent) { + : _id(objectId), _name(objectName), _refType(objectRefType), _comment(objectComment), _parent(objectParent) { assert(objectParent); assert(!objectId.empty()); assert(!objectName.empty()); assert(!objectType.empty()); - addProperty("isa", objectType, "", SettingsNoQuote|SettingsNoValue); + addProperty("isa", objectType, "", kSettingsNoQuote | kSettingsNoValue); } // Add a simple Property with just a name and a value void addProperty(std::string propName, std::string propValue, std::string propComment = "", int propFlags = 0, int propIndent = 0) { - properties[propName] = Property(propValue, "", propComment, propFlags, propIndent); + _properties[propName] = Property(propValue, "", propComment, propFlags, propIndent); } std::string toString(int flags = 0) { std::string output; - output = "\t\t" + parent->getHash(id) + (comment.empty() ? "" : " /* " + comment + " */") + " = {"; + output = "\t\t" + _parent->getHash(_id) + (_comment.empty() ? "" : " /* " + _comment + " */") + " = {"; - if (flags & SettingsAsList) + if (flags & kSettingsAsList) output += "\n"; // Special case: always output the isa property first - output += parent->writeProperty("isa", properties["isa"], flags); + output += _parent->writeProperty("isa", _properties["isa"], flags); // Write each property - for (PropertyList::iterator property = properties.begin(); property != properties.end(); ++property) { - if ((*property).first == "isa") + for (PropertyList::iterator property = _properties.begin(); property != _properties.end(); ++property) { + if (property->first == "isa") continue; - output += parent->writeProperty((*property).first, (*property).second, flags); + output += _parent->writeProperty(property->first, property->second, flags); } - if (flags & SettingsAsList) + if (flags & kSettingsAsList) output += "\t\t"; output += "};\n"; @@ -209,50 +200,59 @@ private: return output; } - // Slight hack, to allow Group access to parent. + // Slight hack, to allow Group access to parent. protected: - XcodeProvider *parent; + XcodeProvider *_parent; private: // Returns the type property (should always be the first in the properties map) std::string getType() { - assert(!properties.empty()); - assert(!properties["isa"].settings.empty()); + assert(!_properties.empty()); + assert(!_properties["isa"]._settings.empty()); - SettingList::iterator it = properties["isa"].settings.begin(); + SettingList::iterator it = _properties["isa"]._settings.begin(); - return (*it).first; + return it->first; } }; struct ObjectList { private: - std::map<std::string, bool> objectMap; + std::map<std::string, bool> _objectMap; public: - std::vector<Object *> objects; - std::string comment; - int flags; + std::vector<Object *> _objects; + std::string _comment; + int _flags; void add(Object *obj) { - std::map<std::string, bool>::iterator it = objectMap.find(obj->id); - if (it != objectMap.end() && it->second == true) + std::map<std::string, bool>::iterator it = _objectMap.find(obj->_id); + if (it != _objectMap.end() && it->second == true) return; - objects.push_back(obj); - objectMap[obj->id] = true; + _objects.push_back(obj); + _objectMap[obj->_id] = true; + } + + Object *find(std::string id) { + for (std::vector<Object *>::iterator it = _objects.begin(); it != _objects.end(); ++it) { + if ((*it)->_id == id) { + return *it; + } + } + return NULL; } std::string toString() { std::string output; - if (!comment.empty()) - output = "\n/* Begin " + comment + " section */\n"; + if (!_comment.empty()) + output = "\n/* Begin " + _comment + " section */\n"; - for (std::vector<Object *>::iterator object = objects.begin(); object != objects.end(); ++object) - output += (*object)->toString(flags); + for (std::vector<Object *>::iterator object = _objects.begin(); object != _objects.end(); ++object) + output += (*object)->toString(_flags); - if (!comment.empty()) - output += "/* End " + comment + " section */\n"; + if (!_comment.empty()) + output += "/* End " + _comment + " section */\n"; return output; } @@ -271,10 +271,10 @@ private: void addChildFile(const std::string &name); void addChildByHash(const std::string &hash, const std::string &name); // Should be passed the hash for the entry - void addChildGroup(const Group* group); + void addChildGroup(const Group *group); void ensureChildExists(const std::string &name); Group *getChildGroup(const std::string &name); - std::string getHashRef() const { return parent->getHash(id); } + std::string getHashRef() const { return _parent->getHash(_id); } }; // The path used by the root-source group @@ -312,18 +312,26 @@ private: // Setup objects void setupCopyFilesBuildPhase(); - void setupFrameworksBuildPhase(); + void setupFrameworksBuildPhase(const BuildSetup &setup); void setupNativeTarget(); void setupProject(); void setupResourcesBuildPhase(); void setupSourcesBuildPhase(); - void setupBuildConfiguration(); + void setupBuildConfiguration(const BuildSetup &setup); + void setupImageAssetCatalog(const BuildSetup &setup); + void setupAdditionalSources(std::string targetName, Property &files, int &order); // Misc void setupDefines(const BuildSetup &setup); // Setup the list of defines to be used on build configurations + // Retrieve information + ValueList& getResourceFiles() const; + // Hash generation std::string getHash(std::string key); +#ifdef MACOSX + std::string md5(std::string key); +#endif std::string newHash() const; // Output diff --git a/devtools/create_project/xcode/create_project.xcodeproj/project.pbxproj b/devtools/create_project/xcode/create_project.xcodeproj/project.pbxproj index f13bcf6969..4f06a5e469 100644 --- a/devtools/create_project/xcode/create_project.xcodeproj/project.pbxproj +++ b/devtools/create_project/xcode/create_project.xcodeproj/project.pbxproj @@ -140,6 +140,9 @@ /* Begin PBXProject section */ F9A66C1E1396D36100CEE494 /* Project object */ = { isa = PBXProject; + attributes = { + LastUpgradeCheck = 0720; + }; buildConfigurationList = F9A66C211396D36100CEE494 /* Build configuration list for PBXProject "create_project" */; compatibilityVersion = "Xcode 3.2"; developmentRegion = English; @@ -177,12 +180,14 @@ F9A66C2E1396D36100CEE494 /* Debug */ = { isa = XCBuildConfiguration; buildSettings = { - ARCHS = "$(ARCHS_STANDARD_32_64_BIT)"; + ENABLE_TESTABILITY = YES; GCC_C_LANGUAGE_STANDARD = gnu99; GCC_OPTIMIZATION_LEVEL = 0; - GCC_PREPROCESSOR_DEFINITIONS = DEBUG; + GCC_PREPROCESSOR_DEFINITIONS = ( + POSIX, + MACOSX, + ); GCC_SYMBOLS_PRIVATE_EXTERN = NO; - GCC_VERSION = com.apple.compilers.llvm.clang.1_0; GCC_WARN_64_TO_32_BIT_CONVERSION = YES; GCC_WARN_ABOUT_RETURN_TYPE = YES; GCC_WARN_UNUSED_VARIABLE = YES; @@ -195,9 +200,11 @@ F9A66C2F1396D36100CEE494 /* Release */ = { isa = XCBuildConfiguration; buildSettings = { - ARCHS = "$(ARCHS_STANDARD_32_64_BIT)"; GCC_C_LANGUAGE_STANDARD = gnu99; - GCC_VERSION = com.apple.compilers.llvm.clang.1_0; + GCC_PREPROCESSOR_DEFINITIONS = ( + POSIX, + MACOSX, + ); GCC_WARN_64_TO_32_BIT_CONVERSION = YES; GCC_WARN_ABOUT_RETURN_TYPE = YES; GCC_WARN_UNUSED_VARIABLE = YES; @@ -213,6 +220,10 @@ COPY_PHASE_STRIP = NO; GCC_DYNAMIC_NO_PIC = NO; GCC_ENABLE_OBJC_EXCEPTIONS = YES; + GCC_PREPROCESSOR_DEFINITIONS = ( + "$(inherited)", + DEBUG, + ); PRODUCT_NAME = "$(TARGET_NAME)"; }; name = Debug; @@ -224,6 +235,7 @@ COPY_PHASE_STRIP = YES; DEBUG_INFORMATION_FORMAT = "dwarf-with-dsym"; GCC_ENABLE_OBJC_EXCEPTIONS = YES; + GCC_PREPROCESSOR_DEFINITIONS = "$(inherited)"; PRODUCT_NAME = "$(TARGET_NAME)"; }; name = Release; |
