ProjectInfo ProjectInfoGenerator::generate()
{
    ProjectInfo projectInfo(m_projectUpdateInfo.project);

    for (const RawProjectPart &rpp : m_projectUpdateInfo.rawProjectParts) {
        if (m_futureInterface.isCanceled())
            return ProjectInfo();

        for (ProjectPart::Ptr part : createProjectParts(rpp))
            projectInfo.appendProjectPart(part);
    }

    return projectInfo;
}
void CodeBlocksImporter::GenerateFromProject(GenericWorkspacePtr genericWorkspace,
                                             GenericProjectDataType& genericProjectData)
{
    wxXmlDocument codeBlocksProject;
    if(codeBlocksProject.Load(genericProjectData[wxT("projectFullPath")])) {
        wxXmlNode* root = codeBlocksProject.GetRoot();
        if(root) {
            wxXmlNode* rootChild = root->GetChildren();

            while(rootChild) {
                if(rootChild->GetName() == wxT("Project")) {
                    wxString globalCompilerOptions = wxT(""), globalIncludePath = wxT(""),
                             globalLinkerOptions = wxT(""), globalLibPath = wxT(""), globalLibraries = wxT("");

                    wxFileName projectInfo(genericProjectData[wxT("projectFullPath")]);
                    GenericProjectPtr genericProject = std::make_shared<GenericProject>();
                    genericProject->path = projectInfo.GetPath();

                    wxStringTokenizer deps(genericProjectData[wxT("projectDeps")], wxT(";"));

                    while(deps.HasMoreTokens()) {
                        wxString projectNameDep = deps.GetNextToken().Trim().Trim(false);
                        genericProject->deps.Add(projectNameDep);
                    }

                    genericWorkspace->projects.push_back(genericProject);

                    wxXmlNode* projectChild = rootChild->GetChildren();

                    while(projectChild) {
                        if(projectChild->GetName() == wxT("Option") && projectChild->HasAttribute(wxT("title"))) {
                            genericProject->name = projectChild->GetAttribute(wxT("title"));
                        }

                        if(projectChild->GetName() == wxT("Build")) {
                            wxXmlNode* buildChild = projectChild->GetChildren();

                            while(buildChild) {
                                if(buildChild->GetName() == wxT("Target") && buildChild->HasAttribute(wxT("title"))) {
                                    GenericProjectCfgPtr genericProjectCfg = std::make_shared<GenericProjectCfg>();
                                    genericProjectCfg->name = buildChild->GetAttribute(wxT("title"));
                                    genericProject->cfgs.push_back(genericProjectCfg);

                                    wxXmlNode* targetChild = buildChild->GetChildren();
                                    while(targetChild) {
                                        if(targetChild->GetName() == wxT("Option") &&
                                           targetChild->HasAttribute(wxT("output"))) {
                                            wxString output = targetChild->GetAttribute(wxT("output"));
                                            genericProjectCfg->outputFilename = output;
                                        }

                                        if(targetChild->GetName() == wxT("Option") &&
                                           targetChild->HasAttribute(wxT("working_dir"))) {
                                            wxString working_dir = targetChild->GetAttribute(wxT("working_dir"));
                                            genericProjectCfg->workingDirectory = working_dir;
                                        }

                                        if(targetChild->GetName() == wxT("Option") &&
                                           targetChild->HasAttribute(wxT("type"))) {
                                            wxString projectType = targetChild->GetAttribute(wxT("type"));

                                            if(projectType == wxT("2")) {
                                                genericProject->cfgType = GenericCfgType::STATIC_LIBRARY;
                                            } else if(projectType == wxT("3")) {
                                                genericProject->cfgType = GenericCfgType::DYNAMIC_LIBRARY;
                                            } else {
                                                genericProject->cfgType = GenericCfgType::EXECUTABLE;
                                            }

                                            genericProjectCfg->type = genericProject->cfgType;
                                        }

                                        if(targetChild->GetName() == wxT("Compiler")) {
                                            wxString compilerOptions = wxT(""), includePath = wxT("");

                                            wxXmlNode* compilerChild = targetChild->GetChildren();
                                            while(compilerChild) {
                                                if(compilerChild->GetName() == wxT("Add") &&
                                                   compilerChild->HasAttribute(wxT("option"))) {
                                                    compilerOptions +=
                                                        compilerChild->GetAttribute(wxT("option")) + wxT(" ");
                                                }

                                                if(compilerChild->GetName() == wxT("Add") &&
                                                   compilerChild->HasAttribute(wxT("directory"))) {
                                                    includePath +=
                                                        compilerChild->GetAttribute(wxT("directory")) + wxT(";");
                                                }

                                                compilerChild = compilerChild->GetNext();
                                            }

                                            if(includePath.Contains(wxT("#")))
                                                includePath.Replace(wxT("#"), wxT(""));

                                            genericProjectCfg->cCompilerOptions = compilerOptions;
                                            genericProjectCfg->cppCompilerOptions = compilerOptions;
                                            genericProjectCfg->includePath = includePath;
                                        }

                                        if(targetChild->GetName() == wxT("Linker")) {
                                            wxString linkerOptions = wxT(""), libPath = wxT(""), libraries = wxT("");

                                            wxXmlNode* linkerChild = targetChild->GetChildren();
                                            while(linkerChild) {
                                                if(linkerChild->GetName() == wxT("Add") &&
                                                   linkerChild->HasAttribute(wxT("option"))) {
                                                    linkerOptions +=
                                                        linkerChild->GetAttribute(wxT("option")) + wxT(" ");
                                                }

                                                if(linkerChild->GetName() == wxT("Add") &&
                                                   linkerChild->HasAttribute(wxT("directory"))) {
                                                    libPath += linkerChild->GetAttribute(wxT("directory")) + wxT(";");
                                                }

                                                if(linkerChild->GetName() == wxT("Add") &&
                                                   linkerChild->HasAttribute(wxT("library"))) {
                                                    libraries += linkerChild->GetAttribute(wxT("library")) + wxT(";");
                                                }

                                                linkerChild = linkerChild->GetNext();
                                            }

                                            if(libPath.Contains(wxT("#")))
                                                libPath.Replace(wxT("#"), wxT(""));

                                            genericProjectCfg->linkerOptions = linkerOptions;
                                            genericProjectCfg->libPath = libPath;
                                            genericProjectCfg->libraries = libraries;
                                        }

                                        targetChild = targetChild->GetNext();
                                    }
                                }

                                buildChild = buildChild->GetNext();
                            }
                        }

                        if(projectChild->GetName() == wxT("Compiler")) {
                            wxXmlNode* compilerChild = projectChild->GetChildren();
                            while(compilerChild) {
                                if(compilerChild->GetName() == wxT("Add") &&
                                   compilerChild->HasAttribute(wxT("option"))) {
                                    globalCompilerOptions += compilerChild->GetAttribute(wxT("option")) + wxT(" ");
                                }

                                if(compilerChild->GetName() == wxT("Add") &&
                                   compilerChild->HasAttribute(wxT("directory"))) {
                                    globalIncludePath += compilerChild->GetAttribute(wxT("directory")) + wxT(";");
                                }

                                compilerChild = compilerChild->GetNext();
                            }

                            if(globalIncludePath.Contains(wxT("#")))
                                globalIncludePath.Replace(wxT("#"), wxT(""));
                        }

                        if(projectChild->GetName() == wxT("Linker")) {
                            wxXmlNode* linkerChild = projectChild->GetChildren();
                            while(linkerChild) {
                                if(linkerChild->GetName() == wxT("Add") && linkerChild->HasAttribute(wxT("option"))) {
                                    globalLinkerOptions += linkerChild->GetAttribute(wxT("option")) + wxT(" ");
                                }

                                if(linkerChild->GetName() == wxT("Add") &&
                                   linkerChild->HasAttribute(wxT("directory"))) {
                                    globalLibPath += linkerChild->GetAttribute(wxT("directory")) + wxT(";");
                                }

                                if(linkerChild->GetName() == wxT("Add") && linkerChild->HasAttribute(wxT("library"))) {
                                    globalLibraries += linkerChild->GetAttribute(wxT("library")) + wxT(";");
                                }

                                linkerChild = linkerChild->GetNext();
                            }

                            if(globalLibPath.Contains(wxT("#")))
                                globalLibPath.Replace(wxT("#"), wxT(""));
                        }

                        if(projectChild->GetName() == wxT("Unit") && projectChild->HasAttribute(wxT("filename"))) {
                            wxString vpath = wxT("");
                            wxXmlNode* unitChild = projectChild->GetChildren();

                            while(unitChild) {
                                if(unitChild->GetName() == wxT("Option") &&
                                   unitChild->HasAttribute(wxT("virtualFolder"))) {
                                    vpath = unitChild->GetAttribute(wxT("virtualFolder"));
                                }
                                unitChild = unitChild->GetNext();
                            }

                            wxString projectFilename = projectChild->GetAttribute(wxT("filename"));
                            GenericProjectFilePtr genericProjectFile = std::make_shared<GenericProjectFile>();
                            genericProjectFile->name = projectFilename;
                            genericProjectFile->vpath = vpath;
                            genericProject->files.push_back(genericProjectFile);
                        }

                        projectChild = projectChild->GetNext();
                    }
                    
                    for(GenericProjectCfgPtr genericProjectCfg : genericProject->cfgs) {
                        genericProjectCfg->cCompilerOptions += globalCompilerOptions;
                        genericProjectCfg->cppCompilerOptions += globalCompilerOptions;
                        genericProjectCfg->includePath += globalIncludePath;
                        genericProjectCfg->linkerOptions += globalLinkerOptions;
                        genericProjectCfg->libPath += globalLibPath;
                        genericProjectCfg->libraries += globalLibraries;
                    }
                }

                rootChild = rootChild->GetNext();
            }
        }
    }
}