refactor project

This commit is contained in:
Roy Qu 2022-10-01 08:54:44 +08:00
parent c1b414d10a
commit e557a31848
11 changed files with 298 additions and 233 deletions

View File

@ -141,8 +141,7 @@ void ProjectCompiler::writeMakeDefines(QFile &file)
QString cleanObjects; QString cleanObjects;
// Create a list of object files // Create a list of object files
for (int i=0;i<mProject->units().count();i++) { foreach(const PProjectUnit &unit, mProject->unitList()) {
PProjectUnit unit = mProject->units()[i];
if (!unit->compile() && !unit->link()) if (!unit->compile() && !unit->link())
continue; continue;
@ -324,8 +323,8 @@ void ProjectCompiler::writeMakeObjFilesRules(QFile &file)
if (mProject->options().usePrecompiledHeader) if (mProject->options().usePrecompiledHeader)
precompileStr = " $(PCH) "; precompileStr = " $(PCH) ";
for (int i = 0;i<mProject->units().count();i++) { QList<PProjectUnit> projectUnits;
PProjectUnit unit = mProject->units()[i]; foreach(const PProjectUnit &unit, projectUnits) {
FileType fileType = getFileType(unit->fileName()); FileType fileType = getFileType(unit->fileName());
// Only process source files // Only process source files
if (fileType!=FileType::CSource && fileType!=FileType::CppSource) if (fileType!=FileType::CSource && fileType!=FileType::CppSource)
@ -343,8 +342,7 @@ void ProjectCompiler::writeMakeObjFilesRules(QFile &file)
continue; continue;
if (!parser->isSystemHeaderFile(headerName) if (!parser->isSystemHeaderFile(headerName)
&& ! parser->isProjectHeaderFile(headerName)) { && ! parser->isProjectHeaderFile(headerName)) {
for (int j = 0;j<mProject->units().count();j++) { foreach(const PProjectUnit &unit2, projectUnits) {
PProjectUnit unit2 = mProject->units()[j];
if (unit2->fileName()==headerName) { if (unit2->fileName()==headerName) {
objStr = objStr + ' ' + genMakePath2(extractRelativePath(mProject->makeFileName(),headerName)); objStr = objStr + ' ' + genMakePath2(extractRelativePath(mProject->makeFileName(),headerName));
break; break;
@ -353,10 +351,10 @@ void ProjectCompiler::writeMakeObjFilesRules(QFile &file)
} }
} }
} else { } else {
foreach (const PProjectUnit& u, mProject->units()) { foreach(const PProjectUnit &unit2, projectUnits) {
FileType fileType = getFileType(u->fileName()); FileType fileType = getFileType(unit2->fileName());
if (fileType == FileType::CHeader || fileType==FileType::CppHeader) if (fileType == FileType::CHeader || fileType==FileType::CppHeader)
objStr = objStr + ' ' + genMakePath2(extractRelativePath(mProject->makeFileName(),u->fileName())); objStr = objStr + ' ' + genMakePath2(extractRelativePath(mProject->makeFileName(),unit2->fileName()));
} }
} }
QString ObjFileName; QString ObjFileName;
@ -449,7 +447,7 @@ void ProjectCompiler::writeMakeObjFilesRules(QFile &file)
QString ResFiles; QString ResFiles;
// Concatenate all resource filenames (not created when syntax checking) // Concatenate all resource filenames (not created when syntax checking)
if (!mOnlyCheckSyntax) { if (!mOnlyCheckSyntax) {
foreach(const PProjectUnit& unit, mProject->units()) { foreach(const PProjectUnit& unit, mProject->unitList()) {
if (getFileType(unit->fileName())!=FileType::WindowsResourceSource) if (getFileType(unit->fileName())!=FileType::WindowsResourceSource)
continue; continue;
if (fileExists(unit->fileName())) { if (fileExists(unit->fileName())) {

View File

@ -177,7 +177,7 @@ void CppRefacter::doFindOccurenceInProject(PStatement statement, std::shared_ptr
statement->fullName, statement->fullName,
SearchFileScope::wholeProject SearchFileScope::wholeProject
); );
foreach (const PProjectUnit& unit, project->units()) { foreach (const PProjectUnit& unit, project->unitList()) {
if (isCFile(unit->fileName()) || isHFile(unit->fileName())) { if (isCFile(unit->fileName()) || isHFile(unit->fileName())) {
PSearchResultTreeItem item = findOccurenceInFile( PSearchResultTreeItem item = findOccurenceInFile(
unit->fileName(), unit->fileName(),

View File

@ -336,8 +336,8 @@ bool Editor::saveAs(const QString &name, bool fromProject){
} }
// Update project information // Update project information
if (mInProject && pMainWindow->project() && !fromProject) { if (mInProject && pMainWindow->project() && !fromProject) {
int unitIndex = pMainWindow->project()->indexInUnits(newName); int unitId = pMainWindow->project()->findUnitId(newName);
if (unitIndex<0) { if (unitId<0) {
mInProject = false; mInProject = false;
} }
} }
@ -423,9 +423,8 @@ void Editor::setEncodingOption(const QByteArray& encoding) noexcept{
if (mInProject) { if (mInProject) {
std::shared_ptr<Project> project = pMainWindow->project(); std::shared_ptr<Project> project = pMainWindow->project();
if (project) { if (project) {
int index = project->indexInUnits(this); PProjectUnit unit = project->findUnit(this);
if (index>=0) { if (unit) {
PProjectUnit unit = project->units()[index];
unit->setEncoding(mEncodingOption); unit->setEncoding(mEncodingOption);
} }
} }
@ -1740,7 +1739,7 @@ bool Editor::isBraceChar(QChar ch)
bool Editor::shouldOpenInReadonly() bool Editor::shouldOpenInReadonly()
{ {
if (pMainWindow->project() && pMainWindow->project()->findUnitByFilename(mFilename)) if (pMainWindow->project() && pMainWindow->project()->findUnit(mFilename))
return false; return false;
return pSettings->editor().readOnlySytemHeader() return pSettings->editor().readOnlySytemHeader()
&& mParser && (mParser->isSystemHeaderFile(mFilename) || mParser->isProjectHeaderFile(mFilename)); && mParser && (mParser->isSystemHeaderFile(mFilename) || mParser->isProjectHeaderFile(mFilename));

View File

@ -56,7 +56,7 @@ Editor* EditorList::newEditor(const QString& filename, const QByteArray& encodin
connect(e, &Editor::renamed, this, &EditorList::onEditorRenamed); connect(e, &Editor::renamed, this, &EditorList::onEditorRenamed);
updateLayout(); updateLayout();
if (pMainWindow->project()){ if (pMainWindow->project()){
PProjectUnit unit = pMainWindow->project()->findUnitByFilename(filename); PProjectUnit unit = pMainWindow->project()->findUnit(filename);
if (unit) { if (unit) {
pMainWindow->project()->associateEditorToUnit(e,unit); pMainWindow->project()->associateEditorToUnit(e,unit);
e->setInProject(true); e->setInProject(true);
@ -169,9 +169,9 @@ bool EditorList::closeEditor(Editor* editor, bool transferFocus, bool force) {
// } // }
if (editor->inProject() && pMainWindow->project()) { if (editor->inProject() && pMainWindow->project()) {
int projIndex = pMainWindow->project()->indexInUnits(editor); int unitId = pMainWindow->project()->findUnitId(editor);
if (projIndex>=0) { if (unitId>=0) {
pMainWindow->project()->closeUnit(projIndex); pMainWindow->project()->closeUnit(unitId);
} }
} else { } else {
if (pSettings->history().addToOpenedFiles(editor->filename())) { if (pSettings->history().addToOpenedFiles(editor->filename())) {

View File

@ -1186,7 +1186,7 @@ void MainWindow::openFile(const QString &filename, bool activate, QTabWidget* pa
pSettings->history().removeFile(filename); pSettings->history().removeFile(filename);
PProjectUnit unit; PProjectUnit unit;
if (mProject) { if (mProject) {
unit = mProject->findUnitByFilename(filename); unit = mProject->findUnit(filename);
} }
bool inProject = (mProject && unit); bool inProject = (mProject && unit);
QByteArray encoding = unit ? unit->encoding() : QByteArray encoding = unit ? unit->encoding() :
@ -1260,8 +1260,7 @@ void MainWindow::openProject(const QString &filename, bool openFiles)
mProject->doAutoOpen(); mProject->doAutoOpen();
//update editor's inproject flag //update editor's inproject flag
for (int i=0;i<mProject->units().count();i++) { foreach (PProjectUnit unit, mProject->unitList()) {
PProjectUnit unit = mProject->units()[i];
Editor* e = mEditorList->getOpenedEditorByFilename(unit->fileName()); Editor* e = mEditorList->getOpenedEditorByFilename(unit->fileName());
mProject->associateEditorToUnit(e,unit); mProject->associateEditorToUnit(e,unit);
} }
@ -2214,7 +2213,7 @@ void MainWindow::loadLastOpens()
page = mEditorList->rightPageWidget(); page = mEditorList->rightPageWidget();
PProjectUnit unit; PProjectUnit unit;
if (mProject) { if (mProject) {
unit = mProject->findUnitByFilename(editorFilename); unit = mProject->findUnit(editorFilename);
} }
bool inProject = (mProject && unit); bool inProject = (mProject && unit);
QByteArray encoding = unit ? unit->encoding() : QByteArray encoding = unit ? unit->encoding() :
@ -3022,7 +3021,7 @@ void MainWindow::onProjectViewContextMenu(const QPoint &pos)
shouldAdd=false; shouldAdd=false;
break; break;
} }
PProjectUnit pUnit=mProject->units()[node->unitIndex]; PProjectUnit pUnit=mProject->findUnitById(node->unitIndex);
if (mProject->model()->iconProvider()->VCSRepository()->isFileInRepository( if (mProject->model()->iconProvider()->VCSRepository()->isFileInRepository(
pUnit->fileName() pUnit->fileName()
) )
@ -3919,7 +3918,7 @@ void MainWindow::onProjectAddFolder()
QLineEdit::Normal, s, QLineEdit::Normal, s,
&ok).trimmed(); &ok).trimmed();
if (ok && !s.isEmpty()) { if (ok && !s.isEmpty()) {
QString path = mProject->getFolderPath(folderNode); QString path = mProject->getNodePath(folderNode);
if (path.isEmpty()) { if (path.isEmpty()) {
mProject->addFolder(s); mProject->addFolder(s);
} else { } else {
@ -5915,10 +5914,9 @@ void MainWindow::on_actionAdd_to_project_triggered()
); );
} }
} }
mProject->rebuildNodes();
mProject->saveUnits(); mProject->saveUnits();
updateProjectActions();
parseFileList(mProject->cppParser()); parseFileList(mProject->cppParser());
updateProjectView();
} }
} }
@ -5929,8 +5927,11 @@ void MainWindow::on_actionRemove_from_project_triggered()
return; return;
if (!ui->projectView->selectionModel()->hasSelection()) if (!ui->projectView->selectionModel()->hasSelection())
return; return;
mProject->model()->beginUpdate();
QSet<int> selected; bool removeFile = (QMessageBox::question(this,tr("Remove file"),
tr("Remove the file from disk?"),
QMessageBox::Yes | QMessageBox::No) == QMessageBox::Yes);
foreach (const QModelIndex& index, ui->projectView->selectionModel()->selectedIndexes()){ foreach (const QModelIndex& index, ui->projectView->selectionModel()->selectedIndexes()){
if (!index.isValid()) if (!index.isValid())
continue; continue;
@ -5939,22 +5940,10 @@ void MainWindow::on_actionRemove_from_project_triggered()
PProjectModelNode folderNode = mProject->pointerToNode(node); PProjectModelNode folderNode = mProject->pointerToNode(node);
if (!folderNode) if (!folderNode)
continue; continue;
selected.insert(folderNode->unitIndex); mProject->removeUnit(folderNode->unitIndex, true, removeFile);
}; };
bool removeFile = (QMessageBox::question(this,tr("Remove file"),
tr("Remove the file from disk?"),
QMessageBox::Yes | QMessageBox::No) == QMessageBox::Yes);
for (int i=mProject->units().count()-1;i>=0;i--) {
if (selected.contains(i)) {
mProject->removeUnit(i,true,removeFile);
}
}
mProject->saveUnits(); mProject->saveUnits();
mProject->model()->endUpdate(); updateProjectActions();
updateProjectView();
} }
@ -6135,7 +6124,6 @@ void MainWindow::newProjectUnitFile()
{ {
if (!mProject) if (!mProject)
return; return;
int idx = -1;
QModelIndex current = mProjectProxyModel->mapToSource(ui->projectView->currentIndex()); QModelIndex current = mProjectProxyModel->mapToSource(ui->projectView->currentIndex());
ProjectModelNode * node = nullptr; ProjectModelNode * node = nullptr;
if (current.isValid()) { if (current.isValid()) {
@ -6217,11 +6205,11 @@ void MainWindow::newProjectUnitFile()
newUnit = mProject->newUnit( newUnit = mProject->newUnit(
pNode,newFileName); pNode,newFileName);
mProject->rebuildNodes(); // mProject->rebuildNodes();
mProject->saveAll(); mProject->saveAll();
updateProjectView(); // updateProjectView();
idx = mProject->units().count()-1; // idx = newUnit->id;
Editor * editor = mProject->openUnit(idx, false); Editor * editor = mProject->openUnit(newUnit->id(), false);
//editor->setUseCppSyntax(mProject->options().useGPP); //editor->setUseCppSyntax(mProject->options().useGPP);
//editor->setModified(true); //editor->setModified(true);
if (editor) if (editor)
@ -6233,7 +6221,7 @@ void MainWindow::newProjectUnitFile()
mProject->model()->beginUpdate(); mProject->model()->beginUpdate();
mProject->model()->endUpdate(); mProject->model()->endUpdate();
} }
updateProjectView(); updateProjectActions();
} }
void MainWindow::fillProblemCaseInputAndExpected(const POJProblemCase &problemCase) void MainWindow::fillProblemCaseInputAndExpected(const POJProblemCase &problemCase)
@ -7484,7 +7472,7 @@ void MainWindow::on_actionGit_Create_Repository_triggered()
QString output; QString output;
vcsManager.add(mProject->folder(), extractFileName(mProject->filename()), output); vcsManager.add(mProject->folder(), extractFileName(mProject->filename()), output);
vcsManager.add(mProject->folder(), extractFileName(mProject->options().icon), output); vcsManager.add(mProject->folder(), extractFileName(mProject->options().icon), output);
foreach (PProjectUnit pUnit, mProject->units()) { foreach (PProjectUnit pUnit, mProject->unitList()) {
vcsManager.add(mProject->folder(),extractRelativePath(mProject->folder(),pUnit->fileName()),output); vcsManager.add(mProject->folder(),extractRelativePath(mProject->folder(),pUnit->fileName()),output);
} }
//update project view //update project view
@ -7528,7 +7516,7 @@ void MainWindow::on_actionGit_Add_Files_triggered()
if (!folderNode) if (!folderNode)
continue; continue;
if (folderNode->unitIndex>=0) { if (folderNode->unitIndex>=0) {
PProjectUnit unit = mProject->units()[folderNode->unitIndex]; PProjectUnit unit = mProject->findUnitById(folderNode->unitIndex);
QFileInfo info(unit->fileName()); QFileInfo info(unit->fileName());
QString output; QString output;
vcsManager.add(info.absolutePath(),info.fileName(),output); vcsManager.add(info.absolutePath(),info.fileName(),output);

View File

@ -473,7 +473,7 @@
<enum>QTabWidget::West</enum> <enum>QTabWidget::West</enum>
</property> </property>
<property name="currentIndex"> <property name="currentIndex">
<number>4</number> <number>1</number>
</property> </property>
<property name="usesScrollButtons"> <property name="usesScrollButtons">
<bool>true</bool> <bool>true</bool>

View File

@ -190,9 +190,12 @@ void Project::open()
} }
newUnit->setNew(false); newUnit->setNew(false);
newUnit->setParent(this); newUnit->setParent(this);
newUnit->setNode(makeNewFileNode(extractFileName(newUnit->fileName()), false, folderNodeFromName(newUnit->folder()))); PProjectModelNode node = makeNewFileNode(extractFileName(newUnit->fileName()),
newUnit->node()->unitIndex = mUnits.count(); newUnit->id(),
mUnits.append(newUnit); newUnit->priority(),
folderNodeFromName(newUnit->folder()));
newUnit->setNode(node);
mUnits.insert(newUnit->id(),newUnit);
} }
rebuildNodes(); rebuildNodes();
} }
@ -215,7 +218,9 @@ void Project::setModified(bool value)
} }
} }
PProjectModelNode Project::makeNewFileNode(const QString &s, bool isFolder, PProjectModelNode newParent) PProjectModelNode Project::makeNewFolderNode(
const QString &folderName, PProjectModelNode newParent,
ProjectModelNodeType nodeType,int priority)
{ {
PProjectModelNode node = std::make_shared<ProjectModelNode>(); PProjectModelNode node = std::make_shared<ProjectModelNode>();
if (!newParent) { if (!newParent) {
@ -223,17 +228,35 @@ PProjectModelNode Project::makeNewFileNode(const QString &s, bool isFolder, PPro
} }
newParent->children.append(node); newParent->children.append(node);
node->parent = newParent; node->parent = newParent;
node->text = s; node->text = folderName;
if (newParent) { if (newParent) {
node->level = newParent->level+1; node->level = newParent->level+1;
} }
if (isFolder) { node->unitIndex = -1;
node->unitIndex = -1; node->priority = priority;
node->priority = 0; node->folderNodeType = nodeType;
node->folderNodeType = ProjectModelNodeType::Folder; QModelIndex parentIndex=mModel.getNodeIndex(newParent.get());
} else { mModel.insertRow(newParent->children.count(),parentIndex);
node->folderNodeType = ProjectModelNodeType::File; return node;
}
PProjectModelNode Project::makeNewFileNode(const QString &fileName, int unitId,int priority, PProjectModelNode newParent)
{
PProjectModelNode node = std::make_shared<ProjectModelNode>();
if (!newParent) {
newParent = mRootNode;
} }
newParent->children.append(node);
node->parent = newParent;
node->text = fileName;
if (newParent) {
node->level = newParent->level+1;
}
node->unitIndex = unitId;
node->priority = priority;
node->folderNodeType = ProjectModelNodeType::File;
QModelIndex parentIndex=mModel.getNodeIndex(newParent.get());
mModel.insertRow(newParent->children.count(),parentIndex);
return node; return node;
} }
@ -269,16 +292,17 @@ PProjectUnit Project::newUnit(PProjectModelNode parentNode, const QString& custo
s = dir.absoluteFilePath(customFileName); s = dir.absoluteFilePath(customFileName);
} }
// Add // Add
int count = mUnits.count();
mUnits.append(newUnit);
// Set all properties // Set all properties
newUnit->setFileName(s); newUnit->setFileName(s);
newUnit->setNew(true); newUnit->setNew(true);
newUnit->setFolder(getFolderPath(parentNode)); newUnit->setFolder(getNodePath(parentNode));
newUnit->setNode(makeNewFileNode(extractFileName(newUnit->fileName()), PProjectModelNode node = makeNewFileNode(extractFileName(newUnit->fileName()),
false, parentNode)); newUnit->id(),newUnit->priority(),parentNode);
newUnit->node()->unitIndex = count; node->unitIndex = newUnit->id();
newUnit->setNode(node);
mUnits.insert(newUnit->id(), newUnit);
//parentNode.Expand(True); //parentNode.Expand(True);
switch(getFileType(customFileName)) { switch(getFileType(customFileName)) {
case FileType::CSource: case FileType::CSource:
@ -311,10 +335,10 @@ PProjectUnit Project::newUnit(PProjectModelNode parentNode, const QString& custo
Editor *Project::openUnit(int index, bool forceOpen) Editor *Project::openUnit(int index, bool forceOpen)
{ {
if ((index < 0) || (index >= mUnits.count()))
return nullptr;
PProjectUnit unit = mUnits[index]; PProjectUnit unit = mUnits.value(index,PProjectUnit());
if (!unit)
return nullptr;
if (!unit->fileName().isEmpty() && fileExists(unit->fileName())) { if (!unit->fileName().isEmpty() && fileExists(unit->fileName())) {
if (getFileType(unit->fileName())==FileType::Other) { if (getFileType(unit->fileName())==FileType::Other) {
@ -353,6 +377,15 @@ Editor *Project::unitEditor(const ProjectUnit *unit) const
return mEditorList->getOpenedEditorByFilename(unit->fileName()); return mEditorList->getOpenedEditorByFilename(unit->fileName());
} }
QList<PProjectUnit> Project::unitList()
{
QList<PProjectUnit> units;
foreach(PProjectUnit unit, mUnits) {
units.append(unit);
}
return units;
}
void Project::rebuildNodes() void Project::rebuildNodes()
{ {
mModel.beginUpdate(); mModel.beginUpdate();
@ -366,35 +399,34 @@ void Project::rebuildNodes()
switch(mOptions.modelType) { switch(mOptions.modelType) {
case ProjectModelType::Custom: case ProjectModelType::Custom:
createFolderNodes(); createFolderNodes();
foreach (PProjectUnit pUnit, mUnits) {
for (int idx=0;idx<mUnits.count();idx++) { QFileInfo fileInfo(pUnit->fileName());
QFileInfo fileInfo(mUnits[idx]->fileName()); pUnit->setNode(
mUnits[idx]->setNode(
makeNewFileNode( makeNewFileNode(
fileInfo.fileName(), fileInfo.fileName(),
false, pUnit->id(),
folderNodeFromName(mUnits[idx]->folder()) pUnit->priority(),
folderNodeFromName(pUnit->folder())
) )
); );
mUnits[idx]->node()->unitIndex = idx; pUnit->node()->priority = pUnit->priority();
mUnits[idx]->node()->priority = mUnits[idx]->priority();
} }
break; break;
case ProjectModelType::FileSystem: case ProjectModelType::FileSystem:
createFileSystemFolderNodes(); createFileSystemFolderNodes();
for (int idx=0;idx<mUnits.count();idx++) { foreach (PProjectUnit pUnit, mUnits) {
QFileInfo fileInfo(mUnits[idx]->fileName()); QFileInfo fileInfo(pUnit->fileName());
mUnits[idx]->setNode( pUnit->setNode(
makeNewFileNode( makeNewFileNode(
fileInfo.fileName(), fileInfo.fileName(),
false, pUnit->id(),
pUnit->priority(),
getParentFolderNode( getParentFolderNode(
mUnits[idx]->fileName()) pUnit->fileName())
) )
); );
mUnits[idx]->node()->unitIndex = idx; pUnit->node()->priority = pUnit->priority();
mUnits[idx]->node()->priority = mUnits[idx]->priority();
} }
break; break;
@ -404,17 +436,12 @@ void Project::rebuildNodes()
emit nodesChanged(); emit nodesChanged();
} }
bool Project::removeUnit(int index, bool doClose , bool removeFile) bool Project::removeUnit(int id, bool doClose , bool removeFile)
{ {
mModel.beginUpdate(); PProjectUnit unit = findUnitById(id);
auto action = finally([this]{ if (!unit)
mModel.endUpdate();
});
if (index<0 || index>=mUnits.count())
return false; return false;
PProjectUnit unit = mUnits[index];
// qDebug()<<unit->fileName(); // qDebug()<<unit->fileName();
// qDebug()<<(qint64)unit->editor(); // qDebug()<<(qint64)unit->editor();
// Attempt to close it // Attempt to close it
@ -432,12 +459,20 @@ bool Project::removeUnit(int index, bool doClose , bool removeFile)
//if not fUnits.GetItem(index).fNew then //if not fUnits.GetItem(index).fNew then
PProjectModelNode node = unit->node(); PProjectModelNode node = unit->node();
PProjectModelNode parent = node->parent.lock(); PProjectModelNode parentNode = node->parent.lock();
if (parent) { if (!parentNode)
parent->children.removeAll(node); return true;
} QModelIndex parentIndex = mModel.getParentIndex(unit->node().get());
mUnits.removeAt(index);
updateNodeIndexes(); int row = parentNode->children.indexOf(unit->node());
if (row<0)
return true;
parentNode->children.removeAt(row);
mUnits.remove(unit->id());
mModel.removeRow(row,parentIndex);
setModified(true); setModified(true);
return true; return true;
} }
@ -495,7 +530,7 @@ void Project::saveLayout()
for (int i=0;i<mEditorList->pageCount();i++) { for (int i=0;i<mEditorList->pageCount();i++) {
Editor* e= (*mEditorList)[i]; Editor* e= (*mEditorList)[i];
if (e && e->inProject()) if (e && e->inProject())
sl.append(QString("%1").arg(indexInUnits(e))); sl.append(QString("%1").arg(findUnitId(e)));
} }
layIni.SetValue("Editors","Order",sl.join(",").toUtf8()); layIni.SetValue("Editors","Order",sl.join(",").toUtf8());
@ -503,11 +538,10 @@ void Project::saveLayout()
// Remember what files were visible // Remember what files were visible
mEditorList->getVisibleEditors(e, e2); mEditorList->getVisibleEditors(e, e2);
if (e) if (e)
layIni.SetLongValue("Editors","Focused", indexInUnits(e)); layIni.SetLongValue("Editors","Focused", findUnitId(e));
// save editor info // save editor info
for (int i=0;i<mUnits.count();i++) { foreach (const PProjectUnit& unit,mUnits) {
QByteArray groupName = QString("Editor_%1").arg(i).toUtf8(); QByteArray groupName = QString("Editor_%1").arg(unit->id()).toUtf8();
PProjectUnit unit = mUnits[i];
Editor* editor = unitEditor(unit); Editor* editor = unitEditor(unit);
if (editor) { if (editor) {
layIni.SetLongValue(groupName,"CursorCol", editor->caretX()); layIni.SetLongValue(groupName,"CursorCol", editor->caretX());
@ -530,51 +564,22 @@ void Project::saveLayout()
layIni.SaveFile(changeFileExt(filename(), "layout").toLocal8Bit()); layIni.SaveFile(changeFileExt(filename(), "layout").toLocal8Bit());
} }
void Project::saveUnitAs(int i, const QString &sFileName, bool syncEditor) void Project::renameUnit(int idx, const QString &sFileName)
{ {
if ((i < 0) || (i >= mUnits.count())) PProjectUnit unit = findUnitById(idx);
if (!unit)
return; return;
PProjectUnit unit = mUnits[i];
if (fileExists(unit->fileName())) { if (fileExists(unit->fileName())) {
unit->setNew(false); unit->setNew(false);
} }
Editor * editor=unitEditor(unit); Editor * editor=unitEditor(unit);
if (editor && syncEditor) { if (editor) {
//prevent recurse //prevent recurse
editor->saveAs(sFileName,true); editor->saveAs(sFileName,true);
} }
unit->setNew(false); unit->setNew(false);
unit->setFileName(sFileName); unit->setFileName(sFileName);
SimpleIni ini;
ini.LoadFile(mFilename.toLocal8Bit());
QByteArray groupName = toByteArray(QString("Unit%1").arg(i+1));
ini.SetValue(
groupName,
"FileName",
toByteArray(
extractRelativePath(
directory(),
sFileName)));
ini.SaveFile(mFilename.toLocal8Bit());
setModified(true); setModified(true);
if (!syncEditor) {
//the call it's from editor, we need to update model
mModel.beginUpdate();
mModel.endUpdate();
}
}
void Project::saveUnitLayout(Editor *e, int index)
{
if (!e)
return;
SimpleIni layIni;
QByteArray groupName = (QString("Editor_%1").arg(index)).toUtf8();
layIni.SetLongValue(groupName,"CursorCol", e->caretX());
layIni.SetLongValue(groupName,"CursorRow", e->caretY());
layIni.SetLongValue(groupName,"TopLine", e->topLine());
layIni.SetLongValue(groupName,"LeftChar", e->leftChar());
layIni.SaveFile((changeFileExt(filename(), "layout")).toLocal8Bit());
} }
bool Project::saveUnits() bool Project::saveUnits()
@ -584,9 +589,10 @@ bool Project::saveUnits()
SI_Error error = ini.LoadFile(mFilename.toLocal8Bit()); SI_Error error = ini.LoadFile(mFilename.toLocal8Bit());
if (error != SI_Error::SI_OK) if (error != SI_Error::SI_OK)
return false; return false;
for (int idx = 0; idx < mUnits.count(); idx++) { int i=0;
PProjectUnit unit = mUnits[idx]; foreach (const PProjectUnit& unit, mUnits) {
QByteArray groupName = toByteArray(QString("Unit%1").arg(count+1)); i++;
QByteArray groupName = toByteArray(QString("Unit%1").arg(i));
if (!unit->FileMissing()) { if (!unit->FileMissing()) {
bool rd_only = false; bool rd_only = false;
if (unit->modified() && fileExists(unit->fileName()) if (unit->modified() && fileExists(unit->fileName())
@ -642,7 +648,12 @@ bool Project::saveUnits()
return true; return true;
} }
PProjectUnit Project::findUnitByFilename(const QString &filename) PProjectUnit Project::findUnitById(int id)
{
return mUnits.value(id,PProjectUnit());
}
PProjectUnit Project::findUnit(const QString &filename)
{ {
foreach(PProjectUnit unit, mUnits) { foreach(PProjectUnit unit, mUnits) {
if (QString::compare(unit->fileName(),filename, PATH_SENSITIVITY)==0) if (QString::compare(unit->fileName(),filename, PATH_SENSITIVITY)==0)
@ -651,11 +662,16 @@ PProjectUnit Project::findUnitByFilename(const QString &filename)
return PProjectUnit(); return PProjectUnit();
} }
void Project::associateEditor(Editor *editor) PProjectUnit Project::findUnit(const Editor *editor)
{ {
if (!editor) if (!editor)
return; return PProjectUnit();
PProjectUnit unit = findUnitByFilename(editor->filename()); return findUnit(editor->filename());
}
void Project::associateEditor(Editor *editor)
{
PProjectUnit unit = findUnit(editor);
associateEditorToUnit(editor,unit); associateEditorToUnit(editor,unit);
} }
@ -718,21 +734,16 @@ void Project::updateFolders()
{ {
mFolders.clear(); mFolders.clear();
updateFolderNode(mRootNode); updateFolderNode(mRootNode);
for (int idx = 0; idx < mUnits.count();idx++) foreach (PProjectUnit unit, mUnits) {
mUnits[idx]->setFolder( unit->setFolder(
getFolderPath( getNodePath(
mUnits[idx]->node()->parent.lock() unit->node()->parent.lock()
) )
); );
}
setModified(true); setModified(true);
} }
void Project::updateNodeIndexes()
{
for (int idx = 0;idx<mUnits.count();idx++)
mUnits[idx]->node()->unitIndex = idx;
}
PProjectModelNode Project::pointerToNode(ProjectModelNode *p, PProjectModelNode parent) PProjectModelNode Project::pointerToNode(ProjectModelNode *p, PProjectModelNode parent)
{ {
if (!p) if (!p)
@ -906,8 +917,8 @@ bool Project::saveAsTemplate(const QString &templateFolder,
if (mOptions.modelType!=ProjectModelType::FileSystem) if (mOptions.modelType!=ProjectModelType::FileSystem)
ini->SetLongValue("Project", "ModelType", (int)mOptions.modelType); ini->SetLongValue("Project", "ModelType", (int)mOptions.modelType);
for (int i=0;i<mUnits.count();i++) { int i=0;
const PProjectUnit& unit=mUnits[i]; foreach (const PProjectUnit &unit, mUnits) {
QString unitName = extractFileName(unit->fileName()); QString unitName = extractFileName(unit->fileName());
QByteArray section = toByteArray(QString("Unit%1").arg(i)); QByteArray section = toByteArray(QString("Unit%1").arg(i));
if (!copyFile(unit->fileName(), dir.absoluteFilePath(unitName),true)) { if (!copyFile(unit->fileName(), dir.absoluteFilePath(unitName),true)) {
@ -936,6 +947,7 @@ bool Project::saveAsTemplate(const QString &templateFolder,
ini->SetValue(section,"Source", unitName.toUtf8()); ini->SetValue(section,"Source", unitName.toUtf8());
ini->SetValue(section,"Target", unitName.toUtf8()); ini->SetValue(section,"Target", unitName.toUtf8());
} }
i++;
} }
ini->SetLongValue("Project","UnitCount",mUnits.count()); ini->SetLongValue("Project","UnitCount",mUnits.count());
if (ini->SaveFile(fileName.toLocal8Bit())!=SI_OK) { if (ini->SaveFile(fileName.toLocal8Bit())!=SI_OK) {
@ -1066,10 +1078,13 @@ PProjectUnit Project::addUnit(const QString &inFileName, PProjectModelNode paren
} else { } else {
newUnit->setEncoding(options().encoding.toUtf8()); newUnit->setEncoding(options().encoding.toUtf8());
} }
newUnit->setFolder(getFolderPath(parentNode)); newUnit->setFolder(getNodePath(parentNode));
newUnit->setNode(makeNewFileNode(extractFileName(newUnit->fileName()), false, parentNode)); PProjectModelNode node = makeNewFileNode(extractFileName(newUnit->fileName()),
newUnit->node()->unitIndex = mUnits.count(); newUnit->id(),
mUnits.append(newUnit); newUnit->priority(), parentNode);
node->unitIndex = newUnit->id();
newUnit->setNode(node);
mUnits.insert(newUnit->id(),newUnit);
// Determine compilation flags // Determine compilation flags
switch(getFileType(inFileName)) { switch(getFileType(inFileName)) {
@ -1436,12 +1451,11 @@ void Project::checkProjectFileForUpdate(SimpleIni &ini)
QMessageBox::Ok); QMessageBox::Ok);
} }
void Project::closeUnit(int index) void Project::closeUnit(int id)
{ {
PProjectUnit unit = mUnits[index]; PProjectUnit unit = findUnitById(id);
Editor * editor =unitEditor(unit); Editor * editor =unitEditor(unit);
if (editor) { if (editor) {
saveUnitLayout(editor,index);
editor->setInProject(false); editor->setInProject(false);
mEditorList->forceCloseEditor(editor); mEditorList->forceCloseEditor(editor);
} }
@ -1460,14 +1474,14 @@ void Project::createFolderNodes()
findnode = node->children[c]; findnode = node->children[c];
} }
if (!findnode) if (!findnode)
node = makeNewFileNode(s.mid(0,i),true,node); node = makeNewFolderNode(s.mid(0,i),node);
else else
node = findnode; node = findnode;
node->unitIndex = -1; node->unitIndex = -1;
s.remove(0,i+1); s.remove(0,i+1);
i = s.indexOf('/'); i = s.indexOf('/');
} }
node = makeNewFileNode(s, true, node); node = makeNewFolderNode(s, node);
node->unitIndex = -1; node->unitIndex = -1;
mFolderNodes.append(node); mFolderNodes.append(node);
} }
@ -1488,8 +1502,8 @@ void Project::createFileSystemFolderNodes()
QSet<QString> headerFolders; QSet<QString> headerFolders;
QSet<QString> sourceFolders; QSet<QString> sourceFolders;
QSet<QString> otherFolders; QSet<QString> otherFolders;
for (int idx=0;idx<mUnits.count();idx++) { foreach (const PProjectUnit& unit, mUnits) {
QFileInfo fileInfo(mUnits[idx]->fileName()); QFileInfo fileInfo(unit->fileName());
if (isHFile(fileInfo.fileName())) { if (isHFile(fileInfo.fileName())) {
addFolderRecursively(headerFolders,fileInfo.absolutePath()); addFolderRecursively(headerFolders,fileInfo.absolutePath());
} else if (isCFile(fileInfo.fileName())) { } else if (isCFile(fileInfo.fileName())) {
@ -1498,23 +1512,26 @@ void Project::createFileSystemFolderNodes()
addFolderRecursively(otherFolders,fileInfo.absolutePath()); addFolderRecursively(otherFolders,fileInfo.absolutePath());
} }
} }
PProjectModelNode node = makeNewFileNode(tr("Headers"),true,mRootNode); PProjectModelNode node = makeNewFolderNode(tr("Headers"),
node->folderNodeType = ProjectModelNodeType::DUMMY_HEADERS_FOLDER; mRootNode,
node->priority = 1000; ProjectModelNodeType::DUMMY_HEADERS_FOLDER,
1000);
createFileSystemFolderNode(ProjectModelNodeType::DUMMY_HEADERS_FOLDER,folder(),node, headerFolders); createFileSystemFolderNode(ProjectModelNodeType::DUMMY_HEADERS_FOLDER,folder(),node, headerFolders);
mFolderNodes.append(node); mFolderNodes.append(node);
mSpecialNodes.insert(ProjectModelNodeType::DUMMY_HEADERS_FOLDER,node); mSpecialNodes.insert(ProjectModelNodeType::DUMMY_HEADERS_FOLDER,node);
node = makeNewFileNode(tr("Sources"),true,mRootNode); node = makeNewFolderNode(tr("Sources"),
node->folderNodeType = ProjectModelNodeType::DUMMY_SOURCES_FOLDER; mRootNode,
node->priority = 900; ProjectModelNodeType::DUMMY_SOURCES_FOLDER,
900);
createFileSystemFolderNode(ProjectModelNodeType::DUMMY_SOURCES_FOLDER,folder(),node, sourceFolders); createFileSystemFolderNode(ProjectModelNodeType::DUMMY_SOURCES_FOLDER,folder(),node, sourceFolders);
mFolderNodes.append(node); mFolderNodes.append(node);
mSpecialNodes.insert(ProjectModelNodeType::DUMMY_SOURCES_FOLDER,node); mSpecialNodes.insert(ProjectModelNodeType::DUMMY_SOURCES_FOLDER,node);
node = makeNewFileNode(tr("Others"),true,mRootNode); node = makeNewFolderNode(tr("Others"),
node->folderNodeType = ProjectModelNodeType::DUMMY_OTHERS_FOLDER; mRootNode,
node->priority = 800; ProjectModelNodeType::DUMMY_OTHERS_FOLDER,
800);
createFileSystemFolderNode(ProjectModelNodeType::DUMMY_OTHERS_FOLDER,folder(),node, otherFolders); createFileSystemFolderNode(ProjectModelNodeType::DUMMY_OTHERS_FOLDER,folder(),node, otherFolders);
mFolderNodes.append(node); mFolderNodes.append(node);
mSpecialNodes.insert(ProjectModelNodeType::DUMMY_OTHERS_FOLDER,node); mSpecialNodes.insert(ProjectModelNodeType::DUMMY_OTHERS_FOLDER,node);
@ -1533,7 +1550,7 @@ void Project::createFileSystemFolderNode(
if (fileInfo.isHidden() || fileInfo.fileName().startsWith('.')) if (fileInfo.isHidden() || fileInfo.fileName().startsWith('.'))
continue; continue;
if (fileInfo.isDir() && validFolders.contains(fileInfo.absoluteFilePath())) { if (fileInfo.isDir() && validFolders.contains(fileInfo.absoluteFilePath())) {
PProjectModelNode node = makeNewFileNode(fileInfo.fileName(),true,parent); PProjectModelNode node = makeNewFolderNode(fileInfo.fileName(),parent);
mFileSystemFolderNodes.insert(QString("%1/%2").arg((int)folderType).arg(fileInfo.absoluteFilePath()),node); mFileSystemFolderNodes.insert(QString("%1/%2").arg((int)folderType).arg(fileInfo.absoluteFilePath()),node);
createFileSystemFolderNode(folderType,fileInfo.absoluteFilePath(), node, validFolders); createFileSystemFolderNode(folderType,fileInfo.absoluteFilePath(), node, validFolders);
} }
@ -1575,7 +1592,7 @@ PProjectModelNode Project::folderNodeFromName(const QString &name)
return mRootNode; return mRootNode;
} }
QString Project::getFolderPath(PProjectModelNode node) QString Project::getNodePath(PProjectModelNode node)
{ {
QString result; QString result;
if (!node) if (!node)
@ -1597,7 +1614,7 @@ QString Project::getFolderPath(PProjectModelNode node)
int Project::getUnitFromString(const QString &s) int Project::getUnitFromString(const QString &s)
{ {
return indexInUnits(s); return findUnitId(s);
} }
PProjectModelNode Project::getParentFolderNode(const QString &filename) PProjectModelNode Project::getParentFolderNode(const QString &filename)
@ -1651,8 +1668,9 @@ void Project::loadLayout()
openUnit(currIdx); openUnit(currIdx);
} }
} }
if (topLeft>=0 && topLeft<mUnits.count()) { PProjectUnit unit = findUnitById(topLeft);
Editor * editor = unitEditor(mUnits[topLeft]); if (unit) {
Editor * editor = unitEditor(unit);
if (editor) if (editor)
editor->activate(); editor->activate();
} }
@ -1919,22 +1937,21 @@ PCppParser Project::cppParser()
return mParser; return mParser;
} }
int Project::indexInUnits(const QString &fileName) const int Project::findUnitId(const QString &fileName) const
{ {
QDir dir(directory()); QDir dir(directory());
for (int i=0;i<mUnits.count();i++) { foreach (const PProjectUnit& unit, mUnits) {
PProjectUnit unit = mUnits[i];
if (dir.absoluteFilePath(fileName) == dir.absoluteFilePath(unit->fileName())) if (dir.absoluteFilePath(fileName) == dir.absoluteFilePath(unit->fileName()))
return i; return unit->id();
} }
return -1; return -1;
} }
int Project::indexInUnits(const Editor *editor) const int Project::findUnitId(const Editor *editor) const
{ {
if (!editor) if (!editor)
return -1; return -1;
return indexInUnits(editor->filename()); return findUnitId(editor->filename());
} }
void Project::removeFolderRecurse(PProjectModelNode node) void Project::removeFolderRecurse(PProjectModelNode node)
@ -1967,7 +1984,7 @@ void Project::updateFolderNode(PProjectModelNode node)
for (int i=0;i<node->children.count();i++){ for (int i=0;i<node->children.count();i++){
PProjectModelNode child = node->children[i]; PProjectModelNode child = node->children[i];
if (child->unitIndex<0) { if (child->unitIndex<0) {
mFolders.append(getFolderPath(child)); mFolders.append(getNodePath(child));
updateFolderNode(child); updateFolderNode(child);
} }
} }
@ -2020,11 +2037,6 @@ EditorList *Project::editorList() const
return mEditorList; return mEditorList;
} }
const QList<PProjectUnit> &Project::units() const
{
return mUnits;
}
ProjectModelType Project::modelType() const ProjectModelType Project::modelType() const
{ {
return mOptions.modelType; return mOptions.modelType;
@ -2072,11 +2084,15 @@ const QString &Project::filename() const
return mFilename; return mFilename;
} }
int ProjectUnit::mIdGenerator=0;
ProjectUnit::ProjectUnit(Project* parent) ProjectUnit::ProjectUnit(Project* parent)
{ {
mNode = nullptr; mNode = nullptr;
mParent = parent; mParent = parent;
mFileMissing = false; mFileMissing = false;
mId=mIdGenerator++;
mPriority=0;
} }
Project *ProjectUnit::parent() const Project *ProjectUnit::parent() const
@ -2270,6 +2286,16 @@ void ProjectUnit::setFileMissing(bool newDontSave)
mFileMissing = newDontSave; mFileMissing = newDontSave;
} }
int ProjectUnit::id() const
{
return mId;
}
void ProjectUnit::setId(int newId)
{
mId = newId;
}
ProjectModel::ProjectModel(Project *project, QObject *parent): ProjectModel::ProjectModel(Project *project, QObject *parent):
QAbstractItemModel(parent), QAbstractItemModel(parent),
mProject(project) mProject(project)
@ -2305,6 +2331,23 @@ CustomFileIconProvider *ProjectModel::iconProvider() const
return mIconProvider; return mIconProvider;
} }
bool ProjectModel::insertRows(int row, int count, const QModelIndex &parent)
{
qDebug()<<"insert rows";
qDebug()<<rowCount(parent);
beginInsertRows(parent,row,row+count-1);
endInsertRows();
return true;
}
bool ProjectModel::removeRows(int row, int count, const QModelIndex &parent)
{
qDebug()<<"remove rows";
beginRemoveRows(parent,row,row+count-1);
endRemoveRows();
return true;
}
Project *ProjectModel::project() const Project *ProjectModel::project() const
{ {
return mProject; return mProject;
@ -2370,7 +2413,7 @@ QVariant ProjectModel::data(const QModelIndex &index, int role) const
} else if (role == Qt::DecorationRole) { } else if (role == Qt::DecorationRole) {
QIcon icon; QIcon icon;
if (p->unitIndex>=0) { if (p->unitIndex>=0) {
icon = mIconProvider->icon(mProject->units()[p->unitIndex]->fileName()); icon = mIconProvider->icon(mProject->findUnitById(p->unitIndex)->fileName());
} else { } else {
if (p == mProject->rootNode().get()) { if (p == mProject->rootNode().get()) {
QString branch; QString branch;
@ -2440,7 +2483,7 @@ bool ProjectModel::setData(const QModelIndex &index, const QVariant &value, int
int idx = node->unitIndex; int idx = node->unitIndex;
if (idx >= 0) { if (idx >= 0) {
//change unit name //change unit name
PProjectUnit unit = mProject->units()[idx]; PProjectUnit unit = mProject->findUnitById(idx);
QString newName = value.toString().trimmed(); QString newName = value.toString().trimmed();
if (newName.isEmpty()) if (newName.isEmpty())
return false; return false;
@ -2464,7 +2507,7 @@ bool ProjectModel::setData(const QModelIndex &index, const QVariant &value, int
mProject->editorList()->closeEditor(e); mProject->editorList()->closeEditor(e);
// Remove it from the current project... // Remove it from the current project...
int projindex = mProject->indexInUnits(newName); int projindex = mProject->findUnitId(newName);
if (projindex>=0) { if (projindex>=0) {
mProject->removeUnit(projindex,false); mProject->removeUnit(projindex,false);
} }
@ -2496,7 +2539,7 @@ bool ProjectModel::setData(const QModelIndex &index, const QVariant &value, int
QMessageBox::Ok); QMessageBox::Ok);
return false; return false;
} }
mProject->saveUnitAs(idx,newName); mProject->renameUnit(idx,newName);
// Add new filename to file minitor // Add new filename to file minitor
mProject->fileSystemWatcher()->addPath(newName); mProject->fileSystemWatcher()->addPath(newName);
@ -2528,9 +2571,11 @@ bool ProjectModel::setData(const QModelIndex &index, const QVariant &value, int
QModelIndex ProjectModel::getNodeIndex(ProjectModelNode *node) const QModelIndex ProjectModel::getNodeIndex(ProjectModelNode *node) const
{ {
if (!node)
return QModelIndex();
PProjectModelNode parent = node->parent.lock(); PProjectModelNode parent = node->parent.lock();
if (!parent) // root node if (!parent) // root node
return QModelIndex(); return createIndex(0,0,node);
int row = -1; int row = -1;
for (int i=0;i<parent->children.count();i++) { for (int i=0;i<parent->children.count();i++) {
const PProjectModelNode& pNode=parent->children[i]; const PProjectModelNode& pNode=parent->children[i];
@ -2648,8 +2693,8 @@ bool ProjectModel::dropMimeData(const QMimeData *data, Qt::DropAction action, in
droppedNode->parent = node; droppedNode->parent = node;
node->children.append(droppedNode); node->children.append(droppedNode);
if (droppedNode->unitIndex>=0) { if (droppedNode->unitIndex>=0) {
PProjectUnit unit = mProject->units()[droppedNode->unitIndex]; PProjectUnit unit = mProject->findUnitById(droppedNode->unitIndex);
unit->setFolder(mProject->getFolderPath(node)); unit->setFolder(mProject->getNodePath(node));
} }
QModelIndex newParentIndex = getParentIndex(droppedPointer); QModelIndex newParentIndex = getParentIndex(droppedPointer);
beginInsertRows(newParentIndex,node->children.count()-1,node->children.count()-1); beginInsertRows(newParentIndex,node->children.count()-1,node->children.count()-1);
@ -2678,7 +2723,7 @@ QMimeData *ProjectModel::mimeData(const QModelIndexList &indexes) const
stream << (qint32)((*it).row()) << (qint32)((*it).column()) << (quintptr)((*it).internalPointer()); stream << (qint32)((*it).row()) << (qint32)((*it).column()) << (quintptr)((*it).internalPointer());
ProjectModelNode* p = static_cast<ProjectModelNode*>((*it).internalPointer()); ProjectModelNode* p = static_cast<ProjectModelNode*>((*it).internalPointer());
if (p && p->unitIndex>=0) { if (p && p->unitIndex>=0) {
urls.append(QUrl::fromLocalFile(mProject->units()[p->unitIndex]->fileName())); urls.append(QUrl::fromLocalFile(mProject->findUnitById(p->unitIndex)->fileName()));
} }
} }
if (!urls.isEmpty()) if (!urls.isEmpty())

View File

@ -18,6 +18,8 @@
#define PROJECT_H #define PROJECT_H
#include <QAbstractItemModel> #include <QAbstractItemModel>
#include <QHash>
#include <QSet>
#include <QSortFilterProxyModel> #include <QSortFilterProxyModel>
#include <memory> #include <memory>
#include "projectoptions.h" #include "projectoptions.h"
@ -37,6 +39,11 @@ enum ProjectModelNodeType {
File File
}; };
struct ProjectModelItemRecord {
ProjectModelNodeType type;
QString fullPath;
};
struct ProjectModelNode; struct ProjectModelNode;
using PProjectModelNode = std::shared_ptr<ProjectModelNode>; using PProjectModelNode = std::shared_ptr<ProjectModelNode>;
struct ProjectModelNode { struct ProjectModelNode {
@ -85,6 +92,10 @@ public:
bool FileMissing() const; bool FileMissing() const;
void setFileMissing(bool newDontSave); void setFileMissing(bool newDontSave);
int id() const;
void setId(int newId);
private: private:
Project* mParent; Project* mParent;
QString mFileName; QString mFileName;
@ -99,6 +110,8 @@ private:
QByteArray mEncoding; QByteArray mEncoding;
PProjectModelNode mNode; PProjectModelNode mNode;
bool mFileMissing; bool mFileMissing;
int mId;
static int mIdGenerator;
}; };
using PProjectUnit = std::shared_ptr<ProjectUnit>; using PProjectUnit = std::shared_ptr<ProjectUnit>;
@ -129,9 +142,9 @@ public:
bool setData(const QModelIndex &index, const QVariant &value, int role) override; bool setData(const QModelIndex &index, const QVariant &value, int role) override;
QModelIndex getNodeIndex(ProjectModelNode *node) const; QModelIndex getNodeIndex(ProjectModelNode *node) const;
QModelIndex getParentIndex(ProjectModelNode * node) const;
private: private:
QModelIndex getParentIndex(ProjectModelNode * node) const;
// QAbstractItemModel interface // QAbstractItemModel interface
public: public:
@ -141,6 +154,11 @@ public:
QMimeData *mimeData(const QModelIndexList &indexes) const override; QMimeData *mimeData(const QModelIndexList &indexes) const override;
Project *project() const; Project *project() const;
CustomFileIconProvider *iconProvider() const; CustomFileIconProvider *iconProvider() const;
// QAbstractItemModel interface
public:
bool insertRows(int row, int count, const QModelIndex &parent) override;
bool removeRows(int row, int count, const QModelIndex &parent) override;
}; };
class ProjectModelSortFilterProxy : public QSortFilterProxyModel class ProjectModelSortFilterProxy : public QSortFilterProxyModel
@ -177,44 +195,51 @@ public:
bool rebuild); bool rebuild);
QString folder(); QString folder();
void buildPrivateResource(bool forceSave=false); void buildPrivateResource(bool forceSave=false);
void closeUnit(int index); void closeUnit(int id);
void doAutoOpen(); void doAutoOpen();
bool fileAlreadyExists(const QString& s); bool fileAlreadyExists(const QString& s);
QString getFolderPath(PProjectModelNode node); QString getNodePath(PProjectModelNode node);
int getUnitFromString(const QString& s); int getUnitFromString(const QString& s);
void incrementBuildNumber(); void incrementBuildNumber();
int indexInUnits(const QString& fileName) const;
int indexInUnits(const Editor* editor) const;
PProjectUnit newUnit(PProjectModelNode parentNode, PProjectUnit newUnit(PProjectModelNode parentNode,
const QString& customFileName=""); const QString& customFileName="");
Editor* openUnit(int index, bool forceOpen=true); Editor* openUnit(int index, bool forceOpen=true);
Editor* unitEditor(const PProjectUnit& unit) const; Editor* unitEditor(const PProjectUnit& unit) const;
Editor* unitEditor(const ProjectUnit* unit) const; Editor* unitEditor(const ProjectUnit* unit) const;
Editor* unitEditor(int index) const { Editor* unitEditor(int id) const {
if (index<0 || index>=mUnits.count()) PProjectUnit unit=mUnits.value(id,PProjectUnit());
if (!unit)
return nullptr; return nullptr;
return unitEditor(mUnits[index]); return unitEditor(unit);
} }
QList<PProjectUnit> unitList();
PProjectModelNode pointerToNode(ProjectModelNode * p, PProjectModelNode parent=PProjectModelNode()); PProjectModelNode pointerToNode(ProjectModelNode * p, PProjectModelNode parent=PProjectModelNode());
void rebuildNodes(); void rebuildNodes();
bool removeUnit(int index, bool doClose, bool removeFile = false); bool removeUnit(int id, bool doClose, bool removeFile = false);
bool removeFolder(PProjectModelNode node); bool removeFolder(PProjectModelNode node);
void resetParserProjectFiles(); void resetParserProjectFiles();
void saveAll(); // save [Project] and all [UnitX] void saveAll(); // save [Project] and all [UnitX]
void saveLayout(); // save all [UnitX] void saveLayout(); // save all [UnitX]
void saveOptions(); void saveOptions();
void saveUnitAs(int i, const QString& sFileName, bool syncEditor = true); // save single [UnitX] void renameUnit(int idx, const QString& sFileName);
bool saveUnits(); bool saveUnits();
PProjectUnit findUnitByFilename(const QString& filename); PProjectUnit findUnitById(int id);
PProjectUnit findUnit(const QString& filename);
PProjectUnit findUnit(const Editor* editor);
int findUnitId(const QString& fileName) const;
int findUnitId(const Editor* editor) const;
void associateEditor(Editor* editor); void associateEditor(Editor* editor);
void associateEditorToUnit(Editor* editor, PProjectUnit unit); void associateEditorToUnit(Editor* editor, PProjectUnit unit);
bool setCompileOption(const QString &key, const QString &value); bool setCompileOption(const QString &key, const QString &value);
QString getCompileOption(const QString &key) const; QString getCompileOption(const QString &key) const;
void updateFolders(); void updateFolders();
void updateNodeIndexes();
void setCompilerSet(int compilerSetIndex); void setCompilerSet(int compilerSetIndex);
bool assignTemplate(const std::shared_ptr<ProjectTemplate> aTemplate, bool useCpp); bool assignTemplate(const std::shared_ptr<ProjectTemplate> aTemplate, bool useCpp);
@ -235,8 +260,6 @@ public:
ProjectModel* model() ; ProjectModel* model() ;
const QList<PProjectUnit> &units() const;
ProjectModelType modelType() const; ProjectModelType modelType() const;
void setModelType(ProjectModelType type); void setModelType(ProjectModelType type);
@ -263,16 +286,24 @@ private:
void loadLayout(); // load all [UnitX] void loadLayout(); // load all [UnitX]
void loadUnitLayout(Editor *e, int index); // load single [UnitX] cursor positions void loadUnitLayout(Editor *e, int index); // load single [UnitX] cursor positions
PProjectModelNode makeNewFileNode(const QString& s, bool isFolder, PProjectModelNode newParent); PProjectModelNode makeNewFolderNode(
const QString& folderName,
PProjectModelNode newParent,
ProjectModelNodeType nodeType=ProjectModelNodeType::Folder,
int priority=0);
PProjectModelNode makeNewFileNode(
const QString& fileName,
int unitId,
int priority,
PProjectModelNode newParent);
PProjectModelNode makeProjectNode(); PProjectModelNode makeProjectNode();
void open(); void open();
void removeFolderRecurse(PProjectModelNode node); void removeFolderRecurse(PProjectModelNode node);
void saveUnitLayout(Editor* e, int index); // save single [UnitX] cursor positions
void updateFolderNode(PProjectModelNode node); void updateFolderNode(PProjectModelNode node);
void updateCompilerSetType(); void updateCompilerSetType();
private: private:
QList<PProjectUnit> mUnits; QHash<int,PProjectUnit> mUnits;
ProjectOptions mOptions; ProjectOptions mOptions;
QString mFilename; QString mFilename;
QString mName; QString mName;

View File

@ -47,7 +47,7 @@ void ProjectFilesWidget::doSave()
{ {
for (int i=0;i<mUnits.count();i++) { for (int i=0;i<mUnits.count();i++) {
PProjectUnit unitCopy = mUnits[i]; PProjectUnit unitCopy = mUnits[i];
PProjectUnit unit = pMainWindow->project()->units()[i]; PProjectUnit unit = pMainWindow->project()->findUnitById(unitCopy->id());
unit->setPriority(unitCopy->priority()); unit->setPriority(unitCopy->priority());
unit->setCompile(unitCopy->compile()); unit->setCompile(unitCopy->compile());
unit->setLink(unitCopy->link()); unit->setLink(unitCopy->link());
@ -70,11 +70,14 @@ PProjectUnit ProjectFilesWidget::currentUnit()
ProjectModelNode* node = static_cast<ProjectModelNode*>(index.internalPointer()); ProjectModelNode* node = static_cast<ProjectModelNode*>(index.internalPointer());
if (!node) if (!node)
return PProjectUnit(); return PProjectUnit();
int i = node->unitIndex; int idx = node->unitIndex;
if (i>=0) { if (idx>=0) {
return mUnits[i]; foreach (PProjectUnit unit, mUnits) {
} else if (unit->id() == idx)
return PProjectUnit(); return unit;
}
}
return PProjectUnit();
} }
void ProjectFilesWidget::copyUnits() void ProjectFilesWidget::copyUnits()
@ -83,8 +86,9 @@ void ProjectFilesWidget::copyUnits()
if (!project) if (!project)
return; return;
mUnits.clear(); mUnits.clear();
foreach (const PProjectUnit& unit, project->units()) { foreach (const PProjectUnit& unit, project->unitList()) {
PProjectUnit unitCopy = std::make_shared<ProjectUnit>(project.get()); PProjectUnit unitCopy = std::make_shared<ProjectUnit>(project.get());
unitCopy->setId(unit->id());
unitCopy->setPriority(unit->priority()); unitCopy->setPriority(unit->priority());
unitCopy->setCompile(unit->compile()); unitCopy->setCompile(unit->compile());
unitCopy->setLink(unit->link()); unitCopy->setLink(unit->link());

View File

@ -57,7 +57,7 @@ void ProjectGeneralWidget::doLoad()
ui->txtOutputFile->setText(project->executable()); ui->txtOutputFile->setText(project->executable());
int srcCount=0,headerCount=0,resCount=0,otherCount=0, totalCount=0; int srcCount=0,headerCount=0,resCount=0,otherCount=0, totalCount=0;
foreach (const PProjectUnit& unit, project->units()) { foreach (const PProjectUnit& unit, project->unitList()) {
switch(getFileType(unit->fileName())) { switch(getFileType(unit->fileName())) {
case FileType::CSource: case FileType::CSource:
case FileType::CppSource: case FileType::CppSource:

View File

@ -362,9 +362,9 @@ void SearchDialog::on_btnExecute_clicked()
mSearchOptions, mSearchOptions,
SearchFileScope::wholeProject SearchFileScope::wholeProject
); );
for (int i=0;i<pMainWindow->project()->units().count();i++) { foreach (PProjectUnit unit, pMainWindow->project()->unitList()) {
Editor * e = pMainWindow->project()->unitEditor(i); Editor * e = pMainWindow->project()->unitEditor(unit);
QString curFilename = pMainWindow->project()->units()[i]->fileName(); QString curFilename = unit->fileName();
if (e) { if (e) {
fileSearched++; fileSearched++;
PSearchResultTreeItem parentItem = batchFindInEditor( PSearchResultTreeItem parentItem = batchFindInEditor(