From b12ceeb6258e19d587a0b5d76fe0e9f8374a7acd Mon Sep 17 00:00:00 2001 From: Brian Fiete Date: Mon, 1 Aug 2022 10:47:17 -0400 Subject: [PATCH] Fixit for expanding auto constructor --- IDE/src/ui/SourceEditWidgetContent.bf | 5 ++ IDEHelper/Compiler/BfAst.cpp | 5 ++ IDEHelper/Compiler/BfAst.h | 3 + IDEHelper/Compiler/BfElementVisitor.cpp | 6 ++ IDEHelper/Compiler/BfElementVisitor.h | 1 + IDEHelper/Compiler/BfModule.cpp | 87 ++++++++++++++++++++++++- IDEHelper/Compiler/BfPrinter.cpp | 10 +++ IDEHelper/Compiler/BfPrinter.h | 1 + IDEHelper/Compiler/BfReducer.cpp | 7 ++ 9 files changed, 124 insertions(+), 1 deletion(-) diff --git a/IDE/src/ui/SourceEditWidgetContent.bf b/IDE/src/ui/SourceEditWidgetContent.bf index fca173e1..b977d064 100644 --- a/IDE/src/ui/SourceEditWidgetContent.bf +++ b/IDE/src/ui/SourceEditWidgetContent.bf @@ -4913,7 +4913,12 @@ namespace IDE.ui var autoComplete = new AutoComplete(mEditWidget); autoComplete.SetInfo(infoCopy); autoComplete.mAutoCompleteListWidget.mSelectIdx = fixitIdx; + + UndoBatchStart undoBatchStart = new UndoBatchStart("autocomplete"); + mData.mUndoManager.Add(undoBatchStart); autoComplete.InsertSelection(0); + mData.mUndoManager.Add(undoBatchStart.mBatchEnd); + autoComplete.Close(); } ~ diff --git a/IDEHelper/Compiler/BfAst.cpp b/IDEHelper/Compiler/BfAst.cpp index 7b850f08..8d97dc94 100644 --- a/IDEHelper/Compiler/BfAst.cpp +++ b/IDEHelper/Compiler/BfAst.cpp @@ -596,6 +596,11 @@ void BfStructuralVisitor::Visit(BfConstructorDeclaration* ctorDeclaration) Visit(ctorDeclaration->ToBase()); } +void BfStructuralVisitor::Visit(BfAutoConstructorDeclaration* ctorDeclaration) +{ + Visit(ctorDeclaration->ToBase()); +} + void BfStructuralVisitor::Visit(BfDestructorDeclaration* dtorDeclaration) { Visit(dtorDeclaration->ToBase()); diff --git a/IDEHelper/Compiler/BfAst.h b/IDEHelper/Compiler/BfAst.h index ec526882..c21d46fb 100644 --- a/IDEHelper/Compiler/BfAst.h +++ b/IDEHelper/Compiler/BfAst.h @@ -556,6 +556,7 @@ public: virtual void Visit(BfUnaryOperatorExpression* binOpExpr); virtual void Visit(BfBinaryOperatorExpression* binOpExpr); virtual void Visit(BfConstructorDeclaration* ctorDeclaration); + virtual void Visit(BfAutoConstructorDeclaration* ctorDeclaration); virtual void Visit(BfDestructorDeclaration* dtorDeclaration); virtual void Visit(BfMethodDeclaration* methodDeclaration); virtual void Visit(BfOperatorDeclaration* operatorDeclaration); @@ -3132,6 +3133,8 @@ class BfAutoConstructorDeclaration : public BfConstructorDeclaration { public: BF_AST_TYPE(BfAutoConstructorDeclaration, BfConstructorDeclaration); + + BfAstNode* mPrefix; }; BF_AST_DECL(BfAutoConstructorDeclaration, BfConstructorDeclaration); class BfDestructorDeclaration : public BfMethodDeclaration diff --git a/IDEHelper/Compiler/BfElementVisitor.cpp b/IDEHelper/Compiler/BfElementVisitor.cpp index edcf2070..aaa007d8 100644 --- a/IDEHelper/Compiler/BfElementVisitor.cpp +++ b/IDEHelper/Compiler/BfElementVisitor.cpp @@ -1038,6 +1038,12 @@ void BfElementVisitor::Visit(BfConstructorDeclaration* ctorDeclaration) VisitChild(ctorDeclaration->mInitializer); } +void BfElementVisitor::Visit(BfAutoConstructorDeclaration* ctorDeclaration) +{ + VisitChild(ctorDeclaration->mPrefix); + Visit(ctorDeclaration->ToBase()); +} + void BfElementVisitor::Visit(BfDestructorDeclaration* dtorDeclaration) { Visit(dtorDeclaration->ToBase()); diff --git a/IDEHelper/Compiler/BfElementVisitor.h b/IDEHelper/Compiler/BfElementVisitor.h index e863fd8b..dc8d1115 100644 --- a/IDEHelper/Compiler/BfElementVisitor.h +++ b/IDEHelper/Compiler/BfElementVisitor.h @@ -119,6 +119,7 @@ public: virtual void Visit(BfUnaryOperatorExpression* binOpExpr); virtual void Visit(BfBinaryOperatorExpression* binOpExpr); virtual void Visit(BfConstructorDeclaration* ctorDeclaration); + virtual void Visit(BfAutoConstructorDeclaration* ctorDeclaration); virtual void Visit(BfDestructorDeclaration* dtorDeclaration); virtual void Visit(BfMethodDeclaration* methodDeclaration); virtual void Visit(BfOperatorDeclaration* operatorDeclaration); diff --git a/IDEHelper/Compiler/BfModule.cpp b/IDEHelper/Compiler/BfModule.cpp index f6c085fd..000a7c97 100644 --- a/IDEHelper/Compiler/BfModule.cpp +++ b/IDEHelper/Compiler/BfModule.cpp @@ -18263,6 +18263,7 @@ void BfModule::EmitCtorBody(bool& skipBody) } } + auto autoComplete = mCompiler->GetAutoComplete(); if (targetType != NULL) { BfAstNode* refNode = methodDeclaration; @@ -18271,7 +18272,6 @@ void BfModule::EmitCtorBody(bool& skipBody) BfAutoParentNodeEntry autoParentNodeEntry(this, refNode); - auto autoComplete = mCompiler->GetAutoComplete(); auto wasCapturingMethodInfo = (autoComplete != NULL) && (autoComplete->mIsCapturingMethodMatchInfo); if ((autoComplete != NULL) && (ctorDeclaration != NULL) && (ctorInvocation != NULL)) { @@ -18317,6 +18317,91 @@ void BfModule::EmitCtorBody(bool& skipBody) autoComplete->mIsCapturingMethodMatchInfo = false; } } + + auto autoCtorDecl = BfNodeDynCast(methodDeclaration); + if ((autoComplete != NULL) && (autoComplete->CheckFixit(methodDeclaration)) && (methodDeclaration != NULL) && (autoCtorDecl != NULL)) + { + auto typeDecl = methodDef->mDeclaringType->mTypeDeclaration; + BfParserData* parser = typeDecl->GetSourceData()->ToParserData(); + if (parser != NULL) + { + String fixitStr = "Expand auto constructor\t"; + int insertPos = typeDecl->mSrcStart; + + bool needsBlock = false; + + if (auto defBlock = BfNodeDynCast(typeDecl->mDefineNode)) + { + insertPos = defBlock->mOpenBrace->mSrcStart + 1; + } + else if (auto tokenNode = BfNodeDynCast(typeDecl->mDefineNode)) + { + insertPos = tokenNode->mSrcStart; + fixitStr += StrFormat("delete|%s-%d|\x01", + autoComplete->FixitGetLocation(parser, tokenNode->mSrcStart).c_str(), tokenNode->mSrcEnd - tokenNode->mSrcStart); + needsBlock = true; + } + + int srcStart = methodDeclaration->mSrcStart; + if ((autoCtorDecl->mPrefix == NULL) && (typeDecl->mColonToken != NULL)) + srcStart = typeDecl->mColonToken->mSrcStart; + + while ((srcStart > 0) && (::isspace((uint8)parser->mSrc[srcStart - 1]))) + srcStart--; + + fixitStr += StrFormat("expand|%s|%d|", + parser->mFileName.c_str(), insertPos); + + if (needsBlock) + fixitStr += "\t"; + else + fixitStr += "\f"; + + for (int paramIdx = 0; paramIdx < autoCtorDecl->mParams.mSize; paramIdx++) + { + String paramStr = autoCtorDecl->mParams[paramIdx]->ToString(); + paramStr.Replace('\n', '\r'); + + fixitStr += "public "; + fixitStr += paramStr; + fixitStr += ";\r"; + } + + fixitStr += "\rpublic this("; + for (int paramIdx = 0; paramIdx < autoCtorDecl->mParams.mSize; paramIdx++) + { + if (paramIdx > 0) + fixitStr += ", "; + String paramStr = autoCtorDecl->mParams[paramIdx]->ToString(); + paramStr.Replace('\n', '\r'); + fixitStr += paramStr; + } + fixitStr += ")\t"; + for (int paramIdx = 0; paramIdx < autoCtorDecl->mParams.mSize; paramIdx++) + { + if (paramIdx > 0) + fixitStr += "\r"; + auto nameNode = autoCtorDecl->mParams[paramIdx]->mNameNode; + if (nameNode == NULL) + continue; + String nameStr = nameNode->ToString(); + fixitStr += "this."; + fixitStr += nameStr; + fixitStr += " = "; + fixitStr += nameStr; + fixitStr += ";"; + } + fixitStr += "\b"; + + if (needsBlock) + fixitStr += "\b"; + + fixitStr += StrFormat("\x01""delete|%s-%d|", + autoComplete->FixitGetLocation(parser, srcStart).c_str(), autoCtorDecl->mSrcEnd - srcStart); + + mCompiler->mResolvePassData->mAutoComplete->AddEntry(AutoCompleteEntry("fixit", fixitStr.c_str())); + } + } } void BfModule::EmitEnumToStringBody() diff --git a/IDEHelper/Compiler/BfPrinter.cpp b/IDEHelper/Compiler/BfPrinter.cpp index 8eb3590b..0e8a36c9 100644 --- a/IDEHelper/Compiler/BfPrinter.cpp +++ b/IDEHelper/Compiler/BfPrinter.cpp @@ -2493,6 +2493,16 @@ void BfPrinter::Visit(BfConstructorDeclaration* ctorDeclaration) FlushVisitChild(); } +void BfPrinter::Visit(BfAutoConstructorDeclaration* ctorDeclaration) +{ + if (ctorDeclaration->mPrefix != NULL) + { + VisitChild(ctorDeclaration->mPrefix); + ExpectSpace(); + } + Visit(ctorDeclaration->ToBase()); +} + void BfPrinter::Visit(BfDestructorDeclaration* dtorDeclaration) { //Visit((BfAstNode*)dtorDeclaration); diff --git a/IDEHelper/Compiler/BfPrinter.h b/IDEHelper/Compiler/BfPrinter.h index 766ceb60..e0a6dcd8 100644 --- a/IDEHelper/Compiler/BfPrinter.h +++ b/IDEHelper/Compiler/BfPrinter.h @@ -218,6 +218,7 @@ public: virtual void Visit(BfUnaryOperatorExpression* binOpExpr) override; virtual void Visit(BfBinaryOperatorExpression* binOpExpr) override; virtual void Visit(BfConstructorDeclaration* ctorDeclaration) override; + virtual void Visit(BfAutoConstructorDeclaration* ctorDeclaration) override; virtual void Visit(BfDestructorDeclaration* dtorDeclaration) override; virtual void Visit(BfMethodDeclaration* methodDeclaration) override; virtual void Visit(BfOperatorDeclaration* opreratorDeclaration) override; diff --git a/IDEHelper/Compiler/BfReducer.cpp b/IDEHelper/Compiler/BfReducer.cpp index 1eb74d63..f73343f2 100644 --- a/IDEHelper/Compiler/BfReducer.cpp +++ b/IDEHelper/Compiler/BfReducer.cpp @@ -8960,6 +8960,13 @@ BfAstNode* BfReducer::CreateTopLevelObject(BfTokenNode* tokenNode, BfAttributeDi MEMBER_SET(ctorDecl, mThisToken, tokenNode); ParseMethod(ctorDecl, ¶ms, &commas); + if (!baseClassCommas.IsEmpty()) + { + ctorDecl->mPrefix = baseClassCommas.back(); + baseClassCommas.pop_back(); + ctorDecl->mSrcStart = ctorDecl->mPrefix->mSrcStart; + } + if (typeDeclaration->mAutoCtor == NULL) { MEMBER_SET(typeDeclaration, mAutoCtor, ctorDecl);