- fix: when show function tips, can't correctly calcuate the current position in the function param list
This commit is contained in:
parent
3fca3e7216
commit
02813587fd
1
NEWS.md
1
NEWS.md
|
@ -5,6 +5,7 @@ Red Panda C++ Version 0.13.3
|
||||||
- fix: If project's compiler set is not the same with the default compiler set, auto openned project's file will use wrong compiler set to do syntax check.
|
- fix: If project's compiler set is not the same with the default compiler set, auto openned project's file will use wrong compiler set to do syntax check.
|
||||||
- change: symbols that exactly match are sorted to the front in the code suggestion popup list
|
- change: symbols that exactly match are sorted to the front in the code suggestion popup list
|
||||||
- fix: symbols defind locally should be sorted to the front in the code suggestion popup list
|
- fix: symbols defind locally should be sorted to the front in the code suggestion popup list
|
||||||
|
- fix: when show function tips, can't correctly calcuate the current position in the function param list
|
||||||
|
|
||||||
Red Panda C++ Version 0.13.2
|
Red Panda C++ Version 0.13.2
|
||||||
- fix: "delete and exit" button in the environtment / folder option page doesn't work correctly
|
- fix: "delete and exit" button in the environtment / folder option page doesn't work correctly
|
||||||
|
|
|
@ -3182,152 +3182,128 @@ void Editor::updateFunctionTip()
|
||||||
pMainWindow->functionTip()->hide();
|
pMainWindow->functionTip()->hide();
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
if (!highlighter())
|
||||||
|
return;
|
||||||
|
|
||||||
|
bool isFunction = false;
|
||||||
|
auto action = finally([&isFunction]{
|
||||||
|
if (!isFunction)
|
||||||
|
pMainWindow->functionTip()->hide();
|
||||||
|
});
|
||||||
|
const int maxLines=20;
|
||||||
BufferCoord caretPos = caretXY();
|
BufferCoord caretPos = caretXY();
|
||||||
ContentsCoord curPos = fromBufferCoord(caretPos);
|
int currentLine = caretPos.Line-1;
|
||||||
ContentsCoord cursorPos = curPos;
|
int currentChar = caretPos.Char-1;
|
||||||
int nBraces = 0;
|
BufferCoord functionNamePos{-1,-1};
|
||||||
int nCommas = 0;
|
bool foundFunctionStart = false;
|
||||||
int FMaxScanLength = 500;
|
int parenthesisLevel = 0;
|
||||||
// Find out where the function ends...
|
int braceLevel = 0;
|
||||||
for (int i=0;i<FMaxScanLength;i++) {
|
int bracketLevel = 0;
|
||||||
// Stopping characters...
|
int paramsCount = 1;
|
||||||
QChar ch = *curPos;
|
int currentParamPos = 1;
|
||||||
if (ch == '\0' || ch == ';') {
|
if (currentLine>=lines()->count())
|
||||||
pMainWindow->functionTip()->hide();
|
|
||||||
return;
|
return;
|
||||||
// Opening brace, increase count
|
while (currentLine>=0) {
|
||||||
}
|
QString line = lines()->getString(currentLine);
|
||||||
QChar nextCh = *(curPos+1);
|
if (currentLine!=caretPos.Line-1)
|
||||||
if (ch == '(') {
|
currentChar = line.length();
|
||||||
nBraces++;
|
QStringList tokens;
|
||||||
// Ending brace, decrease count or success (found ending)!
|
QList<int> positions;
|
||||||
} else if (ch == ')') {
|
if (currentLine==0)
|
||||||
nBraces--;
|
highlighter()->resetState();
|
||||||
if (nBraces == -1)
|
else
|
||||||
|
highlighter()->setState(
|
||||||
|
lines()->ranges(currentLine-1));
|
||||||
|
highlighter()->setLine(line,currentLine);
|
||||||
|
while(!highlighter()->eol()) {
|
||||||
|
int start = highlighter()->getTokenPos();
|
||||||
|
QString token = highlighter()->getToken();
|
||||||
|
PSynHighlighterAttribute attr = highlighter()->getTokenAttribute();
|
||||||
|
if (start>=currentChar)
|
||||||
break;
|
break;
|
||||||
|
|
||||||
// Single line comments
|
if (attr != highlighter()->commentAttribute()
|
||||||
} else if ((ch == '/') && (nextCh == '/')) {
|
&& attr!=highlighter()->whitespaceAttribute()) {
|
||||||
// Walk up to an enter sequence
|
if (foundFunctionStart) {
|
||||||
while (ch!='\0' && ch!='\n') {
|
if (attr!=highlighter()->identifierAttribute())
|
||||||
curPos+=1;
|
return; // not a function
|
||||||
ch = *curPos;
|
functionNamePos.Line = currentLine+1;
|
||||||
}
|
functionNamePos.Char = start+1;
|
||||||
|
|
||||||
|
|
||||||
// Skip linebreak;
|
|
||||||
if (ch == '\n') {
|
|
||||||
curPos += 1;
|
|
||||||
}
|
|
||||||
} else if ((ch == '/') && (nextCh == '*')) {
|
|
||||||
|
|
||||||
// Walk up to "*/"
|
|
||||||
while (ch!='\0' && !(ch=='*' && nextCh=='/')) {
|
|
||||||
curPos += 1;
|
|
||||||
ch = *curPos;
|
|
||||||
nextCh = *(curPos+1);
|
|
||||||
}
|
|
||||||
|
|
||||||
// Step over
|
|
||||||
if (ch!='\0') {
|
|
||||||
curPos+=1;
|
|
||||||
}
|
|
||||||
} else
|
|
||||||
curPos += 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
//qDebug()<<"first pass:"<<nBraces<<" "<<curPos.line()<<":"<<curPos.ch()<<" - '"<<*curPos<<"'";
|
|
||||||
// If we couldn't find the closing brace or reached the FMaxScanLength...
|
|
||||||
if (nBraces!=-1) {
|
|
||||||
pMainWindow->functionTip()->hide();
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
//ContentsCoord FFunctionEnd = curPos;
|
|
||||||
|
|
||||||
int paramPos = 0;
|
|
||||||
bool paramPosFounded = false;
|
|
||||||
// We've stopped at the ending ), start walking backwards )*here* with nBraces = -1
|
|
||||||
for (int i=0;i<FMaxScanLength;i++) {
|
|
||||||
QChar ch = *curPos;
|
|
||||||
QChar prevCh = *(curPos-1);
|
|
||||||
if (prevCh == '*' && ch == '/' ) {
|
|
||||||
while (true) {
|
|
||||||
curPos -= 1;
|
|
||||||
ch = *(curPos);
|
|
||||||
prevCh = *(curPos-1);
|
|
||||||
if (prevCh == '\0') {
|
|
||||||
pMainWindow->functionTip()->hide();
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
if (prevCh == '/' && ch == '*' ) {
|
|
||||||
curPos -= 1;
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
tokens.append(token);
|
||||||
|
positions.append(start);
|
||||||
|
} else if (attr == highlighter()->commentAttribute()
|
||||||
|
&& currentLine == caretPos.Line-1 && start<caretPos.Char
|
||||||
|
&& start+token.length()>=caretPos.Char) {
|
||||||
|
return; // in comment, do nothing
|
||||||
}
|
}
|
||||||
} else if (ch == ')') {
|
highlighter()->next();
|
||||||
nBraces++ ;
|
|
||||||
} else if (ch == '(') {
|
|
||||||
nBraces--;
|
|
||||||
if (nBraces == -1) // found it!
|
|
||||||
break;;
|
|
||||||
} else if (ch == ',') {
|
|
||||||
if (nBraces == 0) {
|
|
||||||
if (curPos <= cursorPos && !paramPosFounded) {
|
|
||||||
paramPos = nCommas;
|
|
||||||
paramPosFounded = true;
|
|
||||||
}
|
}
|
||||||
nCommas++;
|
if (!foundFunctionStart) {
|
||||||
|
for (int i=tokens.length()-1;i>=0;i--) {
|
||||||
|
if (braceLevel>0) {
|
||||||
|
if (tokens[i]=="{") {
|
||||||
|
braceLevel--;
|
||||||
|
} else if (tokens[i]=="}") {
|
||||||
|
braceLevel++;
|
||||||
}
|
}
|
||||||
|
} else if (bracketLevel>0) {
|
||||||
|
if (tokens[i]=="[") {
|
||||||
|
braceLevel--;
|
||||||
|
} else if (tokens[i]=="]") {
|
||||||
|
braceLevel++;
|
||||||
}
|
}
|
||||||
curPos -= 1;
|
}else if (parenthesisLevel>0){
|
||||||
if (curPos.atStart())
|
if (tokens[i]==")") {
|
||||||
break;
|
parenthesisLevel++;
|
||||||
|
} else if (tokens[i]=="(") {
|
||||||
|
parenthesisLevel--;
|
||||||
}
|
}
|
||||||
if (paramPosFounded)
|
|
||||||
paramPos = nCommas - paramPos;
|
|
||||||
|
|
||||||
//qDebug()<<"second pass:"<<nBraces<<","<<nCommas<<","<<paramPos<<" "<<curPos.line()<<":"<<curPos.ch()<<" - '"<<*curPos<<"'";
|
|
||||||
// If we couldn't find the closing brace or reached the FMaxScanLength...
|
|
||||||
if (nBraces!=-1) {
|
|
||||||
pMainWindow->functionTip()->hide();
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
//ContentsCoord FFunctionStart = curPos;
|
|
||||||
|
|
||||||
// Skip blanks
|
|
||||||
while (!curPos.atStart()) {
|
|
||||||
QChar prevCh = *(curPos-1);
|
|
||||||
if (prevCh == '\t' || prevCh == ' '
|
|
||||||
|| prevCh == '\n') {
|
|
||||||
curPos-=1;
|
|
||||||
} else {
|
} else {
|
||||||
|
qDebug()<<i<<tokens[i];
|
||||||
|
if (tokens[i]=="(") {
|
||||||
|
// found start of function
|
||||||
|
foundFunctionStart = true;
|
||||||
|
if (i>0) {
|
||||||
|
functionNamePos.Line = currentLine+1;
|
||||||
|
functionNamePos.Char = positions[i-1]+1;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
} else if (tokens[i]=="[") {
|
||||||
|
//we are not in a function call
|
||||||
|
return;
|
||||||
|
} else if (tokens[i]=="{") {
|
||||||
|
//we are not in a function call
|
||||||
|
return;
|
||||||
|
} else if (tokens[i]==";") {
|
||||||
|
//we are not in a function call
|
||||||
|
return;
|
||||||
|
} else if (tokens[i]==")") {
|
||||||
|
parenthesisLevel++;
|
||||||
|
} else if (tokens[i]=="}") {
|
||||||
|
braceLevel++;
|
||||||
|
} else if (tokens[i]=="}") {
|
||||||
|
bracketLevel++;
|
||||||
|
} else if (tokens[i]==",") {
|
||||||
|
paramsCount++;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (functionNamePos.Char>=0)
|
||||||
|
break;
|
||||||
|
currentLine--;
|
||||||
|
if (caretPos.Line-currentLine>maxLines)
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
isFunction = functionNamePos.Char>=0;
|
||||||
|
currentParamPos = paramsCount-1;
|
||||||
ContentsCoord prevPos = curPos-1;
|
if (!isFunction)
|
||||||
if (prevPos.atStart()) {
|
|
||||||
pMainWindow->functionTip()->hide();
|
|
||||||
return;
|
return;
|
||||||
}
|
|
||||||
// Get the name of the function we're about to show
|
|
||||||
BufferCoord FuncStartXY = prevPos.toBufferCoord();
|
|
||||||
QString token;
|
|
||||||
PSynHighlighterAttribute HLAttr;
|
|
||||||
if (!getHighlighterAttriAtRowCol(FuncStartXY,token,HLAttr)) {
|
|
||||||
pMainWindow->functionTip()->hide();
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
if (HLAttr != highlighter()->identifierAttribute()) {
|
|
||||||
pMainWindow->functionTip()->hide();
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
BufferCoord pWordBegin, pWordEnd;
|
BufferCoord pWordBegin, pWordEnd;
|
||||||
|
|
||||||
QString s = getWordAtPosition(this, FuncStartXY, pWordBegin,pWordEnd, WordPurpose::wpInformation);
|
QString s = getWordAtPosition(this, functionNamePos, pWordBegin,pWordEnd, WordPurpose::wpInformation);
|
||||||
|
|
||||||
// qDebug()<<QString("find word at %1:%2 - '%3'")
|
// qDebug()<<QString("find word at %1:%2 - '%3'")
|
||||||
// .arg(FuncStartXY.Line)
|
// .arg(FuncStartXY.Line)
|
||||||
|
@ -3342,7 +3318,7 @@ void Editor::updateFunctionTip()
|
||||||
pMainWindow->functionTip()->clearTips();
|
pMainWindow->functionTip()->clearTips();
|
||||||
QList<PStatement> statements=mParser->getListOfFunctions(mFilename,
|
QList<PStatement> statements=mParser->getListOfFunctions(mFilename,
|
||||||
s,
|
s,
|
||||||
FuncStartXY.Line);
|
functionNamePos.Line);
|
||||||
|
|
||||||
foreach (const PStatement statement, statements) {
|
foreach (const PStatement statement, statements) {
|
||||||
pMainWindow->functionTip()->addTip(
|
pMainWindow->functionTip()->addTip(
|
||||||
|
@ -3365,9 +3341,9 @@ void Editor::updateFunctionTip()
|
||||||
pMainWindow->functionTip()->move(mapToGlobal(p));
|
pMainWindow->functionTip()->move(mapToGlobal(p));
|
||||||
|
|
||||||
pMainWindow->functionTip()->setFunctioFullName(s);
|
pMainWindow->functionTip()->setFunctioFullName(s);
|
||||||
pMainWindow->functionTip()->guessFunction(nCommas);
|
pMainWindow->functionTip()->guessFunction(paramsCount-1);
|
||||||
pMainWindow->functionTip()->setParamIndex(
|
pMainWindow->functionTip()->setParamIndex(
|
||||||
paramPos
|
currentParamPos
|
||||||
);
|
);
|
||||||
cancelHint();
|
cancelHint();
|
||||||
pMainWindow->functionTip()->show();
|
pMainWindow->functionTip()->show();
|
||||||
|
|
Loading…
Reference in New Issue