diff options
Diffstat (limited to 'src')
-rw-r--r-- | src/Editor.cxx | 53 | ||||
-rw-r--r-- | src/Editor.h | 4 | ||||
-rw-r--r-- | src/PositionCache.cxx | 1 | ||||
-rw-r--r-- | src/ScintillaBase.cxx | 1 |
4 files changed, 51 insertions, 8 deletions
diff --git a/src/Editor.cxx b/src/Editor.cxx index ad0ca635b..4bdbecda8 100644 --- a/src/Editor.cxx +++ b/src/Editor.cxx @@ -4536,14 +4536,36 @@ void Editor::PageMove(int direction, Selection::selTypes selt, bool stuttered) { } } -void Editor::ChangeCaseOfSelection(bool makeUpperCase) { +void Editor::ChangeCaseOfSelection(int caseMapping) { UndoGroup ug(pdoc); for (size_t r=0; r<sel.Count(); r++) { SelectionRange current = sel.Range(r); - pdoc->ChangeCase(Range(current.Start().Position(), current.End().Position()), - makeUpperCase); - // Automatic movement cuts off last character so reset to exactly the same as it was. - sel.Range(r) = current; + SelectionRange currentNoVS = current; + currentNoVS.ClearVirtualSpace(); + char *text = CopyRange(currentNoVS.Start().Position(), currentNoVS.End().Position()); + size_t rangeBytes = currentNoVS.Length(); + if (rangeBytes > 0) { + std::string sText(text, rangeBytes); + + std::string sMapped = CaseMapString(sText, caseMapping); + + if (sMapped != sText) { + size_t firstDifference = 0; + while (sMapped[firstDifference] == sText[firstDifference]) + firstDifference++; + size_t lastDifference = sMapped.size() - 1; + while (sMapped[lastDifference] == sText[lastDifference]) + lastDifference--; + size_t endSame = sMapped.size() - 1 - lastDifference; + pdoc->DeleteChars(currentNoVS.Start().Position() + firstDifference, + rangeBytes - firstDifference - endSame); + pdoc->InsertString(currentNoVS.Start().Position() + firstDifference, + sMapped.c_str() + firstDifference, lastDifference - firstDifference + 1); + // Automatic movement changes selection so reset to exactly the same as it was. + sel.Range(r) = current; + } + } + delete []text; } } @@ -5137,10 +5159,10 @@ int Editor::KeyCommand(unsigned int iMessage) { Duplicate(false); break; case SCI_LOWERCASE: - ChangeCaseOfSelection(false); + ChangeCaseOfSelection(cmLower); break; case SCI_UPPERCASE: - ChangeCaseOfSelection(true); + ChangeCaseOfSelection(cmUpper); break; case SCI_WORDPARTLEFT: MovePositionTo(MovePositionSoVisible(pdoc->WordPartLeft(sel.MainCaret()), -1)); @@ -5366,6 +5388,23 @@ long Editor::SearchText( return pos; } +std::string Editor::CaseMapString(const std::string &s, int caseMapping) { + std::string ret(s); + for (size_t i=0; i<ret.size(); i++) { + switch (caseMapping) { + case cmUpper: + if (ret[i] >= 'a' && ret[i] <= 'z') + ret[i] = static_cast<char>(ret[i] - 'a' + 'A'); + break; + case cmLower: + if (ret[i] >= 'A' && ret[i] <= 'Z') + ret[i] = static_cast<char>(ret[i] - 'A' + 'a'); + break; + } + } + return ret; +} + /** * Search for text in the target range of the document. * @return The position of the found text, -1 if not found. diff --git a/src/Editor.h b/src/Editor.h index 6e6c25f0f..053b10a9e 100644 --- a/src/Editor.h +++ b/src/Editor.h @@ -405,7 +405,9 @@ protected: // ScintillaBase subclass needs access to much of Editor void NotifyMacroRecord(unsigned int iMessage, uptr_t wParam, sptr_t lParam); void PageMove(int direction, Selection::selTypes sel=Selection::noSel, bool stuttered = false); - void ChangeCaseOfSelection(bool makeUpperCase); + enum { cmSame, cmUpper, cmLower } caseMap; + virtual std::string CaseMapString(const std::string &s, int caseMapping); + void ChangeCaseOfSelection(int caseMapping); void LineTranspose(); void Duplicate(bool forLine); virtual void CancelModes(); diff --git a/src/PositionCache.cxx b/src/PositionCache.cxx index 6b48f1859..d27205b5f 100644 --- a/src/PositionCache.cxx +++ b/src/PositionCache.cxx @@ -10,6 +10,7 @@ #include <stdio.h> #include <ctype.h> +#include <string> #include <vector> #include "Platform.h" diff --git a/src/ScintillaBase.cxx b/src/ScintillaBase.cxx index 714e989e7..cecfc0952 100644 --- a/src/ScintillaBase.cxx +++ b/src/ScintillaBase.cxx @@ -10,6 +10,7 @@ #include <stdio.h> #include <ctype.h> +#include <string> #include <vector> #include "Platform.h" |