void GetPropertyForDebugger(RuntimeScene & scene, std::size_t propertyNb, gd::String & name, gd::String & value) const { std::size_t i = 0; std::map < gd::String, ManualTimer >::const_iterator end = TimedEventsManager::managers[&scene].timedEvents.end(); for (std::map < gd::String, ManualTimer >::iterator iter = TimedEventsManager::managers[&scene].timedEvents.begin();iter != end;++iter) { if ( propertyNb == i ) { name = iter->first; //Unmangle name if ( name.find("GDNamedTimedEvent_") == 0 && name.length() > 18 ) name = name.substr(18, name.length()); else name = _("No name"); value = gd::String::From(static_cast<double>(iter->second.GetTime())/1000000.0)+"s"; return; } ++i; } }
/** * Show a message box with Yes/No buttons */ void GD_EXTENSION_API ShowYesNoMsgBox( RuntimeScene & scene, gd::Variable & variable, const gd::String & message, const gd::String & title ) { sf::Clock timeSpent; gd::String result; //Display the box #if defined(WINDOWS) if( MessageBoxW(NULL, message.ToWide().c_str(), title.ToWide().c_str(), MB_ICONQUESTION | MB_YESNO) == IDYES) result = "yes"; else result = "no"; #endif #if defined(LINUX) || defined(MACOS) nw::YesNoMsgBox dialog(title.ToLocale(), message.ToLocale(), result.Raw()); dialog.wait_until_closed(); #endif scene.NotifyPauseWasMade(timeSpent.getElapsedTime().asMicroseconds());//Don't take the time spent in this function in account. //Update the variable variable.SetString(result); //Can only be "yes" or "no", no need to encode in UTF8 }
std::set < gd::String > EventsVariablesFinder::FindArgumentsInInstructions(const gd::Platform & platform, const gd::Project & project, const gd::Layout & layout, const gd::InstructionsList & instructions, bool instructionsAreConditions, const gd::String & parameterType, const gd::String & objectName) { std::set < gd::String > results; for (std::size_t aId = 0;aId < instructions.size();++aId) { gd::String lastObjectParameter = ""; gd::InstructionMetadata instrInfos = instructionsAreConditions ? MetadataProvider::GetConditionMetadata(platform, instructions[aId].GetType()) : MetadataProvider::GetActionMetadata(platform, instructions[aId].GetType()); for (std::size_t pNb = 0;pNb < instrInfos.parameters.size();++pNb) { //The parameter has the searched type... if ( instrInfos.parameters[pNb].type == parameterType ) { //...remember the value of the parameter. if (objectName.empty() || lastObjectParameter == objectName) results.insert(instructions[aId].GetParameter(pNb).GetPlainString()); } //Search in expressions else if (instrInfos.parameters[pNb].type == "expression") { CallbacksForSearchingVariable callbacks(results, parameterType, objectName); gd::ExpressionParser parser(instructions[aId].GetParameter(pNb).GetPlainString()); parser.ParseMathExpression(platform, project, layout, callbacks); } //Search in gd::String expressions else if (instrInfos.parameters[pNb].type == "string"||instrInfos.parameters[pNb].type == "file" ||instrInfos.parameters[pNb].type == "joyaxis" ||instrInfos.parameters[pNb].type == "color"||instrInfos.parameters[pNb].type == "layer") { CallbacksForSearchingVariable callbacks(results, parameterType, objectName); gd::ExpressionParser parser(instructions[aId].GetParameter(pNb).GetPlainString()); parser.ParseStringExpression(platform, project, layout, callbacks); } //Remember the value of the last "object" parameter. else if (gd::ParameterMetadata::IsObject(instrInfos.parameters[pNb].type)) { lastObjectParameter = instructions[aId].GetParameter(pNb).GetPlainString(); } } if ( !instructions[aId].GetSubInstructions().empty() ) FindArgumentsInInstructions(platform, project, layout, instructions[aId].GetSubInstructions(), instructionsAreConditions, parameterType); } return results; }
std::shared_ptr<gd::Platform> PlatformLoader::LoadPlatformInManager(gd::String fullpath) { std::cout << "Loading platform " << fullpath << "..." << std::endl; Handle platformHdl = OpenLibrary(fullpath.ToLocale().c_str()); //Use the system locale for filepath if (platformHdl == NULL) { gd::String error = DynamicLibraryLastError(); cout << "Loading of "<< fullpath <<" failed." << endl; cout << "Error returned : \"" << error << "\"" << endl; #if defined(GD_IDE_ONLY) && !defined(GD_NO_WX_GUI) wxString userMsg = _("Platform ") + fullpath + _(" could not be loaded.\nContact the developer for more information.\n\nDetailed log:\n") + error; wxMessageBox(userMsg, _("Platform not compatible"), wxOK | wxICON_EXCLAMATION); #endif } else { CreatePlatformFunPtr createFunPtr = (CreatePlatformFunPtr)GetSymbol(platformHdl, "CreateGDPlatform"); DestroyPlatformFunPtr destroyFunPtr = (DestroyPlatformFunPtr)GetSymbol(platformHdl, "DestroyGDPlatform"); if ( createFunPtr == NULL || destroyFunPtr == NULL ) { cout << "Loading of "<< fullpath <<" failed (no valid create/destroy functions)." << endl; CloseLibrary(platformHdl); #if defined(GD_IDE_ONLY) && !defined(GD_NO_WX_GUI) wxString userMsg = _("Platform ")+ fullpath + _(" could not be loaded.\nContact the developer for more information.\n\nDetailed log:\nNo valid create/destroy functions." ); wxMessageBox(userMsg, _("Platform not compatible"), wxOK | wxICON_EXCLAMATION); #endif } else { #if defined(GD_IDE_ONLY) && !defined(GD_NO_WX_GUI) gd::LocaleManager::Get()->AddCatalog(wxFileName(fullpath).GetName()); //In editor, load catalog associated with extension, if any. #endif std::shared_ptr<gd::Platform> platform(createFunPtr(), destroyFunPtr); std::cout << "Loading of " << fullpath << " done." << std::endl; gd::PlatformManager::Get()->AddPlatform(platform); std::cout << "Registration in platform manager of " << fullpath << " done." << std::endl; return platform; } } return std::shared_ptr<gd::Platform>(); }
void ExtensionsLoader::ExtensionsLoadingDone(const gd::String & directory) { gd::String suffix = ""; #if defined(WINDOWS) suffix += "w"; #endif #if defined(GD_IDE_ONLY) suffix += "e"; #endif #if defined(LINUX) || defined (MACOS) //List all extensions loaded struct dirent *lecture; DIR *rep; rep = opendir( directory.c_str() ); int l = 0; if ( rep == NULL ) { cout << "Unable to open Extensions ("<< directory <<") directory." << endl; return; } std::vector<gd::String> librariesLoaded; while ( (lecture = readdir( rep )) ) { gd::String lec = lecture->d_name; if ( lec != "." && lec != ".." && lec.find(".xgd"+suffix, lec.length()-4-suffix.length()) != string::npos) { librariesLoaded.push_back(directory+"/"+lec); l++; } } closedir( rep ); //Libraries are loaded using dlopen(.., RTLD_LAZY|RTLD_LOCAL) meaning that their symbols are not available for other libraries //nor for LLVM/Clang. We then reload set them as global to make their symbols available for LLVM/Clang. We couldn't mark them //as global when loading them as every extension use the same "CreateGDExtension" symbol. //SetLibraryGlobal is also setting RTLD_NOW to ensure that all symbols are resolved: Otherwise, we can get weird //"symbol lookup error" even if the symbols exist in the extensions! for (std::size_t i = 0;i<librariesLoaded.size();++i) SetLibraryGlobal(librariesLoaded[i].c_str()); #else //Nothing to do on Windows. #endif }
bool RuntimeObject::ChangeProperty(std::size_t propertyNb, gd::String newValue) { if (propertyNb == 0) { size_t separationPos = newValue.find(";"); if (separationPos > newValue.length()) return false; gd::String xValue = newValue.substr(0, separationPos); gd::String yValue = newValue.substr(separationPos + 1, newValue.length()); SetX(xValue.To<float>()); SetY(yValue.To<float>()); } else if (propertyNb == 1) { return SetAngle(newValue.To<float>()); } else if (propertyNb == 2) { return false; } else if (propertyNb == 3) { if (newValue == _("Hidden")) { SetHidden(); } else SetHidden(false); } else if (propertyNb == 4) { layer = newValue; } else if (propertyNb == 5) { SetZOrder(newValue.To<int>()); } else if (propertyNb == 6) { return false; } else if (propertyNb == 7) { return false; } else if (propertyNb == 8) { return false; } else if (propertyNb == 9) { return false; } return true; }
void HttpServer::Run(gd::String indexDirectory) { // Some options ( Last option must be NULL ) std::string indexDirectoryLocale = indexDirectory.ToLocale(); const char *options[] = {"listening_ports", "2828", "document_root", indexDirectoryLocale.c_str(), NULL}; // Setup callbacks, i.e. nothing to do :) struct mg_callbacks callbacks; memset(&callbacks, 0, sizeof(callbacks)); ctx = mg_start(&callbacks, NULL, options); }
long int ResourcesLoader::GetBinaryFileSize( const gd::String & filename) { if (resFile.ContainsFile(filename)) return resFile.GetFileSize(filename); else { ifstream file (filename.ToLocale().c_str(), ios::in|ios::binary|ios::ate); if (file.is_open()) { return file.tellg(); } } std::cout << "Binary file " << filename << " cannot be read. " << std::endl; return 0; }
void RuntimeSpriteObject::MakeColorTransparent( const gd::String & colorStr ) { if ( needUpdateCurrentSprite ) UpdateCurrentSprite(); ptrToCurrentSprite->MakeSpriteOwnsItsImage(); //We want to modify only the image of the object, not all objects which have the same image. std::shared_ptr<SFMLTextureWrapper> dest = ptrToCurrentSprite->GetSFMLTexture(); std::vector < gd::String > colors = colorStr.Split(U';'); if ( colors.size() < 3 ) return; //La couleur est incorrecte //Update texture and pixel perfect collision mask dest->image.createMaskFromColor( sf::Color( colors[0].To<int>(), colors[1].To<int>(), colors[2].To<int>())); dest->texture.loadFromImage(dest->image); }
void GD_EXTENSION_API OpenSFMLTextureFromFile( RuntimeScene & scene, const gd::String & fileName, const gd::String & imageName ) { //Get or create the texture in memory std::shared_ptr<SFMLTextureWrapper> newTexture; if ( !scene.GetImageManager()->HasLoadedSFMLTexture(imageName) ) newTexture = std::shared_ptr<SFMLTextureWrapper>(new SFMLTextureWrapper); else newTexture = scene.GetImageManager()->GetSFMLTexture(imageName); //Open the SFML image and the SFML texture newTexture->image.loadFromFile(fileName.ToLocale()); newTexture->texture.loadFromImage(newTexture->image); //Do not forget to update the associated texture scene.GetImageManager()->SetSFMLTextureAsPermanentlyLoaded(imageName, newTexture); }
int SerializerElement::GetIntAttribute(const gd::String& name, int defaultValue, gd::String deprecatedName) const { if (attributes.find(name) != attributes.end()) return attributes.find(name)->second.GetInt(); else if (!deprecatedName.empty() && attributes.find(deprecatedName) != attributes.end()) return attributes.find(deprecatedName)->second.GetInt(); else { if (HasChild(name, deprecatedName)) { SerializerElement& child = GetChild(name, 0, deprecatedName); if (!child.IsValueUndefined()) return child.GetValue().GetInt(); } } return defaultValue; }
sf::Texture ResourcesLoader::LoadSFMLTexture(const gd::String & filename) { sf::Texture texture; if (resFile.ContainsFile(filename)) { char* buffer = resFile.GetFile(filename); if (buffer==NULL) cout << "Failed to get the file of a SFML texture from resource file: " << filename << endl; if (!texture.loadFromMemory(buffer, resFile.GetFileSize(filename))) cout << "Failed to load a SFML texture from resource file: " << filename << endl; } else if (!texture.loadFromFile(filename.ToLocale())) cout << "Failed to load a SFML texture: " << filename << endl; return texture; }
sf::SoundBuffer ResourcesLoader::LoadSoundBuffer( const gd::String & filename ) { sf::SoundBuffer sbuffer; if (resFile.ContainsFile(filename)) { char* buffer = resFile.GetFile(filename); if (buffer==NULL) cout << "Failed to get the file of a sound buffer from resource file: " << filename << endl; if (!sbuffer.loadFromMemory(buffer, resFile.GetFileSize(filename))) cout << "Failed to load a sound buffer from resource file: " << filename << endl; } else if (!sbuffer.loadFromFile(filename.ToLocale())) cout << "Failed to load a sound buffer: " << filename << endl; return sbuffer; }
bool ProjectFileWriter::SaveToJSONFile(const gd::Project & project, const gd::String & filename) { //Serialize the whole project gd::SerializerElement rootElement; project.SerializeTo(rootElement); //Write JSON to file gd::String str = gd::Serializer::ToJSON(rootElement); std::ofstream ofs(filename.ToLocale().c_str()); if (!ofs.is_open()) { gd::LogError( _( "Unable to save file ")+ filename + _("!\nCheck that the drive has enough free space, is not write-protected and that you have read/write permissions." ) ); return false; } ofs << str; ofs.close(); return true; }
bool ProjectFileWriter::LoadFromJSONFile(gd::Project & project, const gd::String & filename) { std::ifstream ifs(filename.ToLocale().c_str()); if (!ifs.is_open()) { gd::String error = _( "Unable to open the file.") + _("Make sure the file exists and that you have the right to open the file."); gd::LogError(error); return false; } project.SetProjectFile(filename); project.SetDirty(false); std::string str((std::istreambuf_iterator<char>(ifs)), std::istreambuf_iterator<char>()); gd::SerializerElement rootElement = gd::Serializer::FromJSON(str); project.UnserializeFrom(rootElement); return true; }
std::vector<sf::Vector2f> PhysicsBehavior::GetCoordsVectorFromString(const gd::String &str, char32_t coordsSep, char32_t composantSep) { std::vector<sf::Vector2f> coordsVec; std::vector<gd::String> coordsDecomposed = str.Split(coordsSep); for(std::size_t a = 0; a < coordsDecomposed.size(); a++) { std::vector<gd::String> coordXY = coordsDecomposed.at(a).Split(composantSep); if(coordXY.size() != 2) continue; sf::Vector2f newCoord(coordXY.at(0).To<float>(), coordXY.at(1).To<float>()); coordsVec.push_back(newCoord); } return coordsVec; }
void ParameterControlsHelper::UpdateParameterContent(std::size_t i, const ParameterMetadata & metadata, gd::String content) { if (i >= paramEdits.size()) return; paramMetadata[i] = metadata; if (metadata.IsCodeOnly()) { paramCheckboxes.at(i)->Show(false); paramTexts.at(i)->Show(false); paramBmpBts.at(i)->Show(false); paramEdits.at(i)->Show(false); return; } const gd::String & type = metadata.GetType(); paramCheckboxes.at(i)->Show(metadata.IsOptional()); paramTexts.at(i)->Show(); paramBmpBts.at(i)->Show(!type.empty()); paramEdits.at(i)->Show(); paramCheckboxes.at(i)->SetValue(!paramEdits.at(i)->GetValue().empty()); paramTexts.at(i)->SetLabel(metadata.GetDescription() + _(":")); paramBmpBts.at(i)->SetBitmapLabel(gd::InstructionSentenceFormatter::Get()->BitmapFromType(type)); paramBmpBts.at(i)->SetToolTip(gd::InstructionSentenceFormatter::Get()->LabelFromType(type)); paramEdits.at(i)->SetValue(content); //De/activate widgets if parameter is optional bool disable = metadata.IsOptional() && !paramCheckboxes.at(i)->GetValue() && paramEdits.at(i)->GetValue().empty(); paramCheckboxes.at(i)->SetValue(!disable); paramTexts.at(i)->Enable(!disable); paramBmpBts.at(i)->Enable(!disable); paramEdits.at(i)->Enable(!disable); //Add defaults if (!metadata.IsOptional() && content.empty()) { if (!metadata.GetDefaultValue().empty()) paramEdits.at(i)->SetValue(metadata.GetDefaultValue()); else if ( type == "expression" ) paramEdits.at(i)->SetValue("0"); else if ( type == "string" ) paramEdits.at(i)->SetValue("\"\""); else if ( type == "operator" ) paramEdits.at(i)->SetValue("="); } }
bool SerializerElement::GetBoolAttribute(const gd::String& name, bool defaultValue, gd::String deprecatedName) const { if (attributes.find(name) != attributes.end()) { return attributes.find(name)->second.GetBool(); } else if (!deprecatedName.empty() && attributes.find(deprecatedName) != attributes.end()) { return attributes.find(deprecatedName)->second.GetBool(); } else { if (HasChild(name, deprecatedName)) { SerializerElement& child = GetChild(name, 0, deprecatedName); if (!child.IsValueUndefined()) { return child.GetValue().GetBool(); } } } std::cout << "Bool attribute \"" << name << "\" not found, returning " << defaultValue; return defaultValue; }
sf::Http::Response::Status EventStoreDialog::FetchTemplate(gd::String id) { nameTxt->SetLabel("Loading the template..."); descriptionEdit->SetValue(""); gd::SafeYield::Do(); // Create request sf::Http Http(host.ToLocale(), port); sf::Http::Request request; request.setMethod(sf::Http::Request::Get); request.setUri("/events/"+id.ToLocale()); // Send the request sf::Http::Response response = Http.sendRequest(request, sf::seconds(2)); if (response.getStatus() == sf::Http::Response::Ok) loadedTemplate = Serializer::FromJSON(response.getBody()); return response.getStatus(); }
gd::String GD_EXTENSION_API GetAttributeString(const gd::String &refname, const gd::String &property, RuntimeScene &scene) { TiXmlNode *refNode = RefManager::Get(&scene)->GetRef(refname); if(refNode) { TiXmlElement *refEle = refNode->ToElement(); if(refEle) { gd::String attributeStr = refEle->Attribute(property.c_str()); return attributeStr; } else { return ""; } } else { return ""; } }
std::pair<sf::Font *, char *> ResourcesLoader::LoadFont(const gd::String & filename) { if (resFile.ContainsFile(filename)) { char* buffer = resFile.GetFile(filename); size_t bufferSize = resFile.GetFileSize(filename); if (buffer==NULL) { cout << "Failed to get the file of a font from resource file:" << filename << endl; return std::make_pair((sf::Font*)NULL, (char*)NULL); } sf::Font * font = new sf::Font(); char * fontBuffer = new char[bufferSize]; memcpy(fontBuffer, buffer, bufferSize); if (!font->loadFromMemory(fontBuffer, bufferSize)) { cout << "Failed to load a font from resource file: " << filename << endl; delete font; delete fontBuffer; return std::make_pair((sf::Font*)NULL, (char*)NULL); } return std::make_pair(font, fontBuffer); } else { sf::Font * font = new sf::Font(); if (!font->loadFromFile(filename.ToLocale())) { cout << "Failed to load a font from a file: " << filename << endl; delete font; return std::make_pair<sf::Font*, char*>(NULL, NULL); } return std::make_pair(font, (char*)nullptr); } }
void GD_API DeleteGroupFromFile( const gd::String & filename, const gd::String & group ) { std::shared_ptr<XmlFile> file = XmlFilesManager::GetFile(filename); TiXmlHandle hdl( &file->GetTinyXmlDocument() ); //D�coupage des groupes istringstream groupsStr( group.Raw() ); std::string str; vector < gd::String > groups; while ( std::getline( groupsStr, str, '/' ) ) { groups.push_back(gd::String::FromUTF8(str)); } groups.erase(std::remove_if(groups.begin(), groups.end(), StringEmpty()), groups.end()); if ( groups.empty() ) return; groups.push_back(""); //A chaque fois, on v�rifie si le groupe voulu existe for (std::size_t i =0;i<groups.size();i++) { if ( hdl.FirstChildElement(groups.at(i).c_str()).Element() == NULL ) return; //Si on arrive au groupe parent du groupe //� supprimer if ( i >= (groups.size()-1)-1 ) { hdl.ToNode()->RemoveChild(hdl.FirstChildElement(groups.at(i).c_str()).ToNode()); return; } hdl = hdl.FirstChildElement(groups.at(i).c_str()); } return; }
double GD_EXTENSION_API GetAttributeNumber(const gd::String &refname, const gd::String &property, RuntimeScene &scene) { TiXmlNode *refNode = RefManager::Get(&scene)->GetRef(refname); if(refNode) { TiXmlElement *refEle = refNode->ToElement(); if(refEle) { double attributeDouble = 0; refEle->QueryDoubleAttribute(property.c_str(), &attributeDouble); return attributeDouble; } else { return 0; } } else { return 0; } }
/** * Display an "open file" dialog */ void GD_EXTENSION_API ShowOpenFile( RuntimeScene & scene, gd::Variable & variable, const gd::String & title, gd::String filters ) { sf::Clock timeSpent; gd::String result; //Display the dialog #if defined(WINDOWS) //Process filters to match windows dialogs filters style. filters.Raw() = filters.Raw()+'\0'; std::replace(filters.Raw().begin(), filters.Raw().end(), '|', '\0'); OPENFILENAMEW toGetFileName; //Struct for the dialog wchar_t filePath[MAX_PATH]; _wgetcwd(filePath, MAX_PATH); ZeroMemory(&toGetFileName, sizeof(OPENFILENAMEW)); toGetFileName.lStructSize = sizeof(OPENFILENAMEW); toGetFileName.hwndOwner = NULL; toGetFileName.lpstrFile = filePath; toGetFileName.nMaxFile = MAX_PATH; toGetFileName.lpstrFilter = filters == "\0" ? NULL : filters.ToWide().c_str(); toGetFileName.nFilterIndex = 1; toGetFileName.Flags = OFN_PATHMUSTEXIST | OFN_NOCHANGEDIR;; if(GetOpenFileNameW(&toGetFileName) == TRUE) result = gd::String::FromWide(filePath); #endif #if defined(LINUX) || defined(MACOS) std::string strResult; nw::OpenFile * dialog = new nw::OpenFile(title.ToLocale(), true, strResult); dialog->wait_until_closed(); result = gd::String::FromLocale(strResult); #endif scene.GetTimeManager().NotifyPauseWasMade(timeSpent.getElapsedTime().asMicroseconds());//Don't take the time spent in this function in account. //Update the variable variable.SetString(result); }
gd::String gd::AbstractFileSystem::NormalizeSeparator(gd::String filename) { //Convert all backslash to slashs. return filename.FindAndReplace("\\", "/"); }
void GD_EXTENSION_API SaveSFMLTextureToFile( RuntimeScene & scene, const gd::String & fileName, const gd::String & imageName ) { if ( !scene.GetImageManager()->HasLoadedSFMLTexture(imageName) ) return; scene.GetImageManager()->GetSFMLTexture(imageName)->image.saveToFile(fileName.ToLocale()); }
void ExtensionsLoader::LoadAllExtensions(const gd::String & directory, gd::Platform & platform, bool forgiving) { std::cout << "Loading extensions for " << platform.GetName() << "... "; gd::String suffix = ""; #if defined(WINDOWS) suffix += "w"; #endif #if defined(GD_IDE_ONLY) suffix += "e"; #endif #if defined(__GNUC__) //For compilers with posix support struct dirent *lecture; DIR *rep; rep = opendir( directory.c_str() ); int l = 0; if ( rep == NULL ) { cout << "Unable to open Extensions ("<< directory <<") directory." << endl; return; } std::vector<gd::String> librariesLoaded; while ( (lecture = readdir( rep )) ) { gd::String lec = lecture->d_name; //Load all extensions, except the legacy ones finishing by *Automatism.xgd* from GD3.x if ( lec != "." && lec != ".." && lec.find(".xgd"+suffix, lec.length()-4-suffix.length()) != string::npos && lec.find("Automatism.xgd"+suffix) == string::npos) { //Use a log file, in IDE only #if defined(GD_IDE_ONLY) && !defined(GD_NO_WX_GUI) { wxFile errorDetectFile(wxFileName::GetTempDir()+"/ExtensionBeingLoaded.log", wxFile::write); errorDetectFile.Write(directory+"/"+lec); } #endif LoadExtension(directory+"/"+lec, platform, forgiving); //Everything is ok : Delete the log file #if defined(GD_IDE_ONLY) && !defined(GD_NO_WX_GUI) wxRemoveFile(wxFileName::GetTempDir()+"/ExtensionBeingLoaded.log"); #endif librariesLoaded.push_back(directory+"/"+lec); l++; } } closedir( rep ); #elif defined(_MSC_VER) WIN32_FIND_DATA f; gd::String dirPart = "/*.xgd"; gd::String dirComplete = directory + dirPart + suffix; HANDLE h = FindFirstFile(dirComplete.c_str(), &f); if(h != INVALID_HANDLE_VALUE) { do { //Use a log file, in IDE only #if defined(GD_IDE_ONLY) && !defined(GD_NO_WX_GUI) { wxFile errorDetectFile(wxFileName::GetTempDir()+"/ExtensionBeingLoaded.log", wxFile::write); errorDetectFile.Write(f.cFileName); } #endif LoadExtension(f.cFileName, platform, forgiving); //Everything is ok : Delete the log file #if defined(GD_IDE_ONLY) && !defined(GD_NO_WX_GUI) wxRemoveFile(wxFileName::GetTempDir()+"/ExtensionBeingLoaded.log"); #endif } while(FindNextFile(h, &f)); } #else #warning Compiler not supported (but might support one style of directory listing, update defines if necessary) for dynamic libraries loading #endif std::cout << " done. " << std::endl; }
void ExtensionsLoader::LoadExtension(const gd::String & fullpath, gd::Platform & platform, bool forgiving) { if ( platform.GetExtensionCreateFunctionName().empty() ) { cout << "Unable to load extension " << fullpath << ":" << endl; cout << "The plaftorm does not support extensions creation." << endl; return; } Handle extensionHdl = OpenLibrary(fullpath.c_str()); if (extensionHdl == NULL) { gd::String error = DynamicLibraryLastError(); cout << "Unable to load extension " << fullpath << "." << endl; cout << "Error returned : \"" << error << "\"" << endl; #if defined(GD_IDE_ONLY) && !defined(GD_NO_WX_GUI) wxString userMsg = _("Extension ")+ fullpath + _(" could not be loaded.\nContact the developer for more informations.\n\nDetailed log:\n") + error; wxMessageBox(userMsg, _("Extension not compatible"), wxOK | wxICON_EXCLAMATION); #endif return; } createExtension create_extension = (createExtension)GetSymbol(extensionHdl, platform.GetExtensionCreateFunctionName().c_str()); if (create_extension == NULL) { if (!forgiving) { cout << "Unable to load extension " << fullpath << " (Creation function symbol not found)." << endl; #if defined(GD_IDE_ONLY) && !defined(GD_NO_WX_GUI) wxString userMsg = _("Extension ")+ fullpath + _(" could not be loaded.\nContact the developer for more informations." ); wxMessageBox(userMsg, _("Extension not compatible"), wxOK | wxICON_EXCLAMATION); #endif } CloseLibrary(extensionHdl); return; } #if defined(GD_IDE_ONLY) && !defined(GD_NO_WX_GUI) gd::LocaleManager::Get()->AddCatalog(wxFileName(fullpath).GetName()); //In editor, load catalog associated with extension, if any. #endif gd::PlatformExtension * extensionPtr = create_extension(); gd::String error; //Perform safety check about the compilation if ( !extensionPtr->compilationInfo.informationCompleted ) error += "Compilation information not filled.\n"; #if defined(GD_IDE_ONLY) else if ( extensionPtr->compilationInfo.runtimeOnly ) error += "Extension compiled for runtime only.\n"; #if !defined(GD_NO_WX_GUI) else if ( extensionPtr->compilationInfo.wxWidgetsMajorVersion != wxMAJOR_VERSION || extensionPtr->compilationInfo.wxWidgetsMinorVersion != wxMINOR_VERSION || extensionPtr->compilationInfo.wxWidgetsReleaseNumber != wxRELEASE_NUMBER || extensionPtr->compilationInfo.wxWidgetsSubReleaseNumber != wxSUBRELEASE_NUMBER ) error += "Not the same wxWidgets version.\n"; #endif #endif #if defined(__GNUC__) else if ( extensionPtr->compilationInfo.gccMajorVersion != __GNUC__ || extensionPtr->compilationInfo.gccMinorVersion != __GNUC_MINOR__ ) error += "Not the same GNU Compiler version.\n"; #endif else if ( extensionPtr->compilationInfo.sfmlMajorVersion != 2 || extensionPtr->compilationInfo.sfmlMinorVersion != 0 ) error += "Not the same SFML version.\n"; else if ( extensionPtr->compilationInfo.gdCoreVersion != GDCore_RC_FILEVERSION_STRING) error += "Not the same GDevelop Core version.\n(Extension is using "+extensionPtr->compilationInfo.gdCoreVersion+", GDevelop is using "+GDCore_RC_FILEVERSION_STRING+")\n"; else if ( extensionPtr->compilationInfo.sizeOfpInt != sizeof(int*)) error += "Not the same architecture.\n(Extension sizeof(int*) is "+gd::String::From(extensionPtr->compilationInfo.sizeOfpInt)+", GDevelop sizeof(int*) is "+gd::String::From(sizeof(int*))+")\n"; if ( !error.empty() ) { char beep = 7; cout << "-- WARNING ! --" << beep << endl; cout << "Bad extension " + fullpath + " loaded :\n" + error; cout << "---------------" << endl; #if defined(RELEASE)//Load extension despite errors in non release build //Destroy the extension class THEN unload the library from memory delete extensionPtr; CloseLibrary(extensionHdl); #endif #if defined(GD_IDE_ONLY) && !defined(GD_NO_WX_GUI) && defined(RELEASE) //Show errors in IDE only wxString userMsg = _("Extension ") + fullpath + _(" has errors :\n") + error + _("\nThe extension was not loaded. Contact the developer to get more information." ); wxMessageBox(userMsg, _("Extension not compatible"), wxOK | wxICON_EXCLAMATION); #endif #if defined(RELEASE)//Load extension despite errors in non release build return; #endif } std::shared_ptr<gd::PlatformExtension> extension(extensionPtr); platform.AddExtension(extension); return; }
/** * Execute a system-specific command */ void GD_API ExecuteCmd( const gd::String & cmd ) { system(cmd.ToLocale().c_str()); return; }
/** * Delete a file */ void GD_API GDDeleteFile( const gd::String & filename ) { remove(filename.ToLocale().c_str()); return; }