aboutsummaryrefslogtreecommitdiffhomepage
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/Editor.cxx53
-rw-r--r--src/Editor.h4
-rw-r--r--src/PositionCache.cxx1
-rw-r--r--src/ScintillaBase.cxx1
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"