Some wxStyledTextCtrl bugfixes

Merged in new Scintilla sources

Added new methods to wxStyledTextCtrl to match new Scintilla capabilities.


git-svn-id: https://svn.wxwidgets.org/svn/wx/wxWidgets/branches/WX_2_2_BRANCH@7302 c3d73ce0-8a6f-49c7-b76d-6d57e0e08775
This commit is contained in:
Robin Dunn
2000-04-28 06:37:53 +00:00
parent 21aff0fe10
commit efecda0bf7
94 changed files with 2690 additions and 1056 deletions

View File

@@ -130,7 +130,9 @@ enum {
wxSTC_CMD_LINEDELETE,
wxSTC_CMD_LINETRANSPOSE,
wxSTC_CMD_LOWERCASE,
wxSTC_CMD_UPPERCASE
wxSTC_CMD_UPPERCASE,
wxSTC_CMD_LINESCROLLDOWN,
wxSTC_CMD_LINESCROLLUP
};
@@ -253,7 +255,11 @@ public:
int GetLineStartPos(int line);
int GetLineLengthAtPos(int pos);
int GetLineLength(int line);
wxString GetCurrentLineText();
#ifdef SWIG
wxString GetCurrentLineText(int* OUTPUT);
#else
wxString GetCurrentLineText(int* linePos);
#endif
int GetCurrentLine();
int PositionFromPoint(wxPoint pt);
int LineFromPoint(wxPoint pt);
@@ -274,7 +280,10 @@ public:
void EnsureCaretVisible();
void SetCaretPolicy(int policy, int slop=0);
int GetSelectionType();
int GetLinesOnScreen();
bool IsSelectionRectangle();
void SetUseHorizontalScrollBar(bool use);
bool GetUseHorizontalScrollBar();
// Searching
@@ -303,6 +312,8 @@ public:
void StartStyling(int pos, int mask);
void SetStyleFor(int length, int style);
void SetStyleBytes(int length, char* styleBytes);
void SetLineState(int line, int value);
int GetLineState(int line);
// Style Definition
@@ -348,8 +359,15 @@ public:
// Other settings
void SetBufferedDraw(bool isBuffered);
void SetTabWidth(int numChars);
void SetIndent(int numChars);
void SetUseTabs(bool usetabs);
void SetLineIndentation(int line, int indentation);
int GetLineIndentation(int line);
int GetLineIndentationPos(int line);
void SetWordChars(const wxString& wordChars);
void SetUsePop(bool usepopup);
// Brace highlighting
void BraceHighlight(int pos1, int pos2);
@@ -387,7 +405,9 @@ public:
int AutoCompPosAtStart();
void AutoCompComplete();
void AutoCompStopChars(const wxString& stopChars);
void AutoCompSetSeparator(char separator);
char AutoCompGetSeparator();
void AutoCompSelect(const wxString& stringtoselect);
// Call tips
void CallTipShow(int pos, const wxString& text);

View File

@@ -23,16 +23,7 @@ HEADER_SUBDIR=stc
HEADERS=stc.h
OBJECTS=PlatWX.o ScintillaWX.o stc.o \
Accessor.o \
AutoComplete.o \
CallTip.o \
CellBuffer.o \
ContractionState.o \
Document.o \
Editor.o \
Indicator.o \
KeyMap.o \
KeyWords.o \
DocumentAccessor.o \
LexCPP.o \
LexHTML.o \
LexOthers.o \
@@ -40,11 +31,23 @@ OBJECTS=PlatWX.o ScintillaWX.o stc.o \
LexPython.o \
LexSQL.o \
LexVB.o \
LineMarker.o \
UniConversion.o \
WindowAccessor.o \
AutoComplete.o \
CallTip.o \
CellBuffer.o \
ContractionState.o \
Document.o \
Editor.o \
Indicator.o \
KeyMap.o \
KeyWords.o \
LineMarker.o \
PropSet.o \
ScintillaBase.o \
ScintillaBase.o \
Style.o \
ViewStyle.o
ViewStyle.o \
APPEXTRADEFS=-D__WX__ -DSCI_LEXER -I$(scintilla_dir)/src -I$(scintilla_dir)/include -I$(top_srcdir)/contrib/include

View File

@@ -196,6 +196,12 @@ int Surface::LogPixelsY() {
return hdc->GetPPI().y;
}
int Surface::DeviceHeightFont(int points) {
return points * LogPixelsY() / 72;
}
void Surface::MoveTo(int x_, int y_) {
x = x_;
y = y_;

View File

@@ -195,9 +195,8 @@ void ScintillaWX::NotifyParent(SCNotification scn) {
void ScintillaWX::Copy() {
if (currentPos != anchor) {
char* text = CopySelectionRange();
textDO.SetText(text);
wxTheClipboard->Open();
wxTheClipboard->SetData(&textDO);
wxTheClipboard->SetData(new wxTextDataObject(text));
wxTheClipboard->Close();
}
}

View File

@@ -139,7 +139,6 @@ private:
bool capturedMouse;
wxStyledTextCtrl* stc;
wxTextDataObject textDO;
wxSTCDropTarget* dropTarget;
wxDragResult dragResult;
};

View File

@@ -21,21 +21,17 @@ STCEXTRACPPFLAGS=-D__WX__ -DSCI_LEXER -I$(SCINTILLA)/include -I$(S)
LIBTARGET=$(WXDIR)\contrib\lib\stc.lib
OBJECTS = \
Accessor.obj \
Accessor.obj \
AutoComplete.obj \
CallTip.obj \
CellBuffer.obj \
ContractionState.obj\
Document.obj \
CallTip.obj \
CellBuffer.obj \
ContractionState.obj \
Document.obj \
DocumentAccessor.obj \
Editor.obj \
Indicator.obj \
Indicator.obj \
KeyMap.obj \
KeyWords.obj \
LineMarker.obj \
PropSet.obj \
ScintillaBase.obj \
Style.obj \
ViewStyle.obj \
KeyWords.obj \
LexCPP.obj \
LexHTML.obj \
LexOthers.obj \
@@ -43,10 +39,18 @@ OBJECTS = \
LexPython.obj \
LexSQL.obj \
LexVB.obj \
LineMarker.obj \
PropSet.obj \
ScintillaBase.obj \
Style.obj \
UniConversion.obj \
ViewStyle.obj \
WindowAccessor.obj \
\
PlatWX.obj \
ScintillaWX.obj \
stc.obj \
ScintillaWX.obj \
stc.obj \
!include $(WXDIR)\src\makelib.b32

View File

@@ -32,6 +32,9 @@ OBJECTS = \
$(S)/LexPython.$(OBJSUFF) \
$(S)/LexSQL.$(OBJSUFF) \
$(S)/LexVB.$(OBJSUFF) \
$(S)/DocumentAccessor.$(OBJSUFF)\
$(S)/UniConversion.$(OBJSUFF) \
$(S)/WindowAccessor.$(OBJSUFF) \
PlatWX.$(OBJSUFF) \
ScintillaWX.$(OBJSUFF) \
stc.$(OBJSUFF)

View File

@@ -15,21 +15,16 @@ NOPCH=1
!include $(WXDIR)\src\makevc.env
OBJECTS = \
$(D)\Accessor.obj \
$(D)\AutoComplete.obj \
$(D)\CallTip.obj \
$(D)\CellBuffer.obj \
$(D)\ContractionState.obj\
$(D)\Document.obj \
$(D)\DocumentAccessor.obj\
$(D)\Editor.obj \
$(D)\Indicator.obj \
$(D)\KeyMap.obj \
$(D)\KeyWords.obj \
$(D)\LineMarker.obj \
$(D)\PropSet.obj \
$(D)\ScintillaBase.obj \
$(D)\Style.obj \
$(D)\ViewStyle.obj \
$(D)\LexCPP.obj \
$(D)\LexHTML.obj \
$(D)\LexOthers.obj \
@@ -37,6 +32,13 @@ OBJECTS = \
$(D)\LexPython.obj \
$(D)\LexSQL.obj \
$(D)\LexVB.obj \
$(D)\LineMarker.obj \
$(D)\PropSet.obj \
$(D)\ScintillaBase.obj \
$(D)\Style.obj \
$(D)\UniConversion.obj \
$(D)\ViewStyle.obj \
$(D)\WindowAccessor.obj \
\
$(D)\PlatWX.obj \
$(D)\ScintillaWX.obj \

View File

@@ -5,29 +5,28 @@
enum { wsSpace = 1, wsTab = 2, wsSpaceTab = 4, wsInconsistent=8};
class Accessor;
typedef bool (*PFNIsCommentLeader)(Accessor &styler, int pos, int len);
// Interface to data in a Scintilla
class Accessor {
protected:
// bufferSize is a trade off between time taken to copy the characters and SendMessage overhead
enum {extremePosition=0x7FFFFFFF};
// bufferSize is a trade off between time taken to copy the characters and retrieval overhead
// slopSize positions the buffer before the desired position in case there is some backtracking
enum {bufferSize=4000, slopSize=bufferSize/8};
char buf[bufferSize+1];
WindowID id;
PropSet &props;
int startPos;
int endPos;
int lenDoc;
int offset; // Optional but including an offset makes GCC generate better code
int codePage;
bool InternalIsLeadByte(char ch);
void Fill(int position);
virtual bool InternalIsLeadByte(char ch)=0;
virtual void Fill(int position)=0;
public:
Accessor(WindowID id_, PropSet &props_, int offset_=0) :
id(id_), props(props_), startPos(0x7FFFFFFF), endPos(0),
lenDoc(-1), offset(offset_), codePage(0) {
}
void SetCodePage(int codePage_) { codePage = codePage_; }
Accessor() : startPos(extremePosition), endPos(0), codePage(0) {}
virtual ~Accessor() {}
char operator[](int position) {
position += offset;
if (position < startPos || position >= endPos) {
Fill(position);
}
@@ -35,7 +34,6 @@ public:
}
char SafeGetCharAt(int position, char chDefault=' ') {
// Safe version of operator[], returning a defined value for invalid position
position += offset;
if (position < startPos || position >= endPos) {
Fill(position);
if (position < startPos || position >= endPos) {
@@ -48,41 +46,25 @@ public:
bool IsLeadByte(char ch) {
return codePage && InternalIsLeadByte(ch);
}
char StyleAt(int position);
int GetLine(int position);
int LineStart(int line);
int LevelAt(int line);
int Length();
void Flush() {
startPos = 0x7FFFFFFF;
lenDoc = -1;
}
int GetLineState(int line);
int SetLineState(int line, int state);
PropSet &GetPropSet() { return props; }
};
class StylingContext;
typedef bool (*PFNIsCommentLeader)(StylingContext &styler, int pos, int len);
class StylingContext : public Accessor {
char styleBuf[bufferSize];
int validLen;
char chFlags;
char chWhile;
unsigned int startSeg;
public:
StylingContext(WindowID id_, PropSet &props_, int offset_=0) :
Accessor(id_,props_,offset_), validLen(0), chFlags(0) {}
void StartAt(unsigned int start, char chMask=31);
void SetFlags(char chFlags_, char chWhile_) {chFlags = chFlags_; chWhile = chWhile_; };
unsigned int GetStartSegment() { return startSeg; }
void StartSegment(unsigned int pos);
void ColourTo(unsigned int pos, int chAttr);
int GetLine(int position);
void SetLevel(int line, int level);
void Flush();
int IndentAmount(int line, int *flags, PFNIsCommentLeader pfnIsCommentLeader = 0);
void SetCodePage(int codePage_) { codePage = codePage_; }
virtual char StyleAt(int position)=0;
virtual int GetLine(int position)=0;
virtual int LineStart(int line)=0;
virtual int LevelAt(int line)=0;
virtual int Length()=0;
virtual void Flush()=0;
virtual int GetLineState(int line)=0;
virtual int SetLineState(int line, int state)=0;
virtual int GetPropertyInt(const char *key, int defaultValue=0)=0;
// Style setting
virtual void StartAt(unsigned int start, char chMask=31)=0;
virtual void SetFlags(char chFlags_, char chWhile_)=0;
virtual unsigned int GetStartSegment()=0;
virtual void StartSegment(unsigned int pos)=0;
virtual void ColourTo(unsigned int pos, int chAttr)=0;
virtual void SetLevel(int line, int level)=0;
virtual int IndentAmount(int line, int *flags, PFNIsCommentLeader pfnIsCommentLeader = 0)=0;
};

View File

@@ -4,7 +4,7 @@
// The License.txt file describes the conditions under which this software may be distributed.
typedef void (*LexerFunction)(unsigned int startPos, int lengthDoc, int initStyle,
WordList *keywordlists[], StylingContext &styler);
WordList *keywordlists[], Accessor &styler);
class LexerModule {
static LexerModule *base;
@@ -14,7 +14,7 @@ class LexerModule {
public:
LexerModule(int language_, LexerFunction fn_);
static void Colourise(unsigned int startPos, int lengthDoc, int initStyle,
int language, WordList *keywordlists[], StylingContext &styler);
int language, WordList *keywordlists[], Accessor &styler);
};
inline bool iswordchar(char ch) {

View File

@@ -45,6 +45,7 @@
#pragma warning(disable: 4800 4244 4309)
#endif
#include <windows.h>
#include <commctrl.h>
#include <richedit.h>
#endif
@@ -221,6 +222,7 @@ public:
// A surface abstracts a place to draw
class Surface {
private:
bool unicodeMode;
#if PLAT_GTK
GdkDrawable *drawable;
GdkGC *gc;
@@ -268,6 +270,7 @@ public:
bool Initialised();
void PenColour(Colour fore);
int LogPixelsY();
int DeviceHeightFont(int points);
void MoveTo(int x_, int y_);
void LineTo(int x_, int y_);
void Polygon(Point *pts, int npts, Colour fore, Colour back);
@@ -293,6 +296,10 @@ public:
int SetPalette(Palette *pal, bool inBackGround);
void SetClip(PRectangle rc);
void FlushCachedState();
void SetUnicodeMode(bool unicodeMode_) {
unicodeMode=unicodeMode_;
}
};
// Class to hide the details of window manipulation
@@ -303,6 +310,7 @@ protected:
WindowID id;
public:
Window() : id(0) {}
Window(const Window &source) : id(source.id) {}
virtual ~Window();
Window &operator=(WindowID id_) {
id = id_;

View File

@@ -75,7 +75,7 @@ public:
else
return 0;
}
char operator[](int i) {
char operator[](int i) const {
if (s)
return s[i];
else
@@ -95,7 +95,7 @@ public:
}
return *this;
}
int value() {
int value() const {
if (s)
return atoi(s);
else
@@ -168,7 +168,7 @@ public:
WordList(bool onlyLineEnds_ = false) :
words(0), list(0), len(0), onlyLineEnds(onlyLineEnds_) {}
~WordList() { Clear(); }
operator bool() { return list; }
operator bool() { return list ? true : false; }
const char *operator[](int ind) { return words[ind]; }
void Clear();
void Set(const char *s);

View File

@@ -21,6 +21,7 @@
#define SCLEX_ERRORLIST 10
#define SCLEX_MAKEFILE 11
#define SCLEX_BATCH 12
#define SCLEX_XCODE 13
// Lexical states for SCLEX_PYTHON
#define SCE_P_DEFAULT 0

View File

@@ -107,6 +107,9 @@ extern "C" {
#define SCI_STARTSTYLING SCI_START + 32
#define SCI_SETSTYLING SCI_START + 33
// This is the same value as CP_UTF8 in Windows
#define SC_CP_UTF8 65001
#define SCI_SETBUFFEREDDRAW SCI_START + 35
#define SCI_SETTABWIDTH SCI_START + 36
#define SCI_SETCODEPAGE SCI_START + 37
@@ -213,6 +216,21 @@ extern "C" {
#define SCI_AUTOCPOSSTART SCI_START + 103
#define SCI_AUTOCCOMPLETE SCI_START + 104
#define SCI_AUTOCSTOPS SCI_START + 105
#define SCI_AUTOCSETSEPARATOR SCI_START + 106
#define SCI_AUTOCGETSEPARATOR SCI_START + 107
#define SCI_AUTOCSELECT SCI_START + 108
#define SCI_GETTABWIDTH SCI_START + 121
#define SCI_SETINDENT SCI_START + 122
#define SCI_GETINDENT SCI_START + 123
#define SCI_SETUSETABS SCI_START + 124
#define SCI_GETUSETABS SCI_START + 125
#define SCI_SETLINEINDENTATION SCI_START + 126
#define SCI_GETLINEINDENTATION SCI_START + 127
#define SCI_GETLINEINDENTPOSITION SCI_START + 128
#define SCI_SETHSCROLLBAR SCI_START + 130
#define SCI_GETHSCROLLBAR SCI_START + 131
#define SCI_CALLTIPSHOW SCI_START + 200
#define SCI_CALLTIPCANCEL SCI_START + 201
@@ -284,6 +302,8 @@ extern "C" {
#define SCI_LINETRANSPOSE SCI_START + 339
#define SCI_LOWERCASE SCI_START + 340
#define SCI_UPPERCASE SCI_START + 341
#define SCI_LINESCROLLDOWN SCI_START + 342
#define SCI_LINESCROLLUP SCI_START + 343
#define SCI_LINELENGTH SCI_START + 350
#define SCI_BRACEHIGHLIGHT SCI_START + 351
@@ -318,6 +338,7 @@ extern "C" {
#define SCI_SETCARETPOLICY SCI_START + 369
#define SCI_LINESONSCREEN SCI_START + 370
#define SCI_USEPOPUP SCI_START + 371
#define SCI_SELECTIONISRECTANGLE SCI_START + 372
// GTK+ Specific
#define SCI_GRABFOCUS SCI_START + 400
@@ -350,8 +371,10 @@ typedef void (tMacroRecorder)(UINT iMessage, WPARAM wParam, LPARAM lParam,
#define SC_PERFORMED_REDO 0x40
#define SC_LASTSTEPINUNDOREDO 0x100
#define SC_MOD_CHANGEMARKER 0x200
#define SC_MOD_BEFOREINSERT 0x400
#define SC_MOD_BEFOREDELETE 0x800
#define SC_MODEVENTMASKALL 0x377
#define SC_MODEVENTMASKALL 0xF77
struct SCNotification {
NMHDR nmhdr;

View File

@@ -0,0 +1,47 @@
// WindowAccessor.h - implementation of BufferAccess and StylingAccess on a Scintilla rapid easy access to contents of a Scintilla
// Copyright 1998-2000 by Neil Hodgson <neilh@scintilla.org>
// The License.txt file describes the conditions under which this software may be distributed.
class WindowAccessor : public Accessor {
// Private so WindowAccessor objects can not be copied
WindowAccessor(const WindowAccessor &source) : Accessor(), props(source.props) {}
WindowAccessor &operator=(const WindowAccessor &) { return *this; }
protected:
WindowID id;
PropSet &props;
int lenDoc;
char styleBuf[bufferSize];
int validLen;
char chFlags;
char chWhile;
unsigned int startSeg;
bool InternalIsLeadByte(char ch);
void Fill(int position);
public:
WindowAccessor(WindowID id_, PropSet &props_) :
Accessor(), id(id_), props(props_),
lenDoc(-1), validLen(0), chFlags(0) {
}
~WindowAccessor();
char StyleAt(int position);
int GetLine(int position);
int LineStart(int line);
int LevelAt(int line);
int Length();
void Flush();
int GetLineState(int line);
int SetLineState(int line, int state);
int GetPropertyInt(const char *key, int defaultValue=0) {
return props.GetInt(key, defaultValue);
}
void StartAt(unsigned int start, char chMask=31);
void SetFlags(char chFlags_, char chWhile_) {chFlags = chFlags_; chWhile = chWhile_; };
unsigned int GetStartSegment() { return startSeg; }
void StartSegment(unsigned int pos);
void ColourTo(unsigned int pos, int chAttr);
void SetLevel(int line, int level);
int IndentAmount(int line, int *flags, PFNIsCommentLeader pfnIsCommentLeader = 0);
};

View File

@@ -15,6 +15,7 @@ AutoComplete::AutoComplete() {
active = false;
posStart = 0;
strcpy(stopChars, "");
separator = ' ';
}
AutoComplete::~AutoComplete() {
@@ -44,6 +45,14 @@ bool AutoComplete::IsStopChar(char ch) {
return ch && strchr(stopChars, ch);
}
void AutoComplete::SetSeparator(char separator_) {
separator = separator_;
}
char AutoComplete::GetSeparator() {
return separator;
}
int AutoComplete::SetList(const char *list) {
int maxStrLen = 12;
lb.Clear();
@@ -53,7 +62,7 @@ int AutoComplete::SetList(const char *list) {
char *startword = words;
int i = 0;
for (; words && words[i]; i++) {
if (words[i] == ' ') {
if (words[i] == separator) {
words[i] = '\0';
lb.Append(startword);
maxStrLen = Platform::Maximum(maxStrLen, strlen(startword));

View File

@@ -9,6 +9,7 @@
class AutoComplete {
bool active;
char stopChars[256];
char separator;
public:
ListBox lb;
int posStart;
@@ -27,7 +28,11 @@ public:
void SetStopChars(const char *stopChars_);
bool IsStopChar(char ch);
// The list string contains a sequence of words separated by spaces
// The separator character is used when interpreting the list in SetList
void SetSeparator(char separator_);
char GetSeparator();
// The list string contains a sequence of words separated by the separator character
int SetList(const char *list);
void Show();

View File

@@ -6,13 +6,14 @@
#ifndef CALLTIP_H
#define CALLTIP_H
const char callClassName[] = "CallTip";
class CallTip {
int startHighlight;
int endHighlight;
char *val;
Font font;
// Private so CallTip objects can not be copied
CallTip(const CallTip &) {}
CallTip &operator=(const CallTip &) { return *this; }
public:
Window wCallTip;
Window wDraw;

View File

@@ -191,11 +191,23 @@ void LineVector::InsertValue(int pos, int value) {
}
}
lines++;
for (int i = lines + 1; i > pos; i--) {
for (int i = lines; i > pos; i--) {
linesData[i] = linesData[i - 1];
}
linesData[pos].startPosition = value;
linesData[pos].handleSet = 0;
if (levels) {
for (int j = lines; j > pos; j--) {
levels[j] = levels[j - 1];
}
if (pos == 0) {
levels[pos] = SC_FOLDLEVELBASE;
} else if (pos == (lines-1)) { // Last line will not be a folder
levels[pos] = SC_FOLDLEVELBASE;
} else {
levels[pos] = levels[pos-1];
}
}
}
void LineVector::SetValue(int pos, int value) {
@@ -221,6 +233,15 @@ void LineVector::Remove(int pos) {
for (int i = pos; i < lines; i++) {
linesData[i] = linesData[i + 1];
}
if (levels) {
// Level information merges back onto previous line
int posAbove = pos-1;
if (posAbove < 0)
posAbove = 0;
for (int j = posAbove; j < lines; j++) {
levels[j] = levels[j + 1];
}
}
lines--;
}
@@ -233,9 +254,8 @@ int LineVector::LineFromPosition(int pos) {
return lines - 1;
int lower = 0;
int upper = lines;
int middle = 0;
do {
middle = (upper + lower + 1) / 2; // Round high
int middle = (upper + lower + 1) / 2; // Round high
if (pos < linesData[middle].startPosition) {
upper = middle - 1;
} else {
@@ -316,12 +336,13 @@ Action::~Action() {
Destroy();
}
void Action::Create(actionType at_, int position_, char *data_, int lenData_) {
void Action::Create(actionType at_, int position_, char *data_, int lenData_, bool mayCoalesce_) {
delete []data;
position = position_;
at = at_;
data = data_;
lenData = lenData_;
mayCoalesce = mayCoalesce_;
}
void Action::Destroy() {
@@ -336,12 +357,14 @@ void Action::Grab(Action *source) {
at = source->at;
data = source->data;
lenData = source->lenData;
mayCoalesce = source->mayCoalesce;
// Ownership of source data transferred to this
source->position = 0;
source->at = startAction;
source->data = 0;
source->lenData = 0;
source->mayCoalesce = true;
}
// The undo history stores a sequence of user operations that represent the user's view of the
@@ -426,7 +449,9 @@ void UndoHistory::AppendAction(actionType at, int position, char *data, int leng
//Platform::DebugPrintf("action coalesced\n");
}
} else {
currentAction++;
// Actions not at top level are always coalesced unless this is after return to top level
if (!actions[currentAction].mayCoalesce)
currentAction++;
}
} else {
currentAction++;
@@ -445,6 +470,7 @@ void UndoHistory::BeginUndoAction() {
actions[currentAction].Create(startAction);
maxAction = currentAction;
}
actions[currentAction].mayCoalesce = false;
}
undoSequenceDepth++;
}
@@ -458,6 +484,7 @@ void UndoHistory::EndUndoAction() {
actions[currentAction].Create(startAction);
maxAction = currentAction;
}
actions[currentAction].mayCoalesce = false;
}
}
@@ -499,8 +526,12 @@ int UndoHistory::StartUndo() {
return currentAction - act;
}
const Action &UndoHistory::UndoStep() {
return actions[currentAction--];
const Action &UndoHistory::GetUndoStep() const {
return actions[currentAction];
}
void UndoHistory::CompletedUndoStep() {
currentAction--;
}
bool UndoHistory::CanRedo() const {
@@ -520,8 +551,12 @@ int UndoHistory::StartRedo() {
return act - currentAction;
}
const Action &UndoHistory::RedoStep() {
return actions[currentAction++];
const Action &UndoHistory::GetRedoStep() const {
return actions[currentAction];
}
void UndoHistory::CompletedRedoStep() {
currentAction++;
}
CellBuffer::CellBuffer(int initialLength) {
@@ -673,7 +708,7 @@ void CellBuffer::InsertCharStyle(int position, char ch, char style) {
bool CellBuffer::SetStyleAt(int position, char style, char mask) {
char curVal = ByteAt(position*2 + 1);
if ((curVal & mask) != style) {
SetByteAt(position*2 + 1, (curVal & ~mask) | style);
SetByteAt(position*2 + 1, static_cast<char>((curVal & ~mask) | style));
return true;
} else {
return false;
@@ -686,7 +721,7 @@ bool CellBuffer::SetStyleFor(int position, int lengthStyle, char style, char mas
while (lengthStyle--) {
char curVal = ByteAt(bytePos);
if ((curVal & mask) != style) {
SetByteAt(bytePos, (curVal & ~mask) | style);
SetByteAt(bytePos, static_cast<char>((curVal & ~mask) | style));
changed = true;
}
bytePos += 2;
@@ -947,8 +982,12 @@ int CellBuffer::StartUndo() {
return uh.StartUndo();
}
const Action &CellBuffer::UndoStep() {
const Action &actionStep = uh.UndoStep();
const Action &CellBuffer::GetUndoStep() const {
return uh.GetUndoStep();
}
void CellBuffer::PerformUndoStep() {
const Action &actionStep = uh.GetUndoStep();
if (actionStep.at == insertAction) {
BasicDeleteChars(actionStep.position, actionStep.lenData*2);
} else if (actionStep.at == removeAction) {
@@ -960,7 +999,7 @@ const Action &CellBuffer::UndoStep() {
BasicInsertString(actionStep.position, styledData, actionStep.lenData*2);
delete []styledData;
}
return actionStep;
uh.CompletedUndoStep();
}
bool CellBuffer::CanRedo() {
@@ -971,8 +1010,12 @@ int CellBuffer::StartRedo() {
return uh.StartRedo();
}
const Action &CellBuffer::RedoStep() {
const Action &actionStep = uh.RedoStep();
const Action &CellBuffer::GetRedoStep() const {
return uh.GetRedoStep();
}
void CellBuffer::PerformRedoStep() {
const Action &actionStep = uh.GetRedoStep();
if (actionStep.at == insertAction) {
char *styledData = new char[actionStep.lenData * 2];
for (int i = 0; i < actionStep.lenData; i++) {
@@ -984,7 +1027,7 @@ const Action &CellBuffer::RedoStep() {
} else if (actionStep.at == removeAction) {
BasicDeleteChars(actionStep.position, actionStep.lenData*2);
}
return actionStep;
uh.CompletedRedoStep();
}
int CellBuffer::SetLineState(int line, int state) {

View File

@@ -79,10 +79,11 @@ public:
int position;
char *data;
int lenData;
bool mayCoalesce;
Action();
~Action();
void Create(actionType at_, int position_=0, char *data_=0, int lenData_=0);
void Create(actionType at_, int position_=0, char *data_=0, int lenData_=0, bool mayCoalesce_=true);
void Destroy();
void Grab(Action *source);
};
@@ -119,10 +120,12 @@ public:
// called that many times. Similarly for redo.
bool CanUndo() const;
int StartUndo();
const Action &UndoStep();
const Action &GetUndoStep() const;
void CompletedUndoStep();
bool CanRedo() const;
int StartRedo();
const Action &RedoStep();
const Action &GetRedoStep() const;
void CompletedRedoStep();
};
// Holder for an expandable array of characters that supports undo and line markers
@@ -171,7 +174,7 @@ public:
// Setting styles for positions outside the range of the buffer is safe and has no effect.
// True is returned if the style of a character changed.
bool SetStyleAt(int position, char style, char mask=(char)0xff);
bool SetStyleAt(int position, char style, char mask='\377');
bool SetStyleFor(int position, int length, char style, char mask);
const char *DeleteChars(int position, int deleteLength);
@@ -206,10 +209,12 @@ public:
// called that many times. Similarly for redo.
bool CanUndo();
int StartUndo();
const Action &UndoStep();
const Action &GetUndoStep() const;
void PerformUndoStep();
bool CanRedo();
int StartRedo();
const Action &RedoStep();
const Action &GetRedoStep() const;
void PerformRedoStep();
int SetLineState(int line, int state);
int GetLineState(int line);

View File

@@ -30,7 +30,6 @@ void ContractionState::MakeValid() const {
if (!valid) {
// Could be cleverer by keeping the index of the last still valid entry
// rather than invalidating all.
int linePrev = -1;
int lineDisplay = 0;
for (int line=0; line<linesInDoc; line++) {
lines[line].displayLine = lineDisplay;
@@ -113,7 +112,7 @@ void ContractionState::InsertLines(int lineDoc, int lineCount) {
}
linesInDoc += lineCount;
linesInDisplay += lineCount;
for (int i = linesInDoc + 1; i >= lineDoc + lineCount; i--) {
for (int i = linesInDoc; i >= lineDoc + lineCount; i--) {
lines[i].visible = lines[i - lineCount].visible;
lines[i].expanded = lines[i - lineCount].expanded;
}
@@ -130,16 +129,18 @@ void ContractionState::DeleteLines(int lineDoc, int lineCount) {
linesInDisplay -= lineCount;
return;
}
int delta = 0;
for (int d=0;d<lineCount;d++)
int deltaDisplayed = 0;
for (int d=0;d<lineCount;d++) {
if (lines[lineDoc+d].visible)
delta--;
deltaDisplayed--;
}
for (int i = lineDoc; i < linesInDoc-lineCount; i++) {
lines[i].visible = lines[i + lineCount].visible;
if (i != 0) // Line zero is always visible
lines[i].visible = lines[i + lineCount].visible;
lines[i].expanded = lines[i + lineCount].expanded;
}
linesInDoc -= lineCount;
linesInDisplay += delta;
linesInDisplay += deltaDisplayed;
valid = false;
}
@@ -154,6 +155,10 @@ bool ContractionState::GetVisible(int lineDoc) const {
}
bool ContractionState::SetVisible(int lineDocStart, int lineDocEnd, bool visible) {
if (lineDocStart == 0)
lineDocStart++;
if (lineDocStart > lineDocEnd)
return false;
if (size == 0) {
Grow(linesInDoc + growSize);
}

View File

@@ -32,7 +32,10 @@ Document::Document() {
}
endStyled = 0;
enteredCount = 0;
enteredReadOnlyCount = 0;
tabInChars = 8;
indentInChars = 0;
useTabs = true;
watchers = 0;
lenWatchers = 0;
}
@@ -201,18 +204,23 @@ bool Document::IsCrLf(int pos) {
bool Document::IsDBCS(int pos) {
#if PLAT_WIN
if (dbcsCodePage) {
// Anchor DBCS calculations at start of line because start of line can
// not be a DBCS trail byte.
int startLine = pos;
while (startLine > 0 && cb.CharAt(startLine) != '\r' && cb.CharAt(startLine) != '\n')
startLine--;
while (startLine <= pos) {
if (IsDBCSLeadByteEx(dbcsCodePage, cb.CharAt(startLine))) {
if (SC_CP_UTF8 == dbcsCodePage) {
unsigned char ch = static_cast<unsigned char>(cb.CharAt(pos));
return ch >= 0x80;
} else {
// Anchor DBCS calculations at start of line because start of line can
// not be a DBCS trail byte.
int startLine = pos;
while (startLine > 0 && cb.CharAt(startLine) != '\r' && cb.CharAt(startLine) != '\n')
startLine--;
while (startLine <= pos) {
if (IsDBCSLeadByteEx(dbcsCodePage, cb.CharAt(startLine))) {
startLine++;
if (startLine >= pos)
return true;
}
startLine++;
if (startLine >= pos)
return true;
}
startLine++;
}
}
return false;
@@ -221,6 +229,28 @@ bool Document::IsDBCS(int pos) {
#endif
}
int Document::LenChar(int pos) {
if (IsCrLf(pos)) {
return 2;
} else if (SC_CP_UTF8 == dbcsCodePage) {
unsigned char ch = static_cast<unsigned char>(cb.CharAt(pos));
if (ch < 0x80)
return 1;
int len = 2;
if (ch >= (0x80+0x40+0x20))
len = 3;
int lengthDoc = Length();
if ((pos + len) > lengthDoc)
return lengthDoc-pos;
else
return len;
} else if (IsDBCS(pos)) {
return 2;
} else {
return 1;
}
}
// Normalise a position so that it is not halfway through a two byte character.
// This can occur in two situations -
// When lines are terminated with \r\n pairs which should be treated as one character.
@@ -252,29 +282,41 @@ int Document::MovePositionOutsideChar(int pos, int moveDir, bool checkLineEnd) {
#if PLAT_WIN
if (dbcsCodePage) {
// Anchor DBCS calculations at start of line because start of line can
// not be a DBCS trail byte.
int startLine = pos;
while (startLine > 0 && cb.CharAt(startLine) != '\r' && cb.CharAt(startLine) != '\n')
startLine--;
bool atLeadByte = false;
while (startLine < pos) {
if (atLeadByte)
atLeadByte = false;
else if (IsDBCSLeadByteEx(dbcsCodePage, cb.CharAt(startLine)))
atLeadByte = true;
else
atLeadByte = false;
startLine++;
//Platform::DebugPrintf("DBCS %s\n", atlead ? "D" : "-");
}
if (SC_CP_UTF8 == dbcsCodePage) {
unsigned char ch = static_cast<unsigned char>(cb.CharAt(pos));
while ((pos > 0) && (pos < Length()) && (ch >= 0x80) && (ch < (0x80 + 0x40))) {
// ch is a trail byte
if (moveDir > 0)
pos++;
else
pos--;
ch = static_cast<unsigned char>(cb.CharAt(pos));
}
} else {
// Anchor DBCS calculations at start of line because start of line can
// not be a DBCS trail byte.
int startLine = pos;
while (startLine > 0 && cb.CharAt(startLine) != '\r' && cb.CharAt(startLine) != '\n')
startLine--;
bool atLeadByte = false;
while (startLine < pos) {
if (atLeadByte)
atLeadByte = false;
else if (IsDBCSLeadByteEx(dbcsCodePage, cb.CharAt(startLine)))
atLeadByte = true;
else
atLeadByte = false;
startLine++;
//Platform::DebugPrintf("DBCS %s\n", atlead ? "D" : "-");
}
if (atLeadByte) {
// Position is between a lead byte and a trail byte
if (moveDir > 0)
return pos + 1;
else
return pos - 1;
if (atLeadByte) {
// Position is between a lead byte and a trail byte
if (moveDir > 0)
return pos + 1;
else
return pos - 1;
}
}
}
#endif
@@ -292,41 +334,60 @@ void Document::ModifiedAt(int pos) {
// Unlike Undo, Redo, and InsertStyledString, the pos argument is a cell number not a char number
void Document::DeleteChars(int pos, int len) {
if (cb.IsReadOnly() && enteredReadOnlyCount==0) {
enteredReadOnlyCount++;
NotifyModifyAttempt();
enteredReadOnlyCount--;
}
if (enteredCount == 0) {
enteredCount++;
if (cb.IsReadOnly())
NotifyModifyAttempt();
if (!cb.IsReadOnly()) {
NotifyModified(
DocModification(
SC_MOD_BEFOREDELETE | SC_PERFORMED_USER,
pos, len,
0, 0));
int prevLinesTotal = LinesTotal();
bool startSavePoint = cb.IsSavePoint();
const char *text = cb.DeleteChars(pos*2, len * 2);
if (startSavePoint && cb.IsCollectingUndo())
NotifySavePoint(!startSavePoint);
ModifiedAt(pos);
int modFlags = SC_MOD_DELETETEXT | SC_PERFORMED_USER;
DocModification mh(modFlags, pos, len, LinesTotal() - prevLinesTotal, text);
NotifyModified(mh);
NotifyModified(
DocModification(
SC_MOD_DELETETEXT | SC_PERFORMED_USER,
pos, len,
LinesTotal() - prevLinesTotal, text));
}
enteredCount--;
}
}
void Document::InsertStyledString(int position, char *s, int insertLength) {
if (cb.IsReadOnly() && enteredReadOnlyCount==0) {
enteredReadOnlyCount++;
NotifyModifyAttempt();
enteredReadOnlyCount--;
}
if (enteredCount == 0) {
enteredCount++;
if (cb.IsReadOnly())
NotifyModifyAttempt();
if (!cb.IsReadOnly()) {
NotifyModified(
DocModification(
SC_MOD_BEFOREINSERT | SC_PERFORMED_USER,
position / 2, insertLength / 2,
0, 0));
int prevLinesTotal = LinesTotal();
bool startSavePoint = cb.IsSavePoint();
const char *text = cb.InsertString(position, s, insertLength);
if (startSavePoint && cb.IsCollectingUndo())
NotifySavePoint(!startSavePoint);
ModifiedAt(position / 2);
int modFlags = SC_MOD_INSERTTEXT | SC_PERFORMED_USER;
DocModification mh(modFlags, position / 2, insertLength / 2, LinesTotal() - prevLinesTotal, text);
NotifyModified(mh);
NotifyModified(
DocModification(
SC_MOD_INSERTTEXT | SC_PERFORMED_USER,
position / 2, insertLength / 2,
LinesTotal() - prevLinesTotal, text));
}
enteredCount--;
}
@@ -341,7 +402,15 @@ int Document::Undo() {
//Platform::DebugPrintf("Steps=%d\n", steps);
for (int step=0; step<steps; step++) {
int prevLinesTotal = LinesTotal();
const Action &action = cb.UndoStep();
const Action &action = cb.GetUndoStep();
if (action.at == removeAction) {
NotifyModified(DocModification(
SC_MOD_BEFOREINSERT | SC_PERFORMED_UNDO, action));
} else {
NotifyModified(DocModification(
SC_MOD_BEFOREDELETE | SC_PERFORMED_UNDO, action));
}
cb.PerformUndoStep();
int cellPosition = action.position / 2;
ModifiedAt(cellPosition);
newPos = cellPosition;
@@ -376,10 +445,17 @@ int Document::Redo() {
int steps = cb.StartRedo();
for (int step=0; step<steps; step++) {
int prevLinesTotal = LinesTotal();
const Action &action = cb.RedoStep();
int cellPosition = action.position / 2;
ModifiedAt(cellPosition);
newPos = cellPosition;
const Action &action = cb.GetRedoStep();
if (action.at == insertAction) {
NotifyModified(DocModification(
SC_MOD_BEFOREINSERT | SC_PERFORMED_REDO, action));
} else {
NotifyModified(DocModification(
SC_MOD_BEFOREDELETE | SC_PERFORMED_REDO, action));
}
cb.PerformRedoStep();
ModifiedAt(action.position / 2);
newPos = action.position / 2;
int modFlags = SC_PERFORMED_REDO;
if (action.at == insertAction) {
@@ -390,7 +466,8 @@ int Document::Redo() {
}
if (step == steps-1)
modFlags |= SC_LASTSTEPINUNDOREDO;
NotifyModified(DocModification(modFlags, cellPosition, action.lenData,
NotifyModified(
DocModification(modFlags, action.position / 2, action.lenData,
LinesTotal() - prevLinesTotal, action.data));
}
@@ -433,13 +510,7 @@ void Document::ChangeChar(int pos, char ch) {
}
void Document::DelChar(int pos) {
if (IsCrLf(pos)) {
DeleteChars(pos, 2);
} else if (IsDBCS(pos)) {
DeleteChars(pos, 2);
} else if (pos < Length()) {
DeleteChars(pos, 1);
}
DeleteChars(pos, LenChar(pos));
}
int Document::DelCharBack(int pos) {
@@ -448,6 +519,10 @@ int Document::DelCharBack(int pos) {
} else if (IsCrLf(pos - 2)) {
DeleteChars(pos - 2, 2);
return pos - 2;
} else if (SC_CP_UTF8 == dbcsCodePage) {
int startChar = MovePositionOutsideChar(pos-1, -1, false);
DeleteChars(startChar, pos - startChar);
return startChar;
} else if (IsDBCS(pos - 1)) {
DeleteChars(pos - 2, 2);
return pos - 2;
@@ -457,27 +532,80 @@ int Document::DelCharBack(int pos) {
}
}
static bool isindentchar(char ch) {
return (ch == ' ') || (ch == '\t');
}
static int NextTab(int pos, int tabSize) {
return ((pos / tabSize) + 1) * tabSize;
}
static void CreateIndentation(char *linebuf, int length, int indent, int tabSize, bool insertSpaces) {
length--; // ensure space for \0
if (!insertSpaces) {
while ((indent >= tabSize) && (length > 0)) {
*linebuf++ = '\t';
indent -= tabSize;
length--;
}
}
while ((indent > 0) && (length > 0)) {
*linebuf++ = ' ';
indent--;
length--;
}
*linebuf = '\0';
}
int Document::GetLineIndentation(int line) {
int indent = 0;
if ((line >= 0) && (line < LinesTotal())) {
int lineStart = LineStart(line);
int length = Length();
for (int i=lineStart;i<length;i++) {
char ch = cb.CharAt(i);
if (ch == ' ')
indent++;
else if (ch == '\t')
indent = NextTab(indent, tabInChars);
else
return indent;
}
}
return indent;
}
void Document::SetLineIndentation(int line, int indent) {
int indentOfLine = GetLineIndentation(line);
if (indent < 0)
indent = 0;
if (indent != indentOfLine) {
char linebuf[1000];
CreateIndentation(linebuf, sizeof(linebuf), indent, tabInChars, !useTabs);
int thisLineStart = LineStart(line);
int indentPos = GetLineIndentPosition(line);
DeleteChars(thisLineStart, indentPos - thisLineStart);
InsertString(thisLineStart, linebuf);
}
}
int Document::GetLineIndentPosition(int line) {
int pos = LineStart(line);
int length = Length();
while ((pos < length) && isindentchar(cb.CharAt(pos))) {
pos++;
}
return pos;
}
void Document::Indent(bool forwards, int lineBottom, int lineTop) {
if (forwards) {
// Indent by a tab
for (int line = lineBottom; line >= lineTop; line--) {
InsertChar(LineStart(line), '\t');
}
} else {
// Dedent - suck white space off the front of the line to dedent by equivalent of a tab
for (int line = lineBottom; line >= lineTop; line--) {
int ispc = 0;
while (ispc < tabInChars && cb.CharAt(LineStart(line) + ispc) == ' ')
ispc++;
int posStartLine = LineStart(line);
if (ispc == tabInChars) {
DeleteChars(posStartLine, ispc);
} else if (cb.CharAt(posStartLine + ispc) == '\t') {
DeleteChars(posStartLine, ispc + 1);
} else { // Hit a non-white
DeleteChars(posStartLine, ispc);
}
}
// Dedent - suck white space off the front of the line to dedent by equivalent of a tab
for (int line = lineBottom; line >= lineTop; line--) {
int indentOfLine = GetLineIndentation(line);
if (forwards)
SetLineIndentation(line, indentOfLine + IndentSize());
else
SetLineIndentation(line, indentOfLine - IndentSize());
}
}
@@ -522,6 +650,8 @@ void Document::ConvertLineEnds(int eolModeSet) {
}
bool Document::IsWordChar(unsigned char ch) {
if ((SC_CP_UTF8 == dbcsCodePage) && (ch >0x80))
return true;
return wordchars[ch];
}
@@ -588,16 +718,14 @@ long Document::FindText(int minPos, int maxPos, const char *s, bool caseSensitiv
// Compute actual search ranges needed
int lengthFind = strlen(s);
int endSearch = 0;
int endSearch = endPos;
if (startPos <= endPos) {
endSearch = endPos - lengthFind + 1;
} else {
endSearch = endPos;
}
//Platform::DebugPrintf("Find %d %d %s %d\n", startPos, endPos, ft->lpstrText, lengthFind);
char firstChar = s[0];
if (!caseSensitive)
firstChar = toupper(firstChar);
firstChar = static_cast<char>(toupper(firstChar));
int pos = startPos;
while (forward ? (pos < endSearch) : (pos >= endSearch)) {
char ch = CharAt(pos);
@@ -646,15 +774,15 @@ void Document::ChangeCase(Range r, bool makeUpperCase) {
for (int pos=r.start; pos<r.end; pos++) {
char ch = CharAt(pos);
if (dbcsCodePage && IsDBCS(pos)) {
pos++;
pos += LenChar(pos);
} else {
if (makeUpperCase) {
if (islower(ch)) {
ChangeChar(pos, toupper(ch));
ChangeChar(pos, static_cast<char>(toupper(ch)));
}
} else {
if (isupper(ch)) {
ChangeChar(pos, tolower(ch));
ChangeChar(pos, static_cast<char>(tolower(ch)));
}
}
}
@@ -795,5 +923,3 @@ void Document::NotifyModified(DocModification mh) {
watchers[i].watcher->NotifyModified(this, mh, watchers[i].userData);
}
}

View File

@@ -74,9 +74,10 @@ private:
CellBuffer cb;
bool wordchars[256];
int stylingPos;
int stylingMask;
char stylingMask;
int endStyled;
int enteredCount;
int enteredReadOnlyCount;
WatcherWithUserData *watchers;
int lenWatchers;
@@ -86,8 +87,11 @@ public:
int stylingBitsMask;
int eolMode;
// dbcsCodePage can also be SC_CP_UTF8 to enable UTF-8 mode
int dbcsCodePage;
int tabInChars;
int indentInChars;
bool useTabs;
Document();
virtual ~Document();
@@ -98,6 +102,7 @@ public:
int LineFromPosition(int pos);
int ClampPositionIntoDocument(int pos);
bool IsCrLf(int pos);
int LenChar(int pos);
int MovePositionOutsideChar(int pos, int moveDir, bool checkLineEnd=true);
// Gateways to modifying document
@@ -115,6 +120,10 @@ public:
void EndUndoAction() { cb.EndUndoAction(); }
void SetSavePoint();
bool IsSavePoint() { return cb.IsSavePoint(); }
int GetLineIndentation(int line);
void SetLineIndentation(int line, int indent);
int GetLineIndentPosition(int line);
void Indent(bool forwards, int lineBottom, int lineTop);
void ConvertLineEnds(int eolModeSet);
void SetReadOnly(bool set) { cb.SetReadOnly(set); }
@@ -183,6 +192,8 @@ private:
void NotifyModifyAttempt();
void NotifySavePoint(bool atSavePoint);
void NotifyModified(DocModification mh);
int IndentSize() { return indentInChars ? indentInChars : tabInChars; }
};
// To optimise processing of document modifications by DocWatchers, a hint is passed indicating the
@@ -209,6 +220,16 @@ public:
line(0),
foldLevelNow(0),
foldLevelPrev(0) {}
DocModification(int modificationType_, const Action &act, int linesAdded_=0) :
modificationType(modificationType_),
position(act.position / 2),
length(act.lenData),
linesAdded(linesAdded_),
text(act.data),
line(0),
foldLevelNow(0),
foldLevelPrev(0) {}
};
// A class that wants to receive notifications from a Document must be derived from DocWatcher

View File

@@ -0,0 +1,174 @@
// SciTE - Scintilla based Text Editor
// Accessor.cxx - rapid easy access to contents of a Scintilla
// Copyright 1998-2000 by Neil Hodgson <neilh@scintilla.org>
// The License.txt file describes the conditions under which this software may be distributed.
#include <stdlib.h>
#include <ctype.h>
#include <stdio.h>
#include "Platform.h"
#include "PropSet.h"
#include "SVector.h"
#include "Accessor.h"
#include "DocumentAccessor.h"
#include "CellBuffer.h"
#include "Scintilla.h"
#include "Document.h"
DocumentAccessor::~DocumentAccessor() {
}
bool DocumentAccessor::InternalIsLeadByte(char ch) {
#if PLAT_GTK
// TODO: support DBCS under GTK+
return false;
#elif PLAT_WIN
if (SC_CP_UTF8 == codePage)
// For lexing, all characters >= 0x80 are treated the
// same so none is considered a lead byte.
return false;
else
return IsDBCSLeadByteEx(codePage, ch);
#elif PLAT_WX
return false;
#endif
}
void DocumentAccessor::Fill(int position) {
if (lenDoc == -1)
lenDoc = pdoc->Length();
startPos = position - slopSize;
if (startPos + bufferSize > lenDoc)
startPos = lenDoc - bufferSize;
if (startPos < 0)
startPos = 0;
endPos = startPos + bufferSize;
if (endPos > lenDoc)
endPos = lenDoc;
pdoc->GetCharRange(buf, startPos, endPos-startPos);
buf[endPos-startPos] = '\0';
}
char DocumentAccessor::StyleAt(int position) {
return pdoc->StyleAt(position);
}
int DocumentAccessor::GetLine(int position) {
return pdoc->LineFromPosition(position);
}
int DocumentAccessor::LineStart(int line) {
return pdoc->LineStart(line);
}
int DocumentAccessor::LevelAt(int line) {
return pdoc->GetLevel(line);
}
int DocumentAccessor::Length() {
if (lenDoc == -1)
lenDoc = pdoc->Length();
return lenDoc;
}
int DocumentAccessor::GetLineState(int line) {
return pdoc->GetLineState(line);
}
int DocumentAccessor::SetLineState(int line, int state) {
return pdoc->SetLineState(line, state);
}
void DocumentAccessor::StartAt(unsigned int start, char chMask) {
pdoc->StartStyling(start, chMask);
}
void DocumentAccessor::StartSegment(unsigned int pos) {
startSeg = pos;
}
void DocumentAccessor::ColourTo(unsigned int pos, int chAttr) {
// Only perform styling if non empty range
if (pos != startSeg - 1) {
if (pos < startSeg) {
Platform::DebugPrintf("Bad colour positions %d - %d\n", startSeg, pos);
}
if (validLen + (pos - startSeg + 1) >= bufferSize)
Flush();
if (validLen + (pos - startSeg + 1) >= bufferSize) {
// Too big for buffer so send directly
pdoc->SetStyleFor(pos - startSeg + 1, static_cast<char>(chAttr));
} else {
if (chAttr != chWhile)
chFlags = 0;
chAttr |= chFlags;
for (unsigned int i = startSeg; i <= pos; i++) {
styleBuf[validLen++] = static_cast<char>(chAttr);
}
}
}
startSeg = pos+1;
}
void DocumentAccessor::SetLevel(int line, int level) {
pdoc->SetLevel(line, level);
}
void DocumentAccessor::Flush() {
startPos = extremePosition;
lenDoc = -1;
if (validLen > 0) {
pdoc->SetStyles(validLen, styleBuf);
validLen = 0;
}
}
int DocumentAccessor::IndentAmount(int line, int *flags, PFNIsCommentLeader pfnIsCommentLeader) {
int end = Length();
int spaceFlags = 0;
// Determines the indentation level of the current line and also checks for consistent
// indentation compared to the previous line.
// Indentation is judged consistent when the indentation whitespace of each line lines
// the same or the indentation of one line is a prefix of the other.
int pos = LineStart(line);
char ch = (*this)[pos];
int indent = 0;
bool inPrevPrefix = line > 0;
int posPrev = inPrevPrefix ? LineStart(line-1) : 0;
while ((ch == ' ' || ch == '\t') && (pos < end)) {
if (inPrevPrefix) {
char chPrev = (*this)[posPrev++];
if (chPrev == ' ' || chPrev == '\t') {
if (chPrev != ch)
spaceFlags |= wsInconsistent;
} else {
inPrevPrefix = false;
}
}
if (ch == ' ') {
spaceFlags |= wsSpace;
indent++;
} else { // Tab
spaceFlags |= wsTab;
if (spaceFlags & wsSpace)
spaceFlags |= wsSpaceTab;
indent = (indent / 8 + 1) * 8;
}
ch = (*this)[++pos];
}
*flags = spaceFlags;
indent += SC_FOLDLEVELBASE;
// if completely empty line or the start of a comment...
if (isspace(ch) || (pfnIsCommentLeader && (*pfnIsCommentLeader)(*this, pos, end-pos)) )
return indent | SC_FOLDLEVELWHITEFLAG;
else
return indent;
}

View File

@@ -0,0 +1,49 @@
// DocumentAccessor.h - implementation of BufferAccess and StylingAccess on a Scintilla rapid easy access to contents of a Scintilla
// Copyright 1998-2000 by Neil Hodgson <neilh@scintilla.org>
// The License.txt file describes the conditions under which this software may be distributed.
class Document;
class DocumentAccessor : public Accessor {
// Private so DocumentAccessor objects can not be copied
DocumentAccessor(const DocumentAccessor &source) : Accessor(), props(source.props) {}
DocumentAccessor &operator=(const DocumentAccessor &) { return *this; }
protected:
Document *pdoc;
PropSet &props;
int lenDoc;
char styleBuf[bufferSize];
int validLen;
char chFlags;
char chWhile;
unsigned int startSeg;
bool InternalIsLeadByte(char ch);
void Fill(int position);
public:
DocumentAccessor(Document *pdoc_, PropSet &props_) :
Accessor(), pdoc(pdoc_), props(props_),
lenDoc(-1), validLen(0), chFlags(0) {
}
~DocumentAccessor();
char StyleAt(int position);
int GetLine(int position);
int LineStart(int line);
int LevelAt(int line);
int Length();
void Flush();
int GetLineState(int line);
int SetLineState(int line, int state);
int GetPropertyInt(const char *key, int defaultValue=0) {
return props.GetInt(key, defaultValue);
}
void StartAt(unsigned int start, char chMask=31);
void SetFlags(char chFlags_, char chWhile_) {chFlags = chFlags_; chWhile = chWhile_; };
unsigned int GetStartSegment() { return startSeg; }
void StartSegment(unsigned int pos);
void ColourTo(unsigned int pos, int chAttr);
void SetLevel(int line, int level);
int IndentAmount(int line, int *flags, PFNIsCommentLeader pfnIsCommentLeader = 0);
};

View File

@@ -69,6 +69,7 @@ Editor::Editor() {
xOffset = 0;
xCaretMargin = 50;
horizontalScrollBarVisible = true;
currentPos = 0;
anchor = 0;
@@ -189,7 +190,7 @@ bool IsControlCharacter(char ch) {
return ch >= 0 && ch < ' ';
}
const char *ControlCharacterString(char ch) {
const char *ControlCharacterString(unsigned char ch) {
const char *reps[] = {
"NUL", "SOH", "STX", "ETX", "EOT", "ENQ", "ACK", "BEL",
"BS", "HT", "LF", "VT", "FF", "CR", "SO", "SI",
@@ -210,6 +211,7 @@ Point Editor::LocationFromPosition(unsigned int pos) {
//Platform::DebugPrintf("line=%d\n", line);
Surface surface;
surface.Init();
surface.SetUnicodeMode(SC_CP_UTF8 == pdoc->dbcsCodePage);
Point pt;
pt.y = (lineVisible - topLine) * vs.lineHeight; // + half a lineheight?
unsigned int posLineStart = pdoc->LineStart(line);
@@ -252,6 +254,7 @@ int Editor::PositionFromLocation(Point pt) {
//Platform::DebugPrintf("Position of (%d,%d) line = %d top=%d\n", pt.x, pt.y, line, topLine);
Surface surface;
surface.Init();
surface.SetUnicodeMode(SC_CP_UTF8 == pdoc->dbcsCodePage);
unsigned int posLineStart = pdoc->LineStart(line);
LineLayout ll;
@@ -273,6 +276,7 @@ int Editor::PositionFromLineX(int line, int x) {
//Platform::DebugPrintf("Position of (%d,%d) line = %d top=%d\n", pt.x, pt.y, line, topLine);
Surface surface;
surface.Init();
surface.SetUnicodeMode(SC_CP_UTF8 == pdoc->dbcsCodePage);
unsigned int posLineStart = pdoc->LineStart(line);
LineLayout ll;
@@ -485,7 +489,7 @@ void Editor::ScrollTo(int line) {
}
}
void Editor::ScrollText(int linesToMove) {
void Editor::ScrollText(int /* linesToMove */) {
//Platform::DebugPrintf("Editor::ScrollText %d\n", linesToMove);
Redraw();
}
@@ -499,6 +503,19 @@ void Editor::HorizontalScrollTo(int xPos) {
Redraw();
}
void Editor::MoveCaretInsideView() {
PRectangle rcClient = GetTextRectangle();
Point pt = LocationFromPosition(currentPos);
if (pt.y < rcClient.top) {
MovePositionTo(PositionFromLocation(
Point(lastXChosen, rcClient.top)));
} else if ((pt.y + vs.lineHeight - 1) > rcClient.bottom) {
int yOfLastLineFullyDisplayed = rcClient.top + (LinesOnScreen()-1) * vs.lineHeight;
MovePositionTo(PositionFromLocation(
Point(lastXChosen, rcClient.top + yOfLastLineFullyDisplayed)));
}
}
void Editor::EnsureCaretVisible(bool useMargin) {
//Platform::DebugPrintf("EnsureCaretVisible %d\n", xOffset);
PRectangle rcClient = GetTextRectangle();
@@ -652,11 +669,10 @@ void Editor::PaintSelMargin(Surface *surfWindow, PRectangle &rc) {
sprintf(number, "%d", line + 1);
if (foldFlags & 64)
sprintf(number, "%X", pdoc->GetLevel(line));
int xpos = 0;
PRectangle rcNumber=rcMarker;
// Right justify
int width = surface->WidthText(vs.styles[STYLE_LINENUMBER].font, number, strlen(number));
xpos = rcNumber.right - width - 3;
int xpos = rcNumber.right - width - 3;
rcNumber.left = xpos;
if ((visibleLine < cs.LinesDisplayed()) && cs.GetVisible(line)) {
surface->DrawText(rcNumber, vs.styles[STYLE_LINENUMBER].font,
@@ -720,8 +736,8 @@ void Editor::LayoutLine(int line, Surface *surface, ViewStyle &vstyle, LineLayou
styleByte = pdoc->StyleAt(charInDoc);
if (vstyle.viewEOL || ((chDoc != '\r') && (chDoc != '\n'))) {
ll.chars[numCharsInLine] = chDoc;
ll.styles[numCharsInLine] = styleByte & styleMask;
ll.indicators[numCharsInLine] = styleByte & ~styleMask;
ll.styles[numCharsInLine] = static_cast<char>(styleByte & styleMask);
ll.indicators[numCharsInLine] = static_cast<char>(styleByte & ~styleMask);
numCharsInLine++;
}
}
@@ -1017,14 +1033,13 @@ void Editor::Paint(Surface *surfaceWindow, PRectangle rcArea) {
}
//Platform::DebugPrintf("start display %d, offset = %d\n", pdoc->Length(), xOffset);
Surface *surface = 0;
if (rcArea.right > vs.fixedColumnWidth) {
Surface *surface = surfaceWindow;
if (bufferedDraw) {
surface = &pixmapLine;
} else {
surface = surfaceWindow;
}
surface->SetUnicodeMode(SC_CP_UTF8 == pdoc->dbcsCodePage);
int visibleLine = topLine + screenLinePaintFirst;
int line = cs.DocFromDisplay(visibleLine);
@@ -1060,9 +1075,11 @@ void Editor::Paint(Surface *surfaceWindow, PRectangle rcArea) {
// Highlight the current braces if any
if ((braces[0] >= posLineStart) && (braces[0] < posLineEnd))
ll.styles[braces[0] - posLineStart] = bracesMatchStyle;
ll.styles[braces[0] - posLineStart] =
static_cast<char>(bracesMatchStyle);
if ((braces[1] >= posLineStart) && (braces[1] < posLineEnd))
ll.styles[braces[1] - posLineStart] = bracesMatchStyle;
ll.styles[braces[1] - posLineStart] =
static_cast<char>(bracesMatchStyle);
// Draw the line
if (cs.GetVisible(line))
@@ -1086,9 +1103,10 @@ void Editor::Paint(Surface *surfaceWindow, PRectangle rcArea) {
// Draw the Caret
if (line == lineCaret) {
int xposCaret = ll.positions[posCaret - posLineStart] + xStart;
int offset = Platform::Minimum(posCaret - posLineStart, LineLayout::maxLineLength);
int xposCaret = ll.positions[offset] + xStart;
int widthOverstrikeCaret =
ll.positions[posCaret - posLineStart + 1] - ll.positions[posCaret - posLineStart];
ll.positions[offset + 1] - ll.positions[offset];
if (posCaret == pdoc->Length()) // At end of document
widthOverstrikeCaret = vs.aveCharWidth;
if ((posCaret - posLineStart) >= ll.numCharsInLine) // At end of line
@@ -1163,8 +1181,10 @@ long Editor::FormatRange(bool draw, FORMATRANGE *pfr) {
Surface *surface = new Surface();
surface->Init(pfr->hdc);
surface->SetUnicodeMode(SC_CP_UTF8 == pdoc->dbcsCodePage);
Surface *surfaceMeasure = new Surface();
surfaceMeasure->Init(pfr->hdcTarget);
surfaceMeasure->SetUnicodeMode(SC_CP_UTF8 == pdoc->dbcsCodePage);
ViewStyle vsPrint(vs);
@@ -1270,6 +1290,10 @@ long Editor::FormatRange(bool draw, FORMATRANGE *pfr) {
return endPosPrint;
}
// Empty method is overridden on GTK+ to show / hide scrollbars
void Editor::ReconfigureScrollBars() {
}
void Editor::SetScrollBarsTo(PRectangle) {
RefreshStyleData();
@@ -1295,6 +1319,13 @@ void Editor::SetScrollBars() {
}
void Editor::AddChar(char ch) {
char s[2];
s[0] = ch;
s[1] = '\0';
AddCharUTF(s, 1);
}
void Editor::AddCharUTF(char *s, unsigned int len) {
bool wasSelection = currentPos != anchor;
ClearSelection();
if (inOverstrike && !wasSelection) {
@@ -1304,11 +1335,11 @@ void Editor::AddChar(char ch) {
}
}
}
pdoc->InsertChar(currentPos, ch);
SetEmptySelection(currentPos + 1);
pdoc->InsertString(currentPos, s, len);
SetEmptySelection(currentPos + len);
EnsureCaretVisible();
SetLastXChosen();
NotifyChar(ch);
NotifyChar(s[0]);
}
void Editor::ClearSelection() {
@@ -1429,7 +1460,7 @@ void Editor::DelCharBack() {
void Editor::NotifyFocus(bool) {
}
void Editor::NotifyStyleNeeded(int endStyleNeeded) {
void Editor::NotifyStyleToNeeded(int endStyleNeeded) {
SCNotification scn;
scn.nmhdr.code = SCN_STYLENEEDED;
scn.position = endStyleNeeded;
@@ -1437,7 +1468,7 @@ void Editor::NotifyStyleNeeded(int endStyleNeeded) {
}
void Editor::NotifyStyleNeeded(Document*, void *, int endStyleNeeded) {
NotifyStyleNeeded(endStyleNeeded);
NotifyStyleToNeeded(endStyleNeeded);
}
void Editor::NotifyChar(char ch) {
@@ -1582,13 +1613,17 @@ void Editor::NotifyModified(Document*, DocModification mh, void *) {
}
}
}
if (mh.modificationType & SC_MOD_BEFOREINSERT) {
NotifyNeedShown(mh.position, 0);
} else if (mh.modificationType & SC_MOD_BEFOREDELETE) {
NotifyNeedShown(mh.position, mh.length);
}
if (mh.linesAdded != 0) {
// Update contraction state for inserted and removed lines
// lineOfPos should be calculated in context of state before modification, shouldn't it
int lineOfPos = pdoc->LineFromPosition(mh.position);
if (mh.linesAdded > 0) {
NotifyNeedShown(mh.position, mh.length);
cs.InsertLines(lineOfPos, mh.linesAdded);
} else {
cs.DeleteLines(lineOfPos, -mh.linesAdded);
@@ -1642,7 +1677,7 @@ void Editor::NotifyModified(Document*, DocModification mh, void *) {
}
}
void Editor::NotifyDeleted(Document *document, void *userData) {
void Editor::NotifyDeleted(Document *, void *) {
/* Do nothing */
}
@@ -1806,6 +1841,10 @@ int Editor::KeyCommand(UINT iMessage) {
MovePositionTo(PositionFromLocation(
Point(lastXChosen, pt.y + vs.lineHeight)), true);
break;
case SCI_LINESCROLLDOWN:
ScrollTo(topLine + 1);
MoveCaretInsideView();
break;
case SCI_LINEUP:
MovePositionTo(PositionFromLocation(
Point(lastXChosen, pt.y - vs.lineHeight)));
@@ -1814,6 +1853,10 @@ int Editor::KeyCommand(UINT iMessage) {
MovePositionTo(PositionFromLocation(
Point(lastXChosen, pt.y - vs.lineHeight)), true);
break;
case SCI_LINESCROLLUP:
ScrollTo(topLine - 1);
MoveCaretInsideView();
break;
case SCI_CHARLEFT:
if (SelectionEmpty()) {
MovePositionTo(MovePositionSoVisible(currentPos - 1, -1));
@@ -1909,6 +1952,7 @@ int Editor::KeyCommand(UINT iMessage) {
break;
case SCI_DELETEBACK:
DelCharBack();
SetLastXChosen();
EnsureCaretVisible();
break;
case SCI_TAB:
@@ -1961,6 +2005,7 @@ int Editor::KeyCommand(UINT iMessage) {
int startWord = pdoc->NextWordStart(currentPos, -1);
pdoc->DeleteChars(startWord, currentPos - startWord);
MovePositionTo(startWord);
SetLastXChosen();
}
break;
case SCI_DELWORDRIGHT: {
@@ -2628,12 +2673,13 @@ char BraceOpposite(char ch) {
// TODO: should be able to extend styled region to find matching brace
// TODO: may need to make DBCS safe
// so should be moved into Document
int Editor::BraceMatch(int position, int maxReStyle) {
int Editor::BraceMatch(int position, int /*maxReStyle*/) {
char chBrace = pdoc->CharAt(position);
char chSeek = BraceOpposite(chBrace);
if (!chSeek)
if (chSeek == '\0')
return - 1;
char styBrace = pdoc->StyleAt(position) & pdoc->stylingBitsMask;
char styBrace = static_cast<char>(
pdoc->StyleAt(position) & pdoc->stylingBitsMask);
int direction = -1;
if (chBrace == '(' || chBrace == '[' || chBrace == '{' || chBrace == '<')
direction = 1;
@@ -2641,7 +2687,7 @@ int Editor::BraceMatch(int position, int maxReStyle) {
position = position + direction;
while ((position >= 0) && (position < pdoc->Length())) {
char chAtPos = pdoc->CharAt(position);
char styAtPos = pdoc->StyleAt(position) & pdoc->stylingBitsMask;
char styAtPos = static_cast<char>(pdoc->StyleAt(position) & pdoc->stylingBitsMask);
if ((position > pdoc->GetEndStyled()) || (styAtPos == styBrace)) {
if (chAtPos == chBrace)
depth++;
@@ -2750,6 +2796,11 @@ void Editor::EnsureLineVisible(int line) {
}
}
static bool ValidMargin(WPARAM wParam) {
return wParam < ViewStyle::margins;
}
LRESULT Editor::WndProc(UINT iMessage, WPARAM wParam, LPARAM lParam) {
//Platform::DebugPrintf("S start wnd proc %d %d %d\n",iMessage, wParam, lParam);
@@ -3313,11 +3364,11 @@ LRESULT Editor::WndProc(UINT iMessage, WPARAM wParam, LPARAM lParam) {
break;
case SCI_STARTSTYLING:
pdoc->StartStyling(wParam, lParam);
pdoc->StartStyling(wParam, static_cast<char>(lParam));
break;
case SCI_SETSTYLING:
pdoc->SetStyleFor(wParam, lParam);
pdoc->SetStyleFor(wParam, static_cast<char>(lParam));
break;
case SCI_SETSTYLINGEX: // Specify a complete styling buffer
@@ -3345,6 +3396,44 @@ LRESULT Editor::WndProc(UINT iMessage, WPARAM wParam, LPARAM lParam) {
InvalidateStyleRedraw();
break;
case SCI_GETTABWIDTH:
return pdoc->tabInChars;
case SCI_SETINDENT:
pdoc->indentInChars = wParam;
InvalidateStyleRedraw();
break;
case SCI_GETINDENT:
return pdoc->indentInChars;
case SCI_SETUSETABS:
pdoc->useTabs = wParam;
InvalidateStyleRedraw();
break;
case SCI_GETUSETABS:
return pdoc->useTabs;
case SCI_SETLINEINDENTATION:
pdoc->SetLineIndentation(wParam, lParam);
break;
case SCI_GETLINEINDENTATION:
return pdoc->GetLineIndentation(wParam);
case SCI_GETLINEINDENTPOSITION:
return pdoc->GetLineIndentPosition(wParam);
case SCI_SETHSCROLLBAR :
horizontalScrollBarVisible = wParam;
SetScrollBars();
ReconfigureScrollBars();
break;
case SCI_GETHSCROLLBAR:
return horizontalScrollBarVisible;
case SCI_SETCODEPAGE:
pdoc->dbcsCodePage = wParam;
break;
@@ -3416,53 +3505,53 @@ LRESULT Editor::WndProc(UINT iMessage, WPARAM wParam, LPARAM lParam) {
return -1;
case SCI_SETMARGINTYPEN:
if (wParam >= 0 && wParam < ViewStyle::margins) {
if (ValidMargin(wParam)) {
vs.ms[wParam].symbol = (lParam == SC_MARGIN_SYMBOL);
InvalidateStyleRedraw();
}
break;
case SCI_GETMARGINTYPEN:
if (wParam >= 0 && wParam < ViewStyle::margins)
if (ValidMargin(wParam))
return vs.ms[wParam].symbol ? SC_MARGIN_SYMBOL : SC_MARGIN_NUMBER;
else
return 0;
case SCI_SETMARGINWIDTHN:
if (wParam >= 0 && wParam < ViewStyle::margins) {
if (ValidMargin(wParam)) {
vs.ms[wParam].width = lParam;
InvalidateStyleRedraw();
}
break;
case SCI_GETMARGINWIDTHN:
if (wParam >= 0 && wParam < ViewStyle::margins)
if (ValidMargin(wParam))
return vs.ms[wParam].width;
else
return 0;
case SCI_SETMARGINMASKN:
if (wParam >= 0 && wParam < ViewStyle::margins) {
if (ValidMargin(wParam)) {
vs.ms[wParam].mask = lParam;
InvalidateStyleRedraw();
}
break;
case SCI_GETMARGINMASKN:
if (wParam >= 0 && wParam < ViewStyle::margins)
if (ValidMargin(wParam))
return vs.ms[wParam].mask;
else
return 0;
case SCI_SETMARGINSENSITIVEN:
if (wParam >= 0 && wParam < ViewStyle::margins) {
if (ValidMargin(wParam)) {
vs.ms[wParam].sensitive = lParam;
InvalidateStyleRedraw();
}
break;
case SCI_GETMARGINSENSITIVEN:
if (wParam >= 0 && wParam < ViewStyle::margins)
if (ValidMargin(wParam))
return vs.ms[wParam].sensitive ? 1 : 0;
else
return 0;
@@ -3606,7 +3695,6 @@ LRESULT Editor::WndProc(UINT iMessage, WPARAM wParam, LPARAM lParam) {
case SCI_SEARCHNEXT:
case SCI_SEARCHPREV:
return SearchText(iMessage, wParam, lParam);
break;
case SCI_SETCARETPOLICY:
caretPolicy = wParam;
@@ -3745,6 +3833,8 @@ LRESULT Editor::WndProc(UINT iMessage, WPARAM wParam, LPARAM lParam) {
case SCI_LINETRANSPOSE:
case SCI_LOWERCASE:
case SCI_UPPERCASE:
case SCI_LINESCROLLDOWN:
case SCI_LINESCROLLUP:
return KeyCommand(iMessage);
case SCI_BRACEHIGHLIGHT:
@@ -3808,6 +3898,9 @@ LRESULT Editor::WndProc(UINT iMessage, WPARAM wParam, LPARAM lParam) {
SetSelection(currentPos, anchor); // Ensure selection inside document
return 0;
case SCI_SELECTIONISRECTANGLE:
return (selType == selRectangle) ? 1 : 0;
#ifdef MACRO_SUPPORT
case SCI_STARTRECORD:
recordingMacro = 1;

View File

@@ -38,6 +38,9 @@ public:
};
class Editor : public DocWatcher {
// Private so Editor objects can not be copied
Editor(const Editor &) : DocWatcher() {}
Editor &operator=(const Editor &) { return *this; }
protected: // ScintillaBase subclass needs access to much of Editor
// On GTK+, Scintilla is a container widget holding two scroll bars and a drawing area
@@ -61,13 +64,14 @@ protected: // ScintillaBase subclass needs access to much of Editor
int xOffset; // Horizontal scrolled amount in pixels
int xCaretMargin; // Ensure this many pixels visible on both sides of caret
bool horizontalScrollBarVisible;
Surface pixmapLine;
Surface pixmapSelMargin;
Surface pixmapSelPattern;
// Intellimouse support - currently only implemented for Windows
unsigned int ucWheelScrollLines;
short cWheelDelta; //wheel delta from roll
int cWheelDelta; //wheel delta from roll
KeyMap kmap;
@@ -171,6 +175,7 @@ protected: // ScintillaBase subclass needs access to much of Editor
void ScrollTo(int line);
virtual void ScrollText(int linesToMove);
void HorizontalScrollTo(int xPos);
void MoveCaretInsideView();
void EnsureCaretVisible(bool useMargin=true);
void ShowCaretAtCurrentPosition();
void DropCaret();
@@ -186,10 +191,12 @@ protected: // ScintillaBase subclass needs access to much of Editor
virtual void SetVerticalScrollPos() = 0;
virtual void SetHorizontalScrollPos() = 0;
virtual bool ModifyScrollBars(int nMax, int nPage) = 0;
virtual void ReconfigureScrollBars();
void SetScrollBarsTo(PRectangle rsClient);
void SetScrollBars();
virtual void AddChar(char ch);
void AddChar(char ch);
virtual void AddCharUTF(char *s, unsigned int len);
void ClearSelection();
void ClearAll();
void Cut();
@@ -207,7 +214,7 @@ protected: // ScintillaBase subclass needs access to much of Editor
virtual void NotifyChange() = 0;
virtual void NotifyFocus(bool focus);
virtual void NotifyParent(SCNotification scn) = 0;
virtual void NotifyStyleNeeded(int endStyleNeeded);
virtual void NotifyStyleToNeeded(int endStyleNeeded);
void NotifyChar(char ch);
void NotifySavePoint(bool isSavePoint);
void NotifyModifyAttempt();

View File

@@ -61,56 +61,58 @@ UINT KeyMap::Find(int key, int modifiers) {
}
KeyToCommand KeyMap::MapDefault[] = {
VK_DOWN, SCI_NORM, SCI_LINEDOWN,
VK_DOWN, SCI_SHIFT, SCI_LINEDOWNEXTEND,
VK_UP, SCI_NORM, SCI_LINEUP,
VK_UP, SCI_SHIFT, SCI_LINEUPEXTEND,
VK_LEFT, SCI_NORM, SCI_CHARLEFT,
VK_LEFT, SCI_SHIFT, SCI_CHARLEFTEXTEND,
VK_LEFT, SCI_CTRL, SCI_WORDLEFT,
VK_LEFT, SCI_CSHIFT, SCI_WORDLEFTEXTEND,
VK_RIGHT, SCI_NORM, SCI_CHARRIGHT,
VK_RIGHT, SCI_SHIFT, SCI_CHARRIGHTEXTEND,
VK_RIGHT, SCI_CTRL, SCI_WORDRIGHT,
VK_RIGHT, SCI_CSHIFT, SCI_WORDRIGHTEXTEND,
VK_HOME, SCI_NORM, SCI_VCHOME,
VK_HOME, SCI_SHIFT, SCI_VCHOMEEXTEND,
VK_HOME, SCI_CTRL, SCI_DOCUMENTSTART,
VK_HOME, SCI_CSHIFT, SCI_DOCUMENTSTARTEXTEND,
VK_END, SCI_NORM, SCI_LINEEND,
VK_END, SCI_SHIFT, SCI_LINEENDEXTEND,
VK_END, SCI_CTRL, SCI_DOCUMENTEND,
VK_END, SCI_CSHIFT, SCI_DOCUMENTENDEXTEND,
VK_PRIOR, SCI_NORM, SCI_PAGEUP,
VK_PRIOR, SCI_SHIFT, SCI_PAGEUPEXTEND,
VK_NEXT, SCI_NORM, SCI_PAGEDOWN,
VK_NEXT, SCI_SHIFT, SCI_PAGEDOWNEXTEND,
VK_DELETE, SCI_NORM, WM_CLEAR,
VK_DELETE, SCI_SHIFT, WM_CUT,
VK_DELETE, SCI_CTRL, SCI_DELWORDRIGHT,
VK_INSERT, SCI_NORM, SCI_EDITTOGGLEOVERTYPE,
VK_INSERT, SCI_SHIFT, WM_PASTE,
VK_INSERT, SCI_CTRL, WM_COPY,
VK_ESCAPE, SCI_NORM, SCI_CANCEL,
VK_BACK, SCI_NORM, SCI_DELETEBACK,
VK_BACK, SCI_CTRL, SCI_DELWORDLEFT,
'Z', SCI_CTRL, WM_UNDO,
'Y', SCI_CTRL, SCI_REDO,
'X', SCI_CTRL, WM_CUT,
'C', SCI_CTRL, WM_COPY,
'V', SCI_CTRL, WM_PASTE,
'A', SCI_CTRL, SCI_SELECTALL,
VK_TAB, SCI_NORM, SCI_TAB,
VK_TAB, SCI_SHIFT, SCI_BACKTAB,
VK_RETURN, SCI_NORM, SCI_NEWLINE,
VK_ADD, SCI_CTRL, SCI_ZOOMIN,
VK_SUBTRACT, SCI_CTRL, SCI_ZOOMOUT,
{VK_DOWN, SCI_NORM, SCI_LINEDOWN},
{VK_DOWN, SCI_SHIFT, SCI_LINEDOWNEXTEND},
{VK_DOWN, SCI_CTRL, SCI_LINESCROLLDOWN},
{VK_UP, SCI_NORM, SCI_LINEUP},
{VK_UP, SCI_SHIFT, SCI_LINEUPEXTEND},
{VK_UP, SCI_CTRL, SCI_LINESCROLLUP},
{VK_LEFT, SCI_NORM, SCI_CHARLEFT},
{VK_LEFT, SCI_SHIFT, SCI_CHARLEFTEXTEND},
{VK_LEFT, SCI_CTRL, SCI_WORDLEFT},
{VK_LEFT, SCI_CSHIFT, SCI_WORDLEFTEXTEND},
{VK_RIGHT, SCI_NORM, SCI_CHARRIGHT},
{VK_RIGHT, SCI_SHIFT, SCI_CHARRIGHTEXTEND},
{VK_RIGHT, SCI_CTRL, SCI_WORDRIGHT},
{VK_RIGHT, SCI_CSHIFT, SCI_WORDRIGHTEXTEND},
{VK_HOME, SCI_NORM, SCI_VCHOME},
{VK_HOME, SCI_SHIFT, SCI_VCHOMEEXTEND},
{VK_HOME, SCI_CTRL, SCI_DOCUMENTSTART},
{VK_HOME, SCI_CSHIFT, SCI_DOCUMENTSTARTEXTEND},
{VK_END, SCI_NORM, SCI_LINEEND},
{VK_END, SCI_SHIFT, SCI_LINEENDEXTEND},
{VK_END, SCI_CTRL, SCI_DOCUMENTEND},
{VK_END, SCI_CSHIFT, SCI_DOCUMENTENDEXTEND},
{VK_PRIOR, SCI_NORM, SCI_PAGEUP},
{VK_PRIOR, SCI_SHIFT, SCI_PAGEUPEXTEND},
{VK_NEXT, SCI_NORM, SCI_PAGEDOWN},
{VK_NEXT, SCI_SHIFT, SCI_PAGEDOWNEXTEND},
{VK_DELETE, SCI_NORM, WM_CLEAR},
{VK_DELETE, SCI_SHIFT, WM_CUT},
{VK_DELETE, SCI_CTRL, SCI_DELWORDRIGHT},
{VK_INSERT, SCI_NORM, SCI_EDITTOGGLEOVERTYPE},
{VK_INSERT, SCI_SHIFT, WM_PASTE},
{VK_INSERT, SCI_CTRL, WM_COPY},
{VK_ESCAPE, SCI_NORM, SCI_CANCEL},
{VK_BACK, SCI_NORM, SCI_DELETEBACK},
{VK_BACK, SCI_CTRL, SCI_DELWORDLEFT},
{'Z', SCI_CTRL, WM_UNDO},
{'Y', SCI_CTRL, SCI_REDO},
{'X', SCI_CTRL, WM_CUT},
{'C', SCI_CTRL, WM_COPY},
{'V', SCI_CTRL, WM_PASTE},
{'A', SCI_CTRL, SCI_SELECTALL},
{VK_TAB, SCI_NORM, SCI_TAB},
{VK_TAB, SCI_SHIFT, SCI_BACKTAB},
{VK_RETURN, SCI_NORM, SCI_NEWLINE},
{VK_ADD, SCI_CTRL, SCI_ZOOMIN},
{VK_SUBTRACT, SCI_CTRL, SCI_ZOOMOUT},
//'L', SCI_CTRL, SCI_FORMFEED,
'L', SCI_CTRL, SCI_LINECUT,
'L', SCI_CSHIFT, SCI_LINEDELETE,
'T', SCI_CTRL, SCI_LINETRANSPOSE,
'U', SCI_CTRL, SCI_LOWERCASE,
'U', SCI_CSHIFT, SCI_UPPERCASE,
0,0,0,
{'L', SCI_CTRL, SCI_LINECUT},
{'L', SCI_CSHIFT, SCI_LINEDELETE},
{'T', SCI_CTRL, SCI_LINETRANSPOSE},
{'U', SCI_CTRL, SCI_LOWERCASE},
{'U', SCI_CSHIFT, SCI_UPPERCASE},
{0,0,0},
};

View File

@@ -26,7 +26,7 @@ LexerModule::LexerModule(int language_, LexerFunction fn_) :
}
void LexerModule::Colourise(unsigned int startPos, int lengthDoc, int initStyle,
int language, WordList *keywordlists[], StylingContext &styler) {
int language, WordList *keywordlists[], Accessor &styler) {
LexerModule *lm = base;
while (lm) {
if (lm->language == language) {
@@ -43,5 +43,3 @@ void LexerModule::Colourise(unsigned int startPos, int lengthDoc, int initStyle,
styler.ColourTo(startPos + lengthDoc - 1, 0);
}
}

View File

@@ -17,7 +17,7 @@
#include "Scintilla.h"
#include "SciLexer.h"
static bool classifyWordCpp(unsigned int start, unsigned int end, WordList &keywords, StylingContext &styler) {
static bool classifyWordCpp(unsigned int start, unsigned int end, WordList &keywords, Accessor &styler) {
char s[100];
bool wordIsNumber = isdigit(styler[start]) || (styler[start] == '.');
bool wordIsUUID = false;
@@ -39,38 +39,47 @@ static bool classifyWordCpp(unsigned int start, unsigned int end, WordList &keyw
}
static void ColouriseCppDoc(unsigned int startPos, int length, int initStyle, WordList *keywordlists[],
StylingContext &styler) {
Accessor &styler) {
WordList &keywords = *keywordlists[0];
styler.StartAt(startPos);
bool fold = styler.GetPropSet().GetInt("fold");
bool fold = styler.GetPropertyInt("fold");
int lineCurrent = styler.GetLine(startPos);
int levelPrev = styler.LevelAt(lineCurrent) & SC_FOLDLEVELNUMBERMASK;
int levelCurrent = levelPrev;
int state = initStyle;
if (state == SCE_C_STRINGEOL) // Does not leak onto next line
state = SCE_C_DEFAULT;
char chPrev = ' ';
char chNext = styler[startPos];
unsigned int lengthDoc = startPos + length;
int visChars = 0;
styler.StartSegment(startPos);
bool lastWordWasUUID = false;
for (unsigned int i = startPos; i <= lengthDoc; i++) {
for (unsigned int i = startPos; i < lengthDoc; i++) {
char ch = chNext;
chNext = styler.SafeGetCharAt(i + 1);
if ((fold) && ((ch == '\r' && chNext != '\n') || (ch == '\n'))) {
int lev = levelPrev;
if (visChars == 0)
lev |= SC_FOLDLEVELWHITEFLAG;
if ((levelCurrent > levelPrev) && (visChars > 0))
lev |= SC_FOLDLEVELHEADERFLAG;
styler.SetLevel(lineCurrent, lev);
lineCurrent++;
visChars = 0;
levelPrev = levelCurrent;
if ((ch == '\r' && chNext != '\n') || (ch == '\n')) {
// End of line
if (state == SCE_C_STRINGEOL) {
styler.ColourTo(i, state);
state = SCE_C_DEFAULT;
}
if (fold) {
int lev = levelPrev;
if (visChars == 0)
lev |= SC_FOLDLEVELWHITEFLAG;
if ((levelCurrent > levelPrev) && (visChars > 0))
lev |= SC_FOLDLEVELHEADERFLAG;
styler.SetLevel(lineCurrent, lev);
lineCurrent++;
visChars = 0;
levelPrev = levelCurrent;
}
}
if (!isspace(ch))
visChars++;
@@ -82,12 +91,6 @@ static void ColouriseCppDoc(unsigned int startPos, int length, int initStyle, Wo
continue;
}
if (state == SCE_C_STRINGEOL) {
if (ch != '\r' && ch != '\n') {
styler.ColourTo(i-1, state);
state = SCE_C_DEFAULT;
}
}
if (state == SCE_C_DEFAULT) {
if (iswordstart(ch)) {
styler.ColourTo(i-1, state);
@@ -148,7 +151,7 @@ static void ColouriseCppDoc(unsigned int startPos, int length, int initStyle, Wo
}
} else {
if (state == SCE_C_PREPROCESSOR) {
if ((ch == '\r' || ch == '\n') && (chPrev != '\\')) {
if ((ch == '\r' || ch == '\n') && !(chPrev == '\\' || chPrev == '\r')) {
styler.ColourTo(i-1, state);
state = SCE_C_DEFAULT;
}
@@ -163,7 +166,7 @@ static void ColouriseCppDoc(unsigned int startPos, int length, int initStyle, Wo
}
} else if (state == SCE_C_COMMENTDOC) {
if (ch == '/' && chPrev == '*') {
if (((i > styler.GetStartSegment() + 3) || (
if (((i > styler.GetStartSegment() + 2) || (
(initStyle == SCE_C_COMMENTDOC) &&
(styler.GetStartSegment() == static_cast<unsigned int>(startPos))))) {
styler.ColourTo(i, state);
@@ -177,7 +180,7 @@ static void ColouriseCppDoc(unsigned int startPos, int length, int initStyle, Wo
}
} else if (state == SCE_C_STRING) {
if ((ch == '\r' || ch == '\n') && (chPrev != '\\')) {
styler.ColourTo(i-1, state);
styler.ColourTo(i-1, SCE_C_STRINGEOL);
state = SCE_C_STRINGEOL;
} else if (ch == '\\') {
if (chNext == '\"' || chNext == '\'' || chNext == '\\') {
@@ -194,7 +197,7 @@ static void ColouriseCppDoc(unsigned int startPos, int length, int initStyle, Wo
}
} else if (state == SCE_C_CHARACTER) {
if ((ch == '\r' || ch == '\n') && (chPrev != '\\')) {
styler.ColourTo(i-1, state);
styler.ColourTo(i-1, SCE_C_STRINGEOL);
state = SCE_C_STRINGEOL;
} else if (ch == '\\') {
if (chNext == '\"' || chNext == '\'' || chNext == '\\') {

View File

@@ -18,11 +18,11 @@
#include "SciLexer.h"
enum { eScriptNone, eScriptJS, eScriptVBS, eScriptPython };
static int segIsScriptingIndicator(StylingContext &styler, unsigned int start, unsigned int end, int prevValue) {
static int segIsScriptingIndicator(Accessor &styler, unsigned int start, unsigned int end, int prevValue) {
char s[100];
s[0] = '\0';
for (unsigned int i = 0; i < end - start + 1 && i < 30; i++) {
s[i] = tolower(styler[start + i]);
s[i] = static_cast<char>(tolower(styler[start + i]));
s[i + 1] = '\0';
}
//Platform::DebugPrintf("Scripting indicator [%s]\n", s);
@@ -38,7 +38,7 @@ static int segIsScriptingIndicator(StylingContext &styler, unsigned int start, u
return prevValue;
}
static void classifyAttribHTML(unsigned int start, unsigned int end, WordList &keywords, StylingContext &styler) {
static void classifyAttribHTML(unsigned int start, unsigned int end, WordList &keywords, Accessor &styler) {
bool wordIsNumber = isdigit(styler[start]) || (styler[start] == '.') ||
(styler[start] == '-') || (styler[start] == '#');
char chAttr = SCE_H_ATTRIBUTEUNKNOWN;
@@ -48,7 +48,7 @@ static void classifyAttribHTML(unsigned int start, unsigned int end, WordList &k
char s[100];
s[0] = '\0';
for (unsigned int i = 0; i < end - start + 1 && i < 30; i++) {
s[i] = tolower(styler[start + i]);
s[i] = static_cast<char>(tolower(styler[start + i]));
s[i + 1] = '\0';
}
if (keywords.InList(s))
@@ -58,14 +58,14 @@ static void classifyAttribHTML(unsigned int start, unsigned int end, WordList &k
}
static int classifyTagHTML(unsigned int start, unsigned int end,
WordList &keywords, StylingContext &styler) {
WordList &keywords, Accessor &styler) {
char s[100];
// Copy after the '<'
unsigned int i = 0;
for (unsigned int cPos=start; cPos <= end && i < 30; cPos++) {
char ch = styler[cPos];
if (ch != '<')
s[i++] = tolower(ch);
s[i++] = static_cast<char>(tolower(ch));
}
s[i] = '\0';
char chAttr = SCE_H_TAGUNKNOWN;
@@ -86,7 +86,7 @@ static int classifyTagHTML(unsigned int start, unsigned int end,
}
static void classifyWordHTJS(unsigned int start, unsigned int end,
WordList &keywords, StylingContext &styler) {
WordList &keywords, Accessor &styler) {
char s[100];
bool wordIsNumber = isdigit(styler[start]) || (styler[start] == '.');
for (unsigned int i = 0; i < end - start + 1 && i < 30; i++) {
@@ -104,7 +104,7 @@ static void classifyWordHTJS(unsigned int start, unsigned int end,
}
static void classifyWordHTJSA(unsigned int start, unsigned int end,
WordList &keywords, StylingContext &styler) {
WordList &keywords, Accessor &styler) {
char s[100];
bool wordIsNumber = isdigit(styler[start]) || (styler[start] == '.');
for (unsigned int i = 0; i < end - start + 1 && i < 30; i++) {
@@ -121,11 +121,11 @@ static void classifyWordHTJSA(unsigned int start, unsigned int end,
styler.ColourTo(end, chAttr);
}
static int classifyWordHTVB(unsigned int start, unsigned int end, WordList &keywords, StylingContext &styler) {
static int classifyWordHTVB(unsigned int start, unsigned int end, WordList &keywords, Accessor &styler) {
char s[100];
bool wordIsNumber = isdigit(styler[start]) || (styler[start] == '.');
for (unsigned int i = 0; i < end - start + 1 && i < 30; i++) {
s[i] = tolower(styler[start + i]);
s[i] = static_cast<char>(tolower(styler[start + i]));
s[i + 1] = '\0';
}
char chAttr = SCE_HB_IDENTIFIER;
@@ -145,11 +145,11 @@ static int classifyWordHTVB(unsigned int start, unsigned int end, WordList &keyw
return SCE_HB_DEFAULT;
}
static int classifyWordHTVBA(unsigned int start, unsigned int end, WordList &keywords, StylingContext &styler) {
static int classifyWordHTVBA(unsigned int start, unsigned int end, WordList &keywords, Accessor &styler) {
char s[100];
bool wordIsNumber = isdigit(styler[start]) || (styler[start] == '.');
for (unsigned int i = 0; i < end - start + 1 && i < 30; i++) {
s[i] = tolower(styler[start + i]);
s[i] = static_cast<char>(tolower(styler[start + i]));
s[i + 1] = '\0';
}
char chAttr = SCE_HBA_IDENTIFIER;
@@ -169,7 +169,7 @@ static int classifyWordHTVBA(unsigned int start, unsigned int end, WordList &key
return SCE_HBA_DEFAULT;
}
static void classifyWordHTPy(unsigned int start, unsigned int end, WordList &keywords, StylingContext &styler, char *prevWord) {
static void classifyWordHTPy(unsigned int start, unsigned int end, WordList &keywords, Accessor &styler, char *prevWord) {
char s[100];
bool wordIsNumber = isdigit(styler[start]);
for (unsigned int i = 0; i < end - start + 1 && i < 30; i++) {
@@ -189,7 +189,7 @@ static void classifyWordHTPy(unsigned int start, unsigned int end, WordList &key
strcpy(prevWord, s);
}
static void classifyWordHTPyA(unsigned int start, unsigned int end, WordList &keywords, StylingContext &styler, char *prevWord) {
static void classifyWordHTPyA(unsigned int start, unsigned int end, WordList &keywords, Accessor &styler, char *prevWord) {
char s[100];
bool wordIsNumber = isdigit(styler[start]);
for (unsigned int i = 0; i < end - start + 1 && i < 30; i++) {
@@ -226,7 +226,7 @@ static bool isLineEnd(char ch) {
}
static void ColouriseHyperTextDoc(unsigned int startPos, int length, int initStyle, WordList *keywordlists[],
StylingContext &styler) {
Accessor &styler) {
WordList &keywords=*keywordlists[0];
WordList &keywords2=*keywordlists[1];
@@ -261,7 +261,7 @@ static void ColouriseHyperTextDoc(unsigned int startPos, int length, int initSty
char chPrev2 = ' ';
styler.StartSegment(startPos);
int lengthDoc = startPos + length;
for (int i = startPos; i <= lengthDoc; i++) {
for (int i = startPos; i < lengthDoc; i++) {
char ch = styler[i];
char chNext = styler.SafeGetCharAt(i + 1);
char chNext2 = styler.SafeGetCharAt(i + 2);

View File

@@ -17,7 +17,7 @@
#include "Scintilla.h"
#include "SciLexer.h"
static void ColouriseBatchLine(char *lineBuffer, int endLine, StylingContext &styler) {
static void ColouriseBatchLine(char *lineBuffer, int endLine, Accessor &styler) {
if (0 == strncmp(lineBuffer, "REM", 3)) {
styler.ColourTo(endLine, 1);
} else if (0 == strncmp(lineBuffer, "rem", 3)) {
@@ -33,7 +33,7 @@ static void ColouriseBatchLine(char *lineBuffer, int endLine, StylingContext &st
}
}
static void ColouriseBatchDoc(unsigned int startPos, int length, int, WordList *[], StylingContext &styler) {
static void ColouriseBatchDoc(unsigned int startPos, int length, int, WordList *[], Accessor &styler) {
char lineBuffer[1024];
styler.StartAt(startPos);
styler.StartSegment(startPos);
@@ -49,7 +49,7 @@ static void ColouriseBatchDoc(unsigned int startPos, int length, int, WordList *
ColouriseBatchLine(lineBuffer, startPos + length, styler);
}
static void ColourisePropsLine(char *lineBuffer, int lengthLine, int startLine, int endPos, StylingContext &styler) {
static void ColourisePropsLine(char *lineBuffer, int lengthLine, int startLine, int endPos, Accessor &styler) {
int i = 0;
while (isspace(lineBuffer[i]) && (i < lengthLine)) // Skip initial spaces
i++;
@@ -75,7 +75,7 @@ static void ColourisePropsLine(char *lineBuffer, int lengthLine, int startLine,
}
}
static void ColourisePropsDoc(unsigned int startPos, int length, int, WordList *[], StylingContext &styler) {
static void ColourisePropsDoc(unsigned int startPos, int length, int, WordList *[], Accessor &styler) {
char lineBuffer[1024];
styler.StartAt(startPos);
styler.StartSegment(startPos);
@@ -96,7 +96,7 @@ static void ColourisePropsDoc(unsigned int startPos, int length, int, WordList *
ColourisePropsLine(lineBuffer, linePos, startLine, startPos + length, styler);
}
static void ColouriseMakeLine(char *lineBuffer, int lengthLine, int endPos, StylingContext &styler) {
static void ColouriseMakeLine(char *lineBuffer, int lengthLine, int endPos, Accessor &styler) {
int i = 0;
while (isspace(lineBuffer[i]) && (i < lengthLine))
i++;
@@ -107,7 +107,7 @@ static void ColouriseMakeLine(char *lineBuffer, int lengthLine, int endPos, Styl
}
}
static void ColouriseMakeDoc(unsigned int startPos, int length, int, WordList *[], StylingContext &styler) {
static void ColouriseMakeDoc(unsigned int startPos, int length, int, WordList *[], Accessor &styler) {
char lineBuffer[1024];
styler.StartAt(startPos);
styler.StartSegment(startPos);
@@ -123,7 +123,7 @@ static void ColouriseMakeDoc(unsigned int startPos, int length, int, WordList *[
ColouriseMakeLine(lineBuffer, linePos, startPos + length, styler);
}
static void ColouriseErrorListLine(char *lineBuffer, int lengthLine, int endPos, StylingContext &styler) {
static void ColouriseErrorListLine(char *lineBuffer, int lengthLine, int endPos, Accessor &styler) {
if (lineBuffer[0] == '>') {
// Command or return status
styler.ColourTo(endPos, 4);
@@ -158,7 +158,6 @@ static void ColouriseErrorListLine(char *lineBuffer, int lengthLine, int endPos,
state = 14;
} else if (state == 11 && lineBuffer[i] == ')') {
state = 12;
break;
} else if (state == 12 && lineBuffer[i] == ':') {
state = 13;
} else if (state == 14 && lineBuffer[i] == ')') {
@@ -170,7 +169,7 @@ static void ColouriseErrorListLine(char *lineBuffer, int lengthLine, int endPos,
}
if (state == 3) {
styler.ColourTo(endPos, 2);
} else if ((state == 14) || (state == 15)) {
} else if ((state == 13) || (state == 14) || (state == 15)) {
styler.ColourTo(endPos, 3);
} else {
styler.ColourTo(endPos, 0);
@@ -178,7 +177,7 @@ static void ColouriseErrorListLine(char *lineBuffer, int lengthLine, int endPos,
}
}
static void ColouriseErrorListDoc(unsigned int startPos, int length, int, WordList *[], StylingContext &styler) {
static void ColouriseErrorListDoc(unsigned int startPos, int length, int, WordList *[], Accessor &styler) {
char lineBuffer[1024];
styler.StartAt(startPos);
styler.StartSegment(startPos);

View File

@@ -31,7 +31,7 @@ inline bool isPerlOperator(char ch) {
return false;
}
static int classifyWordPerl(unsigned int start, unsigned int end, WordList &keywords, StylingContext &styler) {
static int classifyWordPerl(unsigned int start, unsigned int end, WordList &keywords, Accessor &styler) {
char s[100];
bool wordIsNumber = isdigit(styler[start]) || (styler[start] == '.');
for (unsigned int i = 0; i < end - start + 1 && i < 30; i++) {
@@ -54,7 +54,7 @@ static bool isEndVar(char ch) {
ch != '_' && ch != '\'';
}
static bool isMatch(StylingContext &styler, int lengthDoc, int pos, const char *val) {
static bool isMatch(Accessor &styler, int lengthDoc, int pos, const char *val) {
if ((pos + static_cast<int>(strlen(val))) >= lengthDoc) {
return false;
}
@@ -67,16 +67,6 @@ static bool isMatch(StylingContext &styler, int lengthDoc, int pos, const char *
return true;
}
static bool isOKQuote(char ch) {
if (isalnum(ch))
return false;
if (isspace(ch))
return false;
if (iscntrl(ch))
return false;
return true;
}
static char opposite(char ch) {
if (ch == '(')
return ')';
@@ -90,7 +80,7 @@ static char opposite(char ch) {
}
static void ColourisePerlDoc(unsigned int startPos, int length, int initStyle,
WordList *keywordlists[], StylingContext &styler) {
WordList *keywordlists[], Accessor &styler) {
// Lexer for perl often has to backtrack to start of current style to determine
// which characters are being used as quotes, how deeply nested is the
@@ -120,7 +110,7 @@ static void ColourisePerlDoc(unsigned int startPos, int length, int initStyle,
char chPrev = ' ';
char chNext = styler[startPos];
styler.StartSegment(startPos);
for (int i = startPos; i <= lengthDoc; i++) {
for (int i = startPos; i < lengthDoc; i++) {
char ch = chNext;
chNext = styler.SafeGetCharAt(i + 1);
char chNext2 = styler.SafeGetCharAt(i + 2);

View File

@@ -17,7 +17,7 @@
#include "Scintilla.h"
#include "SciLexer.h"
static void classifyWordPy(unsigned int start, unsigned int end, WordList &keywords, StylingContext &styler, char *prevWord) {
static void ClassifyWordPy(unsigned int start, unsigned int end, WordList &keywords, Accessor &styler, char *prevWord) {
char s[100];
bool wordIsNumber = isdigit(styler[start]);
for (unsigned int i = 0; i < end - start + 1 && i < 30; i++) {
@@ -37,56 +37,70 @@ static void classifyWordPy(unsigned int start, unsigned int end, WordList &keywo
strcpy(prevWord, s);
}
static bool IsPyComment(StylingContext &styler, int pos, int len) {
static bool IsPyComment(Accessor &styler, int pos, int len) {
return len>0 && styler[pos]=='#';
}
static void ColourisePyDoc(unsigned int startPos, int length, int initStyle,
WordList *keywordlists[], StylingContext &styler) {
WordList *keywordlists[], Accessor &styler) {
int lengthDoc = startPos + length;
// Backtrack to previous line in case need to fix its fold status or tab whinging
int lineCurrent = styler.GetLine(startPos);
if (startPos > 0) {
if (lineCurrent > 0) {
lineCurrent--;
startPos = styler.LineStart(lineCurrent);
}
}
// Python uses a different mask because bad indentation is marked by oring with 32
styler.StartAt(startPos, 127);
WordList &keywords = *keywordlists[0];
//Platform::DebugPrintf("Python coloured\n");
bool fold = styler.GetPropSet().GetInt("fold");
int whingeLevel = styler.GetPropSet().GetInt("tab.timmy.whinge.level");
bool fold = styler.GetPropertyInt("fold");
int whingeLevel = styler.GetPropertyInt("tab.timmy.whinge.level");
char prevWord[200];
prevWord[0] = '\0';
if (length == 0)
return ;
int lineCurrent = styler.GetLine(startPos);
int spaceFlags = 0;
// TODO: Need to check previous line for indentation for both folding and bad indentation
int indentCurrent = styler.IndentAmount(lineCurrent, &spaceFlags, IsPyComment);
int state = initStyle & 31;
int indentCurrent = styler.IndentAmount(lineCurrent, &spaceFlags, IsPyComment);
if ((state == SCE_P_TRIPLE) || (state == SCE_P_TRIPLEDOUBLE))
indentCurrent |= SC_FOLDLEVELWHITEFLAG;
char chPrev = ' ';
char chPrev2 = ' ';
char chNext = styler[startPos];
char chNext2 = styler[startPos];
styler.StartSegment(startPos);
int lengthDoc = startPos + length;
bool atStartLine = true;
for (int i = startPos; i <= lengthDoc; i++) {
for (int i = startPos; i < lengthDoc; i++) {
if (atStartLine) {
char chBad = static_cast<char>(64);
char chGood = static_cast<char>(0);
char chFlags = chGood;
if (whingeLevel == 1) {
styler.SetFlags((spaceFlags & wsInconsistent) ? 64 : 0, state);
chFlags = (spaceFlags & wsInconsistent) ? chBad : chGood;
} else if (whingeLevel == 2) {
styler.SetFlags((spaceFlags & wsSpaceTab) ? 64 : 0, state);
chFlags = (spaceFlags & wsSpaceTab) ? chBad : chGood;
} else if (whingeLevel == 3) {
styler.SetFlags((spaceFlags & wsSpace) ? 64 : 0, state);
chFlags = (spaceFlags & wsSpace) ? chBad : chGood;
} else if (whingeLevel == 4) {
styler.SetFlags((spaceFlags & wsTab) ? 64 : 0, state);
chFlags = (spaceFlags & wsTab) ? chBad : chGood;
}
styler.SetFlags(chFlags, static_cast<char>(state));
atStartLine = false;
}
char ch = chNext;
chNext = styler.SafeGetCharAt(i + 1);
chNext2 = styler.SafeGetCharAt(i + 2);
char chNext2 = styler.SafeGetCharAt(i + 2);
if ((ch == '\r' && chNext != '\n') || (ch == '\n') || (i == lengthDoc)) {
if ((state == SCE_P_DEFAULT) || (state == SCE_P_TRIPLE) || (state == SCE_P_TRIPLEDOUBLE)) {
@@ -97,6 +111,8 @@ static void ColourisePyDoc(unsigned int startPos, int length, int initStyle,
int lev = indentCurrent;
int indentNext = styler.IndentAmount(lineCurrent + 1, &spaceFlags, IsPyComment);
if ((state == SCE_P_TRIPLE) || (state == SCE_P_TRIPLEDOUBLE))
indentNext |= SC_FOLDLEVELWHITEFLAG;
if (!(indentCurrent & SC_FOLDLEVELWHITEFLAG)) {
// Only non whitespace lines can be headers
if ((indentCurrent & SC_FOLDLEVELNUMBERMASK) < (indentNext & SC_FOLDLEVELNUMBERMASK)) {
@@ -167,7 +183,7 @@ static void ColourisePyDoc(unsigned int startPos, int length, int initStyle,
}
} else if (state == SCE_P_WORD) {
if (!iswordchar(ch)) {
classifyWordPy(styler.GetStartSegment(), i - 1, keywords, styler, prevWord);
ClassifyWordPy(styler.GetStartSegment(), i - 1, keywords, styler, prevWord);
state = SCE_P_DEFAULT;
if (ch == '#') {
state = chNext == '#' ? SCE_P_COMMENTBLOCK : SCE_P_COMMENTLINE;
@@ -245,7 +261,7 @@ static void ColourisePyDoc(unsigned int startPos, int length, int initStyle,
chPrev = ch;
}
if (state == SCE_P_WORD) {
classifyWordPy(styler.GetStartSegment(), lengthDoc, keywords, styler, prevWord);
ClassifyWordPy(styler.GetStartSegment(), lengthDoc, keywords, styler, prevWord);
} else {
styler.ColourTo(lengthDoc, state);
}

View File

@@ -17,11 +17,11 @@
#include "Scintilla.h"
#include "SciLexer.h"
static void classifyWordSQL(unsigned int start, unsigned int end, WordList &keywords, StylingContext &styler) {
static void classifyWordSQL(unsigned int start, unsigned int end, WordList &keywords, Accessor &styler) {
char s[100];
bool wordIsNumber = isdigit(styler[start]) || (styler[start] == '.');
for (unsigned int i = 0; i < end - start + 1 && i < 30; i++) {
s[i] = toupper(styler[start + i]);
s[i] = static_cast<char>(toupper(styler[start + i]));
s[i + 1] = '\0';
}
char chAttr = SCE_C_IDENTIFIER;
@@ -35,29 +35,27 @@ static void classifyWordSQL(unsigned int start, unsigned int end, WordList &keyw
}
static void ColouriseSQLDoc(unsigned int startPos, int length,
int initStyle, WordList *keywordlists[], StylingContext &styler) {
int initStyle, WordList *keywordlists[], Accessor &styler) {
WordList &keywords = *keywordlists[0];
styler.StartAt(startPos);
bool fold = styler.GetPropSet().GetInt("fold");
bool fold = styler.GetPropertyInt("fold");
int lineCurrent = styler.GetLine(startPos);
int spaceFlags = 0;
int indentCurrent = 0;
int state = initStyle;
char chPrev = ' ';
char chNext = styler[startPos];
styler.StartSegment(startPos);
unsigned int lengthDoc = startPos + length;
bool prevCr = false;
for (unsigned int i = startPos; i <= lengthDoc; i++) {
for (unsigned int i = startPos; i < lengthDoc; i++) {
char ch = chNext;
chNext = styler.SafeGetCharAt(i + 1);
if ((ch == '\r' && chNext != '\n') || (ch == '\n')) {
indentCurrent = styler.IndentAmount(lineCurrent, &spaceFlags);
int indentCurrent = styler.IndentAmount(lineCurrent, &spaceFlags);
int lev = indentCurrent;
if (!(indentCurrent & SC_FOLDLEVELWHITEFLAG)) {
// Only non whitespace lines can be headers

View File

@@ -17,12 +17,12 @@
#include "Scintilla.h"
#include "SciLexer.h"
static int classifyWordVB(unsigned int start, unsigned int end, WordList &keywords, StylingContext &styler) {
static int classifyWordVB(unsigned int start, unsigned int end, WordList &keywords, Accessor &styler) {
char s[100];
bool wordIsNumber = isdigit(styler[start]) || (styler[start] == '.');
for (unsigned int i = 0; i < end - start + 1 && i < 30; i++) {
s[i] = tolower(styler[start + i]);
s[i] = static_cast<char>(tolower(styler[start + i]));
s[i + 1] = '\0';
}
char chAttr = SCE_C_DEFAULT;
@@ -43,7 +43,7 @@ static int classifyWordVB(unsigned int start, unsigned int end, WordList &keywor
}
static void ColouriseVBDoc(unsigned int startPos, int length, int initStyle,
WordList *keywordlists[], StylingContext &styler) {
WordList *keywordlists[], Accessor &styler) {
WordList &keywords = *keywordlists[0];

View File

@@ -51,20 +51,6 @@ void LineMarker::Draw(Surface *surface, PRectangle &rc) {
} else if (markType == SC_MARK_PLUS) {
int armSize = dimOn2-2;
Point xpts[] = {
Point(centreX - armSize, centreY),
Point(centreX, centreY),
Point(centreX, centreY - armSize),
Point(centreX, centreY - armSize),
Point(centreX, centreY),
Point(centreX + armSize, centreY),
Point(centreX + armSize, centreY),
Point(centreX, centreY),
Point(centreX, centreY + armSize),
Point(centreX, centreY + armSize),
Point(centreX, centreY),
Point(centreX - armSize, centreY),
};
Point pts[] = {
Point(centreX - armSize, centreY - 1),
Point(centreX - 1, centreY - 1),
@@ -90,12 +76,6 @@ void LineMarker::Draw(Surface *surface, PRectangle &rc) {
Point(centreX + armSize, centreY +1),
Point(centreX - armSize, centreY + 1),
};
Point xpts[] = {
Point(centreX - armSize, centreY),
Point(centreX + armSize, centreY),
Point(centreX + armSize, centreY),
Point(centreX - armSize, centreY),
};
surface->Polygon(pts, sizeof(pts) / sizeof(pts[0]),
fore.allocated, back.allocated);

View File

@@ -39,7 +39,7 @@ static bool GetFullLine(const char *&fpc, int &lenData, char *s, int len) {
fpc++;
lenData--;
}
*s++ = '\0';
*s = '\0';
return true;
}
} else if ((ch == '\\') && (lenData > 0) && ((*fpc == '\r') || (*fpc == '\n'))) {
@@ -122,7 +122,7 @@ SString PropSet::Get(const char *key) {
int PropSet::GetInt(const char *key, int defaultValue) {
SString val = Get(key);
if (val.length())
return Get(key).value();
return val.value();
else
return defaultValue;
}
@@ -376,7 +376,7 @@ bool WordList::InList(const char *s) {
for (int i = 0; words[i][0]; i++)
len++;
SortWordList(words, len);
for (int k = 0; k < (sizeof(starts) / sizeof(starts[0])); k++)
for (unsigned int k = 0; k < (sizeof(starts) / sizeof(starts[0])); k++)
starts[k] = -1;
for (int l = len - 1; l >= 0; l--) {
unsigned char indexChar = words[l][0];

View File

@@ -15,6 +15,8 @@
#include "SciLexer.h"
#include "PropSet.h"
#include "Accessor.h"
#include "WindowAccessor.h"
#include "DocumentAccessor.h"
#include "KeyWords.h"
#endif
#include "ContractionState.h"
@@ -50,11 +52,11 @@ void ScintillaBase::RefreshColourPalette(Palette &pal, bool want) {
ct.RefreshColourPalette(pal, want);
}
void ScintillaBase::AddChar(char ch) {
void ScintillaBase::AddCharUTF(char *s, unsigned int len) {
bool acActiveBeforeCharAdded = ac.Active();
Editor::AddChar(ch);
Editor::AddCharUTF(s, len);
if (acActiveBeforeCharAdded)
AutoCompleteChanged(ch);
AutoCompleteChanged(s[0]);
}
void ScintillaBase::Command(int cmdId) {
@@ -276,7 +278,8 @@ void ScintillaBase::Colourise(int start, int end) {
end = lengthDoc;
int len = end - start;
StylingContext styler(wMain.GetID(), props);
//WindowAccessor styler(wMain.GetID(), props);
DocumentAccessor styler(pdoc, props);
int styleStart = 0;
if (start > 0)
@@ -288,7 +291,7 @@ void ScintillaBase::Colourise(int start, int end) {
}
#endif
void ScintillaBase::NotifyStyleNeeded(int endStyleNeeded) {
void ScintillaBase::NotifyStyleToNeeded(int endStyleNeeded) {
#ifdef SCI_LEXER
if (lexLanguage != SCLEX_CONTAINER) {
int endStyled = Platform::SendScintilla(wMain.GetID(), SCI_GETENDSTYLED, 0, 0);
@@ -298,7 +301,7 @@ void ScintillaBase::NotifyStyleNeeded(int endStyleNeeded) {
return;
}
#endif
Editor::NotifyStyleNeeded(endStyleNeeded);
Editor::NotifyStyleToNeeded(endStyleNeeded);
}
LRESULT ScintillaBase::WndProc(UINT iMessage, WPARAM wParam, LPARAM lParam) {
@@ -321,10 +324,21 @@ LRESULT ScintillaBase::WndProc(UINT iMessage, WPARAM wParam, LPARAM lParam) {
AutoCompleteCompleted();
break;
case SCI_AUTOCSETSEPARATOR:
ac.SetSeparator(wParam);
break;
case SCI_AUTOCGETSEPARATOR:
return ac.GetSeparator();
case SCI_AUTOCSTOPS:
ac.SetStopChars(reinterpret_cast<char *>(lParam));
break;
case SCI_AUTOCSELECT:
ac.Select(reinterpret_cast<char *>(lParam));
break;
case SCI_CALLTIPSHOW: {
AutoCompleteCancel();
if (!ct.wCallTip.Created()) {
@@ -384,7 +398,7 @@ LRESULT ScintillaBase::WndProc(UINT iMessage, WPARAM wParam, LPARAM lParam) {
break;
case SCI_SETKEYWORDS:
if ((wParam >= 0) && (wParam < numWordLists)) {
if (wParam < numWordLists) {
keyWordLists[wParam]->Clear();
keyWordLists[wParam]->Set(reinterpret_cast<const char *>(lParam));
}

View File

@@ -7,6 +7,9 @@
#define SCINTILLABASE_H
class ScintillaBase : public Editor {
// Private so ScintillaBase objects can not be copied
ScintillaBase(const ScintillaBase &) : Editor() {}
ScintillaBase &operator=(const ScintillaBase &) { return *this; }
protected:
// Enumeration of commands and child windows
enum {
@@ -42,7 +45,7 @@ protected:
virtual void RefreshColourPalette(Palette &pal, bool want);
virtual void AddChar(char ch);
virtual void AddCharUTF(char *s, unsigned int len);
void Command(int cmdId);
virtual int KeyCommand(UINT iMessage);
@@ -59,7 +62,7 @@ protected:
virtual void ButtonDown(Point pt, unsigned int curTime, bool shift, bool ctrl, bool alt);
virtual void NotifyStyleNeeded(int endStyleNeeded);
virtual void NotifyStyleToNeeded(int endStyleNeeded);
public:
// Public so scintilla_send_message can use it
virtual LRESULT WndProc(UINT iMessage, WPARAM wParam, LPARAM lParam);

View File

@@ -16,6 +16,18 @@ Style::Style() {
false, false, false);
}
Style::Style(const Style &source) {
Clear(Colour(0,0,0), Colour(0xff,0xff,0xff),
0, 0,
false, false, false);
fore.desired = source.fore.desired;
back.desired = source.back.desired;
bold = source.bold;
italic = source.italic;
size = source.size;
eolFilled = source.eolFilled;
}
Style::~Style() {
if (aliasOfDefaultFont)
font.SetID(0);
@@ -78,7 +90,7 @@ void Style::Realise(Surface &surface, int zoomLevel, Style *defaultStyle) {
font.SetID(0);
else
font.Release();
int deviceHeight = (sizeZoomed * surface.LogPixelsY()) / 72;
int deviceHeight = surface.DeviceHeightFont(sizeZoomed);
aliasOfDefaultFont = defaultStyle &&
(EquivalentFontTo(defaultStyle) || !fontName);
if (aliasOfDefaultFont) {
@@ -99,5 +111,3 @@ void Style::Realise(Surface &surface, int zoomLevel, Style *defaultStyle) {
aveCharWidth = surface.AverageCharWidth(font);
spaceWidth = surface.WidthChar(font, ' ');
}

View File

@@ -26,6 +26,7 @@ public:
unsigned int spaceWidth;
Style();
Style(const Style &source);
~Style();
Style &operator=(const Style &source);
void Clear(Colour fore_, Colour back_,

View File

@@ -0,0 +1,77 @@
// UniConversion.h - functions to handle UFT-8 and UCS-2 strings
// Copyright 1998-2000 by Neil Hodgson <neilh@scintilla.org>
// The License.txt file describes the conditions under which this software may be distributed.
#include <stdlib.h>
#include "UniConversion.h"
unsigned int UTF8Length(const wchar_t *uptr, unsigned int tlen) {
unsigned int len = 0;
for (unsigned int i = 0; i < tlen && uptr[i]; i++) {
unsigned int uch = uptr[i];
if (uch < 0x80)
len++;
else if (uch < 0x800)
len+=2;
else
len +=3;
}
return len;
}
void UTF8FromUCS2(const wchar_t *uptr, unsigned int tlen, char *putf, unsigned int len) {
int k = 0;
for (unsigned int i = 0; i < tlen && uptr[i]; i++) {
unsigned int uch = uptr[i];
if (uch < 0x80) {
putf[k++] = static_cast<char>(uch);
} else if (uch < 0x800) {
putf[k++] = static_cast<char>(0xC0 | (uch >> 6));
putf[k++] = static_cast<char>(0x80 | (uch & 0x3f));
} else {
putf[k++] = static_cast<char>(0xE0 | (uch >> 12));
putf[k++] = static_cast<char>(0x80 | ((uch >> 6) & 0x3f));
putf[k++] = static_cast<char>(0x80 | (uch & 0x3f));
}
}
putf[len] = '\0';
}
unsigned int UCS2Length(const char *s, unsigned int len) {
unsigned int ulen = 0;
for (unsigned int i=0;i<len;i++) {
unsigned char ch = static_cast<unsigned char>(s[i]);
if ((ch < 0x80) || (ch > (0x80 + 0x40)))
ulen++;
}
return ulen;
}
unsigned int UCS2FromUTF8(const char *s, unsigned int len, wchar_t *tbuf, unsigned int tlen) {
#ifdef USE_API
return ::MultiByteToWideChar(CP_UTF8, 0, s, len, tbuf, tlen);
#else
unsigned int ui=0;
const unsigned char *us = reinterpret_cast<const unsigned char *>(s);
unsigned int i=0;
while ((i<len) && (ui<tlen)) {
unsigned char ch = us[i++];
if (ch < 0x80) {
tbuf[ui] = ch;
} else if (ch < 0x80 + 0x40 + 0x20) {
tbuf[ui] = static_cast<wchar_t>((ch & 0x1F) << 6);
ch = us[i++];
tbuf[ui] = static_cast<wchar_t>(tbuf[ui] + (ch & 0x7F));
} else {
tbuf[ui] = static_cast<wchar_t>((ch & 0xF) << 12);
ch = us[i++];
tbuf[ui] = static_cast<wchar_t>(tbuf[ui] + ((ch & 0x7F) << 6));
ch = us[i++];
tbuf[ui] = static_cast<wchar_t>(tbuf[ui] + (ch & 0x7F));
}
ui++;
}
return ui;
#endif
}

View File

@@ -0,0 +1,9 @@
// UniConversion.h - functions to handle UFT-8 and UCS-2 strings
// Copyright 1998-2000 by Neil Hodgson <neilh@scintilla.org>
// The License.txt file describes the conditions under which this software may be distributed.
unsigned int UTF8Length(const wchar_t *uptr, unsigned int tlen);
void UTF8FromUCS2(const wchar_t *uptr, unsigned int tlen, char *putf, unsigned int len);
unsigned int UCS2Length(const char *s, unsigned int len);
unsigned int UCS2FromUTF8(const char *s, unsigned int len, wchar_t *tbuf, unsigned int tlen);

View File

@@ -225,5 +225,3 @@ void ViewStyle::ClearStyles() {
void ViewStyle::SetStyleFontName(int styleIndex, const char *name) {
styles[styleIndex].fontName = fontNames.Save(name);
}

View File

@@ -11,20 +11,29 @@
#include "PropSet.h"
#include "Accessor.h"
#include "WindowAccessor.h"
#include "Scintilla.h"
bool Accessor::InternalIsLeadByte(char ch) {
WindowAccessor::~WindowAccessor() {
}
bool WindowAccessor::InternalIsLeadByte(char ch) {
#if PLAT_GTK
// TODO: support DBCS under GTK+
return false;
#elif PLAT_WIN
return IsDBCSLeadByteEx(codePage, ch);
if (SC_CP_UTF8 == codePage)
// For lexing, all characters >= 0x80 are treated the
// same so none is considered a lead byte.
return false;
else
return IsDBCSLeadByteEx(codePage, ch);
#elif PLAT_WX
return false;
#endif
}
void Accessor::Fill(int position) {
void WindowAccessor::Fill(int position) {
if (lenDoc == -1)
lenDoc = Platform::SendScintilla(id, WM_GETTEXTLENGTH, 0, 0);
startPos = position - slopSize;
@@ -40,46 +49,46 @@ void Accessor::Fill(int position) {
Platform::SendScintilla(id, EM_GETTEXTRANGE, 0, reinterpret_cast<LPARAM>(&tr));
}
char Accessor::StyleAt(int position) {
char WindowAccessor::StyleAt(int position) {
return static_cast<char>(Platform::SendScintilla(
id, SCI_GETSTYLEAT, position, 0));
}
int Accessor::GetLine(int position) {
int WindowAccessor::GetLine(int position) {
return Platform::SendScintilla(id, EM_LINEFROMCHAR, position, 0);
}
int Accessor::LineStart(int line) {
int WindowAccessor::LineStart(int line) {
return Platform::SendScintilla(id, EM_LINEINDEX, line, 0);
}
int Accessor::LevelAt(int line) {
int WindowAccessor::LevelAt(int line) {
return Platform::SendScintilla(id, SCI_GETFOLDLEVEL, line, 0);
}
int Accessor::Length() {
int WindowAccessor::Length() {
if (lenDoc == -1)
lenDoc = Platform::SendScintilla(id, WM_GETTEXTLENGTH, 0, 0);
return lenDoc;
}
int Accessor::GetLineState(int line) {
int WindowAccessor::GetLineState(int line) {
return Platform::SendScintilla(id, SCI_GETLINESTATE, line);
}
int Accessor::SetLineState(int line, int state) {
int WindowAccessor::SetLineState(int line, int state) {
return Platform::SendScintilla(id, SCI_SETLINESTATE, line, state);
}
void StylingContext::StartAt(unsigned int start, char chMask) {
void WindowAccessor::StartAt(unsigned int start, char chMask) {
Platform::SendScintilla(id, SCI_STARTSTYLING, start, chMask);
}
void StylingContext::StartSegment(unsigned int pos) {
void WindowAccessor::StartSegment(unsigned int pos) {
startSeg = pos;
}
void StylingContext::ColourTo(unsigned int pos, int chAttr) {
void WindowAccessor::ColourTo(unsigned int pos, int chAttr) {
// Only perform styling if non empty range
if (pos != startSeg - 1) {
if (pos < startSeg) {
@@ -96,22 +105,20 @@ void StylingContext::ColourTo(unsigned int pos, int chAttr) {
chFlags = 0;
chAttr |= chFlags;
for (unsigned int i = startSeg; i <= pos; i++) {
styleBuf[validLen++] = chAttr;
styleBuf[validLen++] = static_cast<char>(chAttr);
}
}
}
startSeg = pos+1;
}
int StylingContext::GetLine(int position) {
return Platform::SendScintilla(id, EM_LINEFROMCHAR, position, 0);
}
void StylingContext::SetLevel(int line, int level) {
void WindowAccessor::SetLevel(int line, int level) {
Platform::SendScintilla(id, SCI_SETFOLDLEVEL, line, level);
}
void StylingContext::Flush() {
void WindowAccessor::Flush() {
startPos = extremePosition;
lenDoc = -1;
if (validLen > 0) {
Platform::SendScintilla(id, SCI_SETSTYLINGEX, validLen,
reinterpret_cast<LPARAM>(styleBuf));
@@ -119,7 +126,7 @@ void StylingContext::Flush() {
}
}
int StylingContext::IndentAmount(int line, int *flags, PFNIsCommentLeader pfnIsCommentLeader) {
int WindowAccessor::IndentAmount(int line, int *flags, PFNIsCommentLeader pfnIsCommentLeader) {
int end = Length();
int spaceFlags = 0;

View File

@@ -116,7 +116,7 @@ wxStyledTextCtrl::~wxStyledTextCtrl() {
//----------------------------------------------------------------------
inline long wxStyledTextCtrl::SendMsg(int msg, long wp, long lp) {
long wxStyledTextCtrl::SendMsg(int msg, long wp, long lp) {
return m_swx->WndProc(msg, wp, lp);
}
@@ -146,8 +146,9 @@ wxString wxStyledTextCtrl::GetLine(int line) {
int len = GetLineLength(line);
char* buff = text.GetWriteBuf(len+1);
*((WORD*)buff) = len+1;
*((WORD*)buff) = len;
SendMsg(EM_GETLINE, line, (long)buff);
buff[len] = 0;
text.UngetWriteBuf();
return text;
}
@@ -426,16 +427,16 @@ int wxStyledTextCtrl::GetCurrentLine() {
}
wxString wxStyledTextCtrl::GetCurrentLineText(/*int* linePos*/) {
wxString wxStyledTextCtrl::GetCurrentLineText(int* linePos) {
wxString text;
int len = GetLineLength(GetCurrentLine());
char* buff = text.GetWriteBuf(len+1);
int pos = SendMsg(SCI_GETCURLINE, len+1, (long)buff);
int pos = SendMsg(SCI_GETCURLINE, len, (long)buff);
text.UngetWriteBuf();
/* if (linePos)
*linePos = pos; */
if (linePos)
*linePos = pos;
return text;
}
@@ -457,7 +458,7 @@ int wxStyledTextCtrl::LineFromPoint(wxPoint pt) {
wxPoint wxStyledTextCtrl::PointFromPosition(int pos) {
Point pt;
SendMsg(EM_POSFROMCHAR, pos, (long)&pt);
SendMsg(EM_POSFROMCHAR, (long)&pt, pos);
return wxPoint(pt.x, pt.y);
}
@@ -538,6 +539,27 @@ int wxStyledTextCtrl::GetSelectionType() {
}
int wxStyledTextCtrl::GetLinesOnScreen() {
return SendMsg(SCI_LINESONSCREEN);
}
bool wxStyledTextCtrl::IsSelectionRectangle() {
return SendMsg(SCI_SELECTIONISRECTANGLE) != 0;
}
void wxStyledTextCtrl::SetUseHorizontalScrollBar(bool use) {
SendMsg(SCI_SETHSCROLLBAR, use);
}
bool wxStyledTextCtrl::GetUseHorizontalScrollBar() {
return SendMsg(SCI_GETHSCROLLBAR) != 0;
}
//----------------------------------------------------------------------
@@ -645,6 +667,16 @@ void wxStyledTextCtrl::SetStyleBytes(int length, char* styleBytes) {
}
void wxStyledTextCtrl::SetLineState(int line, int value) {
SendMsg(SCI_SETLINESTATE, line, value);
}
int wxStyledTextCtrl::GetLineState(int line) {
return SendMsg(SCI_GETLINESTATE, line);
}
//----------------------------------------------------------------------
// Style Definition
@@ -905,11 +937,41 @@ void wxStyledTextCtrl::SetTabWidth(int numChars) {
}
void wxStyledTextCtrl::SetIndent(int numChars) {
SendMsg(SCI_SETINDENT, numChars);
}
void wxStyledTextCtrl::SetUseTabs(bool usetabs) {
SendMsg(SCI_SETUSETABS, usetabs);
}
void wxStyledTextCtrl::SetLineIndentation(int line, int indentation) {
SendMsg(SCI_SETLINEINDENTATION, line, indentation);
}
int wxStyledTextCtrl:: GetLineIndentation(int line) {
return SendMsg(SCI_GETLINEINDENTATION, line);
}
int wxStyledTextCtrl::GetLineIndentationPos(int line) {
return SendMsg(SCI_GETLINEINDENTPOSITION, line);
}
void wxStyledTextCtrl::SetWordChars(const wxString& wordChars) {
SendMsg(SCI_SETTABWIDTH, 0, (long)wordChars.c_str());
}
void wxStyledTextCtrl::SetUsePop(bool usepopup) {
SendMsg(SCI_USEPOPUP, usepopup);
}
//----------------------------------------------------------------------
// Brace highlighting
@@ -1053,6 +1115,21 @@ void wxStyledTextCtrl::AutoCompStopChars(const wxString& stopChars) {
}
void wxStyledTextCtrl::AutoCompSetSeparator(char separator) {
SendMsg(SCI_AUTOCSETSEPARATOR, separator);
}
char wxStyledTextCtrl::AutoCompGetSeparator() {
return SendMsg(SCI_AUTOCGETSEPARATOR);
}
void wxStyledTextCtrl::AutoCompSelect(const wxString& stringtoselect) {
SendMsg(SCI_AUTOCSELECT, (long)stringtoselect.c_str());
}
//----------------------------------------------------------------------
// Call tips

View File

@@ -130,7 +130,9 @@ enum {
wxSTC_CMD_LINEDELETE,
wxSTC_CMD_LINETRANSPOSE,
wxSTC_CMD_LOWERCASE,
wxSTC_CMD_UPPERCASE
wxSTC_CMD_UPPERCASE,
wxSTC_CMD_LINESCROLLDOWN,
wxSTC_CMD_LINESCROLLUP
};
@@ -253,7 +255,11 @@ public:
int GetLineStartPos(int line);
int GetLineLengthAtPos(int pos);
int GetLineLength(int line);
wxString GetCurrentLineText();
#ifdef SWIG
wxString GetCurrentLineText(int* OUTPUT);
#else
wxString GetCurrentLineText(int* linePos);
#endif
int GetCurrentLine();
int PositionFromPoint(wxPoint pt);
int LineFromPoint(wxPoint pt);
@@ -274,7 +280,10 @@ public:
void EnsureCaretVisible();
void SetCaretPolicy(int policy, int slop=0);
int GetSelectionType();
int GetLinesOnScreen();
bool IsSelectionRectangle();
void SetUseHorizontalScrollBar(bool use);
bool GetUseHorizontalScrollBar();
// Searching
@@ -303,6 +312,8 @@ public:
void StartStyling(int pos, int mask);
void SetStyleFor(int length, int style);
void SetStyleBytes(int length, char* styleBytes);
void SetLineState(int line, int value);
int GetLineState(int line);
// Style Definition
@@ -348,8 +359,15 @@ public:
// Other settings
void SetBufferedDraw(bool isBuffered);
void SetTabWidth(int numChars);
void SetIndent(int numChars);
void SetUseTabs(bool usetabs);
void SetLineIndentation(int line, int indentation);
int GetLineIndentation(int line);
int GetLineIndentationPos(int line);
void SetWordChars(const wxString& wordChars);
void SetUsePop(bool usepopup);
// Brace highlighting
void BraceHighlight(int pos1, int pos2);
@@ -387,7 +405,9 @@ public:
int AutoCompPosAtStart();
void AutoCompComplete();
void AutoCompStopChars(const wxString& stopChars);
void AutoCompSetSeparator(char separator);
char AutoCompGetSeparator();
void AutoCompSelect(const wxString& stringtoselect);
// Call tips
void CallTipShow(int pos, const wxString& text);

View File

@@ -23,16 +23,7 @@ HEADER_SUBDIR=stc
HEADERS=stc.h
OBJECTS=PlatWX.o ScintillaWX.o stc.o \
Accessor.o \
AutoComplete.o \
CallTip.o \
CellBuffer.o \
ContractionState.o \
Document.o \
Editor.o \
Indicator.o \
KeyMap.o \
KeyWords.o \
DocumentAccessor.o \
LexCPP.o \
LexHTML.o \
LexOthers.o \
@@ -40,11 +31,23 @@ OBJECTS=PlatWX.o ScintillaWX.o stc.o \
LexPython.o \
LexSQL.o \
LexVB.o \
LineMarker.o \
UniConversion.o \
WindowAccessor.o \
AutoComplete.o \
CallTip.o \
CellBuffer.o \
ContractionState.o \
Document.o \
Editor.o \
Indicator.o \
KeyMap.o \
KeyWords.o \
LineMarker.o \
PropSet.o \
ScintillaBase.o \
ScintillaBase.o \
Style.o \
ViewStyle.o
ViewStyle.o \
APPEXTRADEFS=-D__WX__ -DSCI_LEXER -I$(scintilla_dir)/src -I$(scintilla_dir)/include -I$(top_srcdir)/contrib/include

View File

@@ -196,6 +196,12 @@ int Surface::LogPixelsY() {
return hdc->GetPPI().y;
}
int Surface::DeviceHeightFont(int points) {
return points * LogPixelsY() / 72;
}
void Surface::MoveTo(int x_, int y_) {
x = x_;
y = y_;

View File

@@ -195,9 +195,8 @@ void ScintillaWX::NotifyParent(SCNotification scn) {
void ScintillaWX::Copy() {
if (currentPos != anchor) {
char* text = CopySelectionRange();
textDO.SetText(text);
wxTheClipboard->Open();
wxTheClipboard->SetData(&textDO);
wxTheClipboard->SetData(new wxTextDataObject(text));
wxTheClipboard->Close();
}
}

View File

@@ -139,7 +139,6 @@ private:
bool capturedMouse;
wxStyledTextCtrl* stc;
wxTextDataObject textDO;
wxSTCDropTarget* dropTarget;
wxDragResult dragResult;
};

View File

@@ -21,21 +21,17 @@ STCEXTRACPPFLAGS=-D__WX__ -DSCI_LEXER -I$(SCINTILLA)/include -I$(S)
LIBTARGET=$(WXDIR)\contrib\lib\stc.lib
OBJECTS = \
Accessor.obj \
Accessor.obj \
AutoComplete.obj \
CallTip.obj \
CellBuffer.obj \
ContractionState.obj\
Document.obj \
CallTip.obj \
CellBuffer.obj \
ContractionState.obj \
Document.obj \
DocumentAccessor.obj \
Editor.obj \
Indicator.obj \
Indicator.obj \
KeyMap.obj \
KeyWords.obj \
LineMarker.obj \
PropSet.obj \
ScintillaBase.obj \
Style.obj \
ViewStyle.obj \
KeyWords.obj \
LexCPP.obj \
LexHTML.obj \
LexOthers.obj \
@@ -43,10 +39,18 @@ OBJECTS = \
LexPython.obj \
LexSQL.obj \
LexVB.obj \
LineMarker.obj \
PropSet.obj \
ScintillaBase.obj \
Style.obj \
UniConversion.obj \
ViewStyle.obj \
WindowAccessor.obj \
\
PlatWX.obj \
ScintillaWX.obj \
stc.obj \
ScintillaWX.obj \
stc.obj \
!include $(WXDIR)\src\makelib.b32

View File

@@ -32,6 +32,9 @@ OBJECTS = \
$(S)/LexPython.$(OBJSUFF) \
$(S)/LexSQL.$(OBJSUFF) \
$(S)/LexVB.$(OBJSUFF) \
$(S)/DocumentAccessor.$(OBJSUFF)\
$(S)/UniConversion.$(OBJSUFF) \
$(S)/WindowAccessor.$(OBJSUFF) \
PlatWX.$(OBJSUFF) \
ScintillaWX.$(OBJSUFF) \
stc.$(OBJSUFF)

View File

@@ -15,21 +15,16 @@ NOPCH=1
!include $(WXDIR)\src\makevc.env
OBJECTS = \
$(D)\Accessor.obj \
$(D)\AutoComplete.obj \
$(D)\CallTip.obj \
$(D)\CellBuffer.obj \
$(D)\ContractionState.obj\
$(D)\Document.obj \
$(D)\DocumentAccessor.obj\
$(D)\Editor.obj \
$(D)\Indicator.obj \
$(D)\KeyMap.obj \
$(D)\KeyWords.obj \
$(D)\LineMarker.obj \
$(D)\PropSet.obj \
$(D)\ScintillaBase.obj \
$(D)\Style.obj \
$(D)\ViewStyle.obj \
$(D)\LexCPP.obj \
$(D)\LexHTML.obj \
$(D)\LexOthers.obj \
@@ -37,6 +32,13 @@ OBJECTS = \
$(D)\LexPython.obj \
$(D)\LexSQL.obj \
$(D)\LexVB.obj \
$(D)\LineMarker.obj \
$(D)\PropSet.obj \
$(D)\ScintillaBase.obj \
$(D)\Style.obj \
$(D)\UniConversion.obj \
$(D)\ViewStyle.obj \
$(D)\WindowAccessor.obj \
\
$(D)\PlatWX.obj \
$(D)\ScintillaWX.obj \

View File

@@ -5,29 +5,28 @@
enum { wsSpace = 1, wsTab = 2, wsSpaceTab = 4, wsInconsistent=8};
class Accessor;
typedef bool (*PFNIsCommentLeader)(Accessor &styler, int pos, int len);
// Interface to data in a Scintilla
class Accessor {
protected:
// bufferSize is a trade off between time taken to copy the characters and SendMessage overhead
enum {extremePosition=0x7FFFFFFF};
// bufferSize is a trade off between time taken to copy the characters and retrieval overhead
// slopSize positions the buffer before the desired position in case there is some backtracking
enum {bufferSize=4000, slopSize=bufferSize/8};
char buf[bufferSize+1];
WindowID id;
PropSet &props;
int startPos;
int endPos;
int lenDoc;
int offset; // Optional but including an offset makes GCC generate better code
int codePage;
bool InternalIsLeadByte(char ch);
void Fill(int position);
virtual bool InternalIsLeadByte(char ch)=0;
virtual void Fill(int position)=0;
public:
Accessor(WindowID id_, PropSet &props_, int offset_=0) :
id(id_), props(props_), startPos(0x7FFFFFFF), endPos(0),
lenDoc(-1), offset(offset_), codePage(0) {
}
void SetCodePage(int codePage_) { codePage = codePage_; }
Accessor() : startPos(extremePosition), endPos(0), codePage(0) {}
virtual ~Accessor() {}
char operator[](int position) {
position += offset;
if (position < startPos || position >= endPos) {
Fill(position);
}
@@ -35,7 +34,6 @@ public:
}
char SafeGetCharAt(int position, char chDefault=' ') {
// Safe version of operator[], returning a defined value for invalid position
position += offset;
if (position < startPos || position >= endPos) {
Fill(position);
if (position < startPos || position >= endPos) {
@@ -48,41 +46,25 @@ public:
bool IsLeadByte(char ch) {
return codePage && InternalIsLeadByte(ch);
}
char StyleAt(int position);
int GetLine(int position);
int LineStart(int line);
int LevelAt(int line);
int Length();
void Flush() {
startPos = 0x7FFFFFFF;
lenDoc = -1;
}
int GetLineState(int line);
int SetLineState(int line, int state);
PropSet &GetPropSet() { return props; }
};
class StylingContext;
typedef bool (*PFNIsCommentLeader)(StylingContext &styler, int pos, int len);
class StylingContext : public Accessor {
char styleBuf[bufferSize];
int validLen;
char chFlags;
char chWhile;
unsigned int startSeg;
public:
StylingContext(WindowID id_, PropSet &props_, int offset_=0) :
Accessor(id_,props_,offset_), validLen(0), chFlags(0) {}
void StartAt(unsigned int start, char chMask=31);
void SetFlags(char chFlags_, char chWhile_) {chFlags = chFlags_; chWhile = chWhile_; };
unsigned int GetStartSegment() { return startSeg; }
void StartSegment(unsigned int pos);
void ColourTo(unsigned int pos, int chAttr);
int GetLine(int position);
void SetLevel(int line, int level);
void Flush();
int IndentAmount(int line, int *flags, PFNIsCommentLeader pfnIsCommentLeader = 0);
void SetCodePage(int codePage_) { codePage = codePage_; }
virtual char StyleAt(int position)=0;
virtual int GetLine(int position)=0;
virtual int LineStart(int line)=0;
virtual int LevelAt(int line)=0;
virtual int Length()=0;
virtual void Flush()=0;
virtual int GetLineState(int line)=0;
virtual int SetLineState(int line, int state)=0;
virtual int GetPropertyInt(const char *key, int defaultValue=0)=0;
// Style setting
virtual void StartAt(unsigned int start, char chMask=31)=0;
virtual void SetFlags(char chFlags_, char chWhile_)=0;
virtual unsigned int GetStartSegment()=0;
virtual void StartSegment(unsigned int pos)=0;
virtual void ColourTo(unsigned int pos, int chAttr)=0;
virtual void SetLevel(int line, int level)=0;
virtual int IndentAmount(int line, int *flags, PFNIsCommentLeader pfnIsCommentLeader = 0)=0;
};

View File

@@ -4,7 +4,7 @@
// The License.txt file describes the conditions under which this software may be distributed.
typedef void (*LexerFunction)(unsigned int startPos, int lengthDoc, int initStyle,
WordList *keywordlists[], StylingContext &styler);
WordList *keywordlists[], Accessor &styler);
class LexerModule {
static LexerModule *base;
@@ -14,7 +14,7 @@ class LexerModule {
public:
LexerModule(int language_, LexerFunction fn_);
static void Colourise(unsigned int startPos, int lengthDoc, int initStyle,
int language, WordList *keywordlists[], StylingContext &styler);
int language, WordList *keywordlists[], Accessor &styler);
};
inline bool iswordchar(char ch) {

View File

@@ -45,6 +45,7 @@
#pragma warning(disable: 4800 4244 4309)
#endif
#include <windows.h>
#include <commctrl.h>
#include <richedit.h>
#endif
@@ -221,6 +222,7 @@ public:
// A surface abstracts a place to draw
class Surface {
private:
bool unicodeMode;
#if PLAT_GTK
GdkDrawable *drawable;
GdkGC *gc;
@@ -268,6 +270,7 @@ public:
bool Initialised();
void PenColour(Colour fore);
int LogPixelsY();
int DeviceHeightFont(int points);
void MoveTo(int x_, int y_);
void LineTo(int x_, int y_);
void Polygon(Point *pts, int npts, Colour fore, Colour back);
@@ -293,6 +296,10 @@ public:
int SetPalette(Palette *pal, bool inBackGround);
void SetClip(PRectangle rc);
void FlushCachedState();
void SetUnicodeMode(bool unicodeMode_) {
unicodeMode=unicodeMode_;
}
};
// Class to hide the details of window manipulation
@@ -303,6 +310,7 @@ protected:
WindowID id;
public:
Window() : id(0) {}
Window(const Window &source) : id(source.id) {}
virtual ~Window();
Window &operator=(WindowID id_) {
id = id_;

View File

@@ -75,7 +75,7 @@ public:
else
return 0;
}
char operator[](int i) {
char operator[](int i) const {
if (s)
return s[i];
else
@@ -95,7 +95,7 @@ public:
}
return *this;
}
int value() {
int value() const {
if (s)
return atoi(s);
else
@@ -168,7 +168,7 @@ public:
WordList(bool onlyLineEnds_ = false) :
words(0), list(0), len(0), onlyLineEnds(onlyLineEnds_) {}
~WordList() { Clear(); }
operator bool() { return list; }
operator bool() { return list ? true : false; }
const char *operator[](int ind) { return words[ind]; }
void Clear();
void Set(const char *s);

View File

@@ -21,6 +21,7 @@
#define SCLEX_ERRORLIST 10
#define SCLEX_MAKEFILE 11
#define SCLEX_BATCH 12
#define SCLEX_XCODE 13
// Lexical states for SCLEX_PYTHON
#define SCE_P_DEFAULT 0

View File

@@ -107,6 +107,9 @@ extern "C" {
#define SCI_STARTSTYLING SCI_START + 32
#define SCI_SETSTYLING SCI_START + 33
// This is the same value as CP_UTF8 in Windows
#define SC_CP_UTF8 65001
#define SCI_SETBUFFEREDDRAW SCI_START + 35
#define SCI_SETTABWIDTH SCI_START + 36
#define SCI_SETCODEPAGE SCI_START + 37
@@ -213,6 +216,21 @@ extern "C" {
#define SCI_AUTOCPOSSTART SCI_START + 103
#define SCI_AUTOCCOMPLETE SCI_START + 104
#define SCI_AUTOCSTOPS SCI_START + 105
#define SCI_AUTOCSETSEPARATOR SCI_START + 106
#define SCI_AUTOCGETSEPARATOR SCI_START + 107
#define SCI_AUTOCSELECT SCI_START + 108
#define SCI_GETTABWIDTH SCI_START + 121
#define SCI_SETINDENT SCI_START + 122
#define SCI_GETINDENT SCI_START + 123
#define SCI_SETUSETABS SCI_START + 124
#define SCI_GETUSETABS SCI_START + 125
#define SCI_SETLINEINDENTATION SCI_START + 126
#define SCI_GETLINEINDENTATION SCI_START + 127
#define SCI_GETLINEINDENTPOSITION SCI_START + 128
#define SCI_SETHSCROLLBAR SCI_START + 130
#define SCI_GETHSCROLLBAR SCI_START + 131
#define SCI_CALLTIPSHOW SCI_START + 200
#define SCI_CALLTIPCANCEL SCI_START + 201
@@ -284,6 +302,8 @@ extern "C" {
#define SCI_LINETRANSPOSE SCI_START + 339
#define SCI_LOWERCASE SCI_START + 340
#define SCI_UPPERCASE SCI_START + 341
#define SCI_LINESCROLLDOWN SCI_START + 342
#define SCI_LINESCROLLUP SCI_START + 343
#define SCI_LINELENGTH SCI_START + 350
#define SCI_BRACEHIGHLIGHT SCI_START + 351
@@ -318,6 +338,7 @@ extern "C" {
#define SCI_SETCARETPOLICY SCI_START + 369
#define SCI_LINESONSCREEN SCI_START + 370
#define SCI_USEPOPUP SCI_START + 371
#define SCI_SELECTIONISRECTANGLE SCI_START + 372
// GTK+ Specific
#define SCI_GRABFOCUS SCI_START + 400
@@ -350,8 +371,10 @@ typedef void (tMacroRecorder)(UINT iMessage, WPARAM wParam, LPARAM lParam,
#define SC_PERFORMED_REDO 0x40
#define SC_LASTSTEPINUNDOREDO 0x100
#define SC_MOD_CHANGEMARKER 0x200
#define SC_MOD_BEFOREINSERT 0x400
#define SC_MOD_BEFOREDELETE 0x800
#define SC_MODEVENTMASKALL 0x377
#define SC_MODEVENTMASKALL 0xF77
struct SCNotification {
NMHDR nmhdr;

View File

@@ -0,0 +1,47 @@
// WindowAccessor.h - implementation of BufferAccess and StylingAccess on a Scintilla rapid easy access to contents of a Scintilla
// Copyright 1998-2000 by Neil Hodgson <neilh@scintilla.org>
// The License.txt file describes the conditions under which this software may be distributed.
class WindowAccessor : public Accessor {
// Private so WindowAccessor objects can not be copied
WindowAccessor(const WindowAccessor &source) : Accessor(), props(source.props) {}
WindowAccessor &operator=(const WindowAccessor &) { return *this; }
protected:
WindowID id;
PropSet &props;
int lenDoc;
char styleBuf[bufferSize];
int validLen;
char chFlags;
char chWhile;
unsigned int startSeg;
bool InternalIsLeadByte(char ch);
void Fill(int position);
public:
WindowAccessor(WindowID id_, PropSet &props_) :
Accessor(), id(id_), props(props_),
lenDoc(-1), validLen(0), chFlags(0) {
}
~WindowAccessor();
char StyleAt(int position);
int GetLine(int position);
int LineStart(int line);
int LevelAt(int line);
int Length();
void Flush();
int GetLineState(int line);
int SetLineState(int line, int state);
int GetPropertyInt(const char *key, int defaultValue=0) {
return props.GetInt(key, defaultValue);
}
void StartAt(unsigned int start, char chMask=31);
void SetFlags(char chFlags_, char chWhile_) {chFlags = chFlags_; chWhile = chWhile_; };
unsigned int GetStartSegment() { return startSeg; }
void StartSegment(unsigned int pos);
void ColourTo(unsigned int pos, int chAttr);
void SetLevel(int line, int level);
int IndentAmount(int line, int *flags, PFNIsCommentLeader pfnIsCommentLeader = 0);
};

View File

@@ -15,6 +15,7 @@ AutoComplete::AutoComplete() {
active = false;
posStart = 0;
strcpy(stopChars, "");
separator = ' ';
}
AutoComplete::~AutoComplete() {
@@ -44,6 +45,14 @@ bool AutoComplete::IsStopChar(char ch) {
return ch && strchr(stopChars, ch);
}
void AutoComplete::SetSeparator(char separator_) {
separator = separator_;
}
char AutoComplete::GetSeparator() {
return separator;
}
int AutoComplete::SetList(const char *list) {
int maxStrLen = 12;
lb.Clear();
@@ -53,7 +62,7 @@ int AutoComplete::SetList(const char *list) {
char *startword = words;
int i = 0;
for (; words && words[i]; i++) {
if (words[i] == ' ') {
if (words[i] == separator) {
words[i] = '\0';
lb.Append(startword);
maxStrLen = Platform::Maximum(maxStrLen, strlen(startword));

View File

@@ -9,6 +9,7 @@
class AutoComplete {
bool active;
char stopChars[256];
char separator;
public:
ListBox lb;
int posStart;
@@ -27,7 +28,11 @@ public:
void SetStopChars(const char *stopChars_);
bool IsStopChar(char ch);
// The list string contains a sequence of words separated by spaces
// The separator character is used when interpreting the list in SetList
void SetSeparator(char separator_);
char GetSeparator();
// The list string contains a sequence of words separated by the separator character
int SetList(const char *list);
void Show();

View File

@@ -6,13 +6,14 @@
#ifndef CALLTIP_H
#define CALLTIP_H
const char callClassName[] = "CallTip";
class CallTip {
int startHighlight;
int endHighlight;
char *val;
Font font;
// Private so CallTip objects can not be copied
CallTip(const CallTip &) {}
CallTip &operator=(const CallTip &) { return *this; }
public:
Window wCallTip;
Window wDraw;

View File

@@ -191,11 +191,23 @@ void LineVector::InsertValue(int pos, int value) {
}
}
lines++;
for (int i = lines + 1; i > pos; i--) {
for (int i = lines; i > pos; i--) {
linesData[i] = linesData[i - 1];
}
linesData[pos].startPosition = value;
linesData[pos].handleSet = 0;
if (levels) {
for (int j = lines; j > pos; j--) {
levels[j] = levels[j - 1];
}
if (pos == 0) {
levels[pos] = SC_FOLDLEVELBASE;
} else if (pos == (lines-1)) { // Last line will not be a folder
levels[pos] = SC_FOLDLEVELBASE;
} else {
levels[pos] = levels[pos-1];
}
}
}
void LineVector::SetValue(int pos, int value) {
@@ -221,6 +233,15 @@ void LineVector::Remove(int pos) {
for (int i = pos; i < lines; i++) {
linesData[i] = linesData[i + 1];
}
if (levels) {
// Level information merges back onto previous line
int posAbove = pos-1;
if (posAbove < 0)
posAbove = 0;
for (int j = posAbove; j < lines; j++) {
levels[j] = levels[j + 1];
}
}
lines--;
}
@@ -233,9 +254,8 @@ int LineVector::LineFromPosition(int pos) {
return lines - 1;
int lower = 0;
int upper = lines;
int middle = 0;
do {
middle = (upper + lower + 1) / 2; // Round high
int middle = (upper + lower + 1) / 2; // Round high
if (pos < linesData[middle].startPosition) {
upper = middle - 1;
} else {
@@ -316,12 +336,13 @@ Action::~Action() {
Destroy();
}
void Action::Create(actionType at_, int position_, char *data_, int lenData_) {
void Action::Create(actionType at_, int position_, char *data_, int lenData_, bool mayCoalesce_) {
delete []data;
position = position_;
at = at_;
data = data_;
lenData = lenData_;
mayCoalesce = mayCoalesce_;
}
void Action::Destroy() {
@@ -336,12 +357,14 @@ void Action::Grab(Action *source) {
at = source->at;
data = source->data;
lenData = source->lenData;
mayCoalesce = source->mayCoalesce;
// Ownership of source data transferred to this
source->position = 0;
source->at = startAction;
source->data = 0;
source->lenData = 0;
source->mayCoalesce = true;
}
// The undo history stores a sequence of user operations that represent the user's view of the
@@ -426,7 +449,9 @@ void UndoHistory::AppendAction(actionType at, int position, char *data, int leng
//Platform::DebugPrintf("action coalesced\n");
}
} else {
currentAction++;
// Actions not at top level are always coalesced unless this is after return to top level
if (!actions[currentAction].mayCoalesce)
currentAction++;
}
} else {
currentAction++;
@@ -445,6 +470,7 @@ void UndoHistory::BeginUndoAction() {
actions[currentAction].Create(startAction);
maxAction = currentAction;
}
actions[currentAction].mayCoalesce = false;
}
undoSequenceDepth++;
}
@@ -458,6 +484,7 @@ void UndoHistory::EndUndoAction() {
actions[currentAction].Create(startAction);
maxAction = currentAction;
}
actions[currentAction].mayCoalesce = false;
}
}
@@ -499,8 +526,12 @@ int UndoHistory::StartUndo() {
return currentAction - act;
}
const Action &UndoHistory::UndoStep() {
return actions[currentAction--];
const Action &UndoHistory::GetUndoStep() const {
return actions[currentAction];
}
void UndoHistory::CompletedUndoStep() {
currentAction--;
}
bool UndoHistory::CanRedo() const {
@@ -520,8 +551,12 @@ int UndoHistory::StartRedo() {
return act - currentAction;
}
const Action &UndoHistory::RedoStep() {
return actions[currentAction++];
const Action &UndoHistory::GetRedoStep() const {
return actions[currentAction];
}
void UndoHistory::CompletedRedoStep() {
currentAction++;
}
CellBuffer::CellBuffer(int initialLength) {
@@ -673,7 +708,7 @@ void CellBuffer::InsertCharStyle(int position, char ch, char style) {
bool CellBuffer::SetStyleAt(int position, char style, char mask) {
char curVal = ByteAt(position*2 + 1);
if ((curVal & mask) != style) {
SetByteAt(position*2 + 1, (curVal & ~mask) | style);
SetByteAt(position*2 + 1, static_cast<char>((curVal & ~mask) | style));
return true;
} else {
return false;
@@ -686,7 +721,7 @@ bool CellBuffer::SetStyleFor(int position, int lengthStyle, char style, char mas
while (lengthStyle--) {
char curVal = ByteAt(bytePos);
if ((curVal & mask) != style) {
SetByteAt(bytePos, (curVal & ~mask) | style);
SetByteAt(bytePos, static_cast<char>((curVal & ~mask) | style));
changed = true;
}
bytePos += 2;
@@ -947,8 +982,12 @@ int CellBuffer::StartUndo() {
return uh.StartUndo();
}
const Action &CellBuffer::UndoStep() {
const Action &actionStep = uh.UndoStep();
const Action &CellBuffer::GetUndoStep() const {
return uh.GetUndoStep();
}
void CellBuffer::PerformUndoStep() {
const Action &actionStep = uh.GetUndoStep();
if (actionStep.at == insertAction) {
BasicDeleteChars(actionStep.position, actionStep.lenData*2);
} else if (actionStep.at == removeAction) {
@@ -960,7 +999,7 @@ const Action &CellBuffer::UndoStep() {
BasicInsertString(actionStep.position, styledData, actionStep.lenData*2);
delete []styledData;
}
return actionStep;
uh.CompletedUndoStep();
}
bool CellBuffer::CanRedo() {
@@ -971,8 +1010,12 @@ int CellBuffer::StartRedo() {
return uh.StartRedo();
}
const Action &CellBuffer::RedoStep() {
const Action &actionStep = uh.RedoStep();
const Action &CellBuffer::GetRedoStep() const {
return uh.GetRedoStep();
}
void CellBuffer::PerformRedoStep() {
const Action &actionStep = uh.GetRedoStep();
if (actionStep.at == insertAction) {
char *styledData = new char[actionStep.lenData * 2];
for (int i = 0; i < actionStep.lenData; i++) {
@@ -984,7 +1027,7 @@ const Action &CellBuffer::RedoStep() {
} else if (actionStep.at == removeAction) {
BasicDeleteChars(actionStep.position, actionStep.lenData*2);
}
return actionStep;
uh.CompletedRedoStep();
}
int CellBuffer::SetLineState(int line, int state) {

View File

@@ -79,10 +79,11 @@ public:
int position;
char *data;
int lenData;
bool mayCoalesce;
Action();
~Action();
void Create(actionType at_, int position_=0, char *data_=0, int lenData_=0);
void Create(actionType at_, int position_=0, char *data_=0, int lenData_=0, bool mayCoalesce_=true);
void Destroy();
void Grab(Action *source);
};
@@ -119,10 +120,12 @@ public:
// called that many times. Similarly for redo.
bool CanUndo() const;
int StartUndo();
const Action &UndoStep();
const Action &GetUndoStep() const;
void CompletedUndoStep();
bool CanRedo() const;
int StartRedo();
const Action &RedoStep();
const Action &GetRedoStep() const;
void CompletedRedoStep();
};
// Holder for an expandable array of characters that supports undo and line markers
@@ -171,7 +174,7 @@ public:
// Setting styles for positions outside the range of the buffer is safe and has no effect.
// True is returned if the style of a character changed.
bool SetStyleAt(int position, char style, char mask=(char)0xff);
bool SetStyleAt(int position, char style, char mask='\377');
bool SetStyleFor(int position, int length, char style, char mask);
const char *DeleteChars(int position, int deleteLength);
@@ -206,10 +209,12 @@ public:
// called that many times. Similarly for redo.
bool CanUndo();
int StartUndo();
const Action &UndoStep();
const Action &GetUndoStep() const;
void PerformUndoStep();
bool CanRedo();
int StartRedo();
const Action &RedoStep();
const Action &GetRedoStep() const;
void PerformRedoStep();
int SetLineState(int line, int state);
int GetLineState(int line);

View File

@@ -30,7 +30,6 @@ void ContractionState::MakeValid() const {
if (!valid) {
// Could be cleverer by keeping the index of the last still valid entry
// rather than invalidating all.
int linePrev = -1;
int lineDisplay = 0;
for (int line=0; line<linesInDoc; line++) {
lines[line].displayLine = lineDisplay;
@@ -113,7 +112,7 @@ void ContractionState::InsertLines(int lineDoc, int lineCount) {
}
linesInDoc += lineCount;
linesInDisplay += lineCount;
for (int i = linesInDoc + 1; i >= lineDoc + lineCount; i--) {
for (int i = linesInDoc; i >= lineDoc + lineCount; i--) {
lines[i].visible = lines[i - lineCount].visible;
lines[i].expanded = lines[i - lineCount].expanded;
}
@@ -130,16 +129,18 @@ void ContractionState::DeleteLines(int lineDoc, int lineCount) {
linesInDisplay -= lineCount;
return;
}
int delta = 0;
for (int d=0;d<lineCount;d++)
int deltaDisplayed = 0;
for (int d=0;d<lineCount;d++) {
if (lines[lineDoc+d].visible)
delta--;
deltaDisplayed--;
}
for (int i = lineDoc; i < linesInDoc-lineCount; i++) {
lines[i].visible = lines[i + lineCount].visible;
if (i != 0) // Line zero is always visible
lines[i].visible = lines[i + lineCount].visible;
lines[i].expanded = lines[i + lineCount].expanded;
}
linesInDoc -= lineCount;
linesInDisplay += delta;
linesInDisplay += deltaDisplayed;
valid = false;
}
@@ -154,6 +155,10 @@ bool ContractionState::GetVisible(int lineDoc) const {
}
bool ContractionState::SetVisible(int lineDocStart, int lineDocEnd, bool visible) {
if (lineDocStart == 0)
lineDocStart++;
if (lineDocStart > lineDocEnd)
return false;
if (size == 0) {
Grow(linesInDoc + growSize);
}

View File

@@ -32,7 +32,10 @@ Document::Document() {
}
endStyled = 0;
enteredCount = 0;
enteredReadOnlyCount = 0;
tabInChars = 8;
indentInChars = 0;
useTabs = true;
watchers = 0;
lenWatchers = 0;
}
@@ -201,18 +204,23 @@ bool Document::IsCrLf(int pos) {
bool Document::IsDBCS(int pos) {
#if PLAT_WIN
if (dbcsCodePage) {
// Anchor DBCS calculations at start of line because start of line can
// not be a DBCS trail byte.
int startLine = pos;
while (startLine > 0 && cb.CharAt(startLine) != '\r' && cb.CharAt(startLine) != '\n')
startLine--;
while (startLine <= pos) {
if (IsDBCSLeadByteEx(dbcsCodePage, cb.CharAt(startLine))) {
if (SC_CP_UTF8 == dbcsCodePage) {
unsigned char ch = static_cast<unsigned char>(cb.CharAt(pos));
return ch >= 0x80;
} else {
// Anchor DBCS calculations at start of line because start of line can
// not be a DBCS trail byte.
int startLine = pos;
while (startLine > 0 && cb.CharAt(startLine) != '\r' && cb.CharAt(startLine) != '\n')
startLine--;
while (startLine <= pos) {
if (IsDBCSLeadByteEx(dbcsCodePage, cb.CharAt(startLine))) {
startLine++;
if (startLine >= pos)
return true;
}
startLine++;
if (startLine >= pos)
return true;
}
startLine++;
}
}
return false;
@@ -221,6 +229,28 @@ bool Document::IsDBCS(int pos) {
#endif
}
int Document::LenChar(int pos) {
if (IsCrLf(pos)) {
return 2;
} else if (SC_CP_UTF8 == dbcsCodePage) {
unsigned char ch = static_cast<unsigned char>(cb.CharAt(pos));
if (ch < 0x80)
return 1;
int len = 2;
if (ch >= (0x80+0x40+0x20))
len = 3;
int lengthDoc = Length();
if ((pos + len) > lengthDoc)
return lengthDoc-pos;
else
return len;
} else if (IsDBCS(pos)) {
return 2;
} else {
return 1;
}
}
// Normalise a position so that it is not halfway through a two byte character.
// This can occur in two situations -
// When lines are terminated with \r\n pairs which should be treated as one character.
@@ -252,29 +282,41 @@ int Document::MovePositionOutsideChar(int pos, int moveDir, bool checkLineEnd) {
#if PLAT_WIN
if (dbcsCodePage) {
// Anchor DBCS calculations at start of line because start of line can
// not be a DBCS trail byte.
int startLine = pos;
while (startLine > 0 && cb.CharAt(startLine) != '\r' && cb.CharAt(startLine) != '\n')
startLine--;
bool atLeadByte = false;
while (startLine < pos) {
if (atLeadByte)
atLeadByte = false;
else if (IsDBCSLeadByteEx(dbcsCodePage, cb.CharAt(startLine)))
atLeadByte = true;
else
atLeadByte = false;
startLine++;
//Platform::DebugPrintf("DBCS %s\n", atlead ? "D" : "-");
}
if (SC_CP_UTF8 == dbcsCodePage) {
unsigned char ch = static_cast<unsigned char>(cb.CharAt(pos));
while ((pos > 0) && (pos < Length()) && (ch >= 0x80) && (ch < (0x80 + 0x40))) {
// ch is a trail byte
if (moveDir > 0)
pos++;
else
pos--;
ch = static_cast<unsigned char>(cb.CharAt(pos));
}
} else {
// Anchor DBCS calculations at start of line because start of line can
// not be a DBCS trail byte.
int startLine = pos;
while (startLine > 0 && cb.CharAt(startLine) != '\r' && cb.CharAt(startLine) != '\n')
startLine--;
bool atLeadByte = false;
while (startLine < pos) {
if (atLeadByte)
atLeadByte = false;
else if (IsDBCSLeadByteEx(dbcsCodePage, cb.CharAt(startLine)))
atLeadByte = true;
else
atLeadByte = false;
startLine++;
//Platform::DebugPrintf("DBCS %s\n", atlead ? "D" : "-");
}
if (atLeadByte) {
// Position is between a lead byte and a trail byte
if (moveDir > 0)
return pos + 1;
else
return pos - 1;
if (atLeadByte) {
// Position is between a lead byte and a trail byte
if (moveDir > 0)
return pos + 1;
else
return pos - 1;
}
}
}
#endif
@@ -292,41 +334,60 @@ void Document::ModifiedAt(int pos) {
// Unlike Undo, Redo, and InsertStyledString, the pos argument is a cell number not a char number
void Document::DeleteChars(int pos, int len) {
if (cb.IsReadOnly() && enteredReadOnlyCount==0) {
enteredReadOnlyCount++;
NotifyModifyAttempt();
enteredReadOnlyCount--;
}
if (enteredCount == 0) {
enteredCount++;
if (cb.IsReadOnly())
NotifyModifyAttempt();
if (!cb.IsReadOnly()) {
NotifyModified(
DocModification(
SC_MOD_BEFOREDELETE | SC_PERFORMED_USER,
pos, len,
0, 0));
int prevLinesTotal = LinesTotal();
bool startSavePoint = cb.IsSavePoint();
const char *text = cb.DeleteChars(pos*2, len * 2);
if (startSavePoint && cb.IsCollectingUndo())
NotifySavePoint(!startSavePoint);
ModifiedAt(pos);
int modFlags = SC_MOD_DELETETEXT | SC_PERFORMED_USER;
DocModification mh(modFlags, pos, len, LinesTotal() - prevLinesTotal, text);
NotifyModified(mh);
NotifyModified(
DocModification(
SC_MOD_DELETETEXT | SC_PERFORMED_USER,
pos, len,
LinesTotal() - prevLinesTotal, text));
}
enteredCount--;
}
}
void Document::InsertStyledString(int position, char *s, int insertLength) {
if (cb.IsReadOnly() && enteredReadOnlyCount==0) {
enteredReadOnlyCount++;
NotifyModifyAttempt();
enteredReadOnlyCount--;
}
if (enteredCount == 0) {
enteredCount++;
if (cb.IsReadOnly())
NotifyModifyAttempt();
if (!cb.IsReadOnly()) {
NotifyModified(
DocModification(
SC_MOD_BEFOREINSERT | SC_PERFORMED_USER,
position / 2, insertLength / 2,
0, 0));
int prevLinesTotal = LinesTotal();
bool startSavePoint = cb.IsSavePoint();
const char *text = cb.InsertString(position, s, insertLength);
if (startSavePoint && cb.IsCollectingUndo())
NotifySavePoint(!startSavePoint);
ModifiedAt(position / 2);
int modFlags = SC_MOD_INSERTTEXT | SC_PERFORMED_USER;
DocModification mh(modFlags, position / 2, insertLength / 2, LinesTotal() - prevLinesTotal, text);
NotifyModified(mh);
NotifyModified(
DocModification(
SC_MOD_INSERTTEXT | SC_PERFORMED_USER,
position / 2, insertLength / 2,
LinesTotal() - prevLinesTotal, text));
}
enteredCount--;
}
@@ -341,7 +402,15 @@ int Document::Undo() {
//Platform::DebugPrintf("Steps=%d\n", steps);
for (int step=0; step<steps; step++) {
int prevLinesTotal = LinesTotal();
const Action &action = cb.UndoStep();
const Action &action = cb.GetUndoStep();
if (action.at == removeAction) {
NotifyModified(DocModification(
SC_MOD_BEFOREINSERT | SC_PERFORMED_UNDO, action));
} else {
NotifyModified(DocModification(
SC_MOD_BEFOREDELETE | SC_PERFORMED_UNDO, action));
}
cb.PerformUndoStep();
int cellPosition = action.position / 2;
ModifiedAt(cellPosition);
newPos = cellPosition;
@@ -376,10 +445,17 @@ int Document::Redo() {
int steps = cb.StartRedo();
for (int step=0; step<steps; step++) {
int prevLinesTotal = LinesTotal();
const Action &action = cb.RedoStep();
int cellPosition = action.position / 2;
ModifiedAt(cellPosition);
newPos = cellPosition;
const Action &action = cb.GetRedoStep();
if (action.at == insertAction) {
NotifyModified(DocModification(
SC_MOD_BEFOREINSERT | SC_PERFORMED_REDO, action));
} else {
NotifyModified(DocModification(
SC_MOD_BEFOREDELETE | SC_PERFORMED_REDO, action));
}
cb.PerformRedoStep();
ModifiedAt(action.position / 2);
newPos = action.position / 2;
int modFlags = SC_PERFORMED_REDO;
if (action.at == insertAction) {
@@ -390,7 +466,8 @@ int Document::Redo() {
}
if (step == steps-1)
modFlags |= SC_LASTSTEPINUNDOREDO;
NotifyModified(DocModification(modFlags, cellPosition, action.lenData,
NotifyModified(
DocModification(modFlags, action.position / 2, action.lenData,
LinesTotal() - prevLinesTotal, action.data));
}
@@ -433,13 +510,7 @@ void Document::ChangeChar(int pos, char ch) {
}
void Document::DelChar(int pos) {
if (IsCrLf(pos)) {
DeleteChars(pos, 2);
} else if (IsDBCS(pos)) {
DeleteChars(pos, 2);
} else if (pos < Length()) {
DeleteChars(pos, 1);
}
DeleteChars(pos, LenChar(pos));
}
int Document::DelCharBack(int pos) {
@@ -448,6 +519,10 @@ int Document::DelCharBack(int pos) {
} else if (IsCrLf(pos - 2)) {
DeleteChars(pos - 2, 2);
return pos - 2;
} else if (SC_CP_UTF8 == dbcsCodePage) {
int startChar = MovePositionOutsideChar(pos-1, -1, false);
DeleteChars(startChar, pos - startChar);
return startChar;
} else if (IsDBCS(pos - 1)) {
DeleteChars(pos - 2, 2);
return pos - 2;
@@ -457,27 +532,80 @@ int Document::DelCharBack(int pos) {
}
}
static bool isindentchar(char ch) {
return (ch == ' ') || (ch == '\t');
}
static int NextTab(int pos, int tabSize) {
return ((pos / tabSize) + 1) * tabSize;
}
static void CreateIndentation(char *linebuf, int length, int indent, int tabSize, bool insertSpaces) {
length--; // ensure space for \0
if (!insertSpaces) {
while ((indent >= tabSize) && (length > 0)) {
*linebuf++ = '\t';
indent -= tabSize;
length--;
}
}
while ((indent > 0) && (length > 0)) {
*linebuf++ = ' ';
indent--;
length--;
}
*linebuf = '\0';
}
int Document::GetLineIndentation(int line) {
int indent = 0;
if ((line >= 0) && (line < LinesTotal())) {
int lineStart = LineStart(line);
int length = Length();
for (int i=lineStart;i<length;i++) {
char ch = cb.CharAt(i);
if (ch == ' ')
indent++;
else if (ch == '\t')
indent = NextTab(indent, tabInChars);
else
return indent;
}
}
return indent;
}
void Document::SetLineIndentation(int line, int indent) {
int indentOfLine = GetLineIndentation(line);
if (indent < 0)
indent = 0;
if (indent != indentOfLine) {
char linebuf[1000];
CreateIndentation(linebuf, sizeof(linebuf), indent, tabInChars, !useTabs);
int thisLineStart = LineStart(line);
int indentPos = GetLineIndentPosition(line);
DeleteChars(thisLineStart, indentPos - thisLineStart);
InsertString(thisLineStart, linebuf);
}
}
int Document::GetLineIndentPosition(int line) {
int pos = LineStart(line);
int length = Length();
while ((pos < length) && isindentchar(cb.CharAt(pos))) {
pos++;
}
return pos;
}
void Document::Indent(bool forwards, int lineBottom, int lineTop) {
if (forwards) {
// Indent by a tab
for (int line = lineBottom; line >= lineTop; line--) {
InsertChar(LineStart(line), '\t');
}
} else {
// Dedent - suck white space off the front of the line to dedent by equivalent of a tab
for (int line = lineBottom; line >= lineTop; line--) {
int ispc = 0;
while (ispc < tabInChars && cb.CharAt(LineStart(line) + ispc) == ' ')
ispc++;
int posStartLine = LineStart(line);
if (ispc == tabInChars) {
DeleteChars(posStartLine, ispc);
} else if (cb.CharAt(posStartLine + ispc) == '\t') {
DeleteChars(posStartLine, ispc + 1);
} else { // Hit a non-white
DeleteChars(posStartLine, ispc);
}
}
// Dedent - suck white space off the front of the line to dedent by equivalent of a tab
for (int line = lineBottom; line >= lineTop; line--) {
int indentOfLine = GetLineIndentation(line);
if (forwards)
SetLineIndentation(line, indentOfLine + IndentSize());
else
SetLineIndentation(line, indentOfLine - IndentSize());
}
}
@@ -522,6 +650,8 @@ void Document::ConvertLineEnds(int eolModeSet) {
}
bool Document::IsWordChar(unsigned char ch) {
if ((SC_CP_UTF8 == dbcsCodePage) && (ch >0x80))
return true;
return wordchars[ch];
}
@@ -588,16 +718,14 @@ long Document::FindText(int minPos, int maxPos, const char *s, bool caseSensitiv
// Compute actual search ranges needed
int lengthFind = strlen(s);
int endSearch = 0;
int endSearch = endPos;
if (startPos <= endPos) {
endSearch = endPos - lengthFind + 1;
} else {
endSearch = endPos;
}
//Platform::DebugPrintf("Find %d %d %s %d\n", startPos, endPos, ft->lpstrText, lengthFind);
char firstChar = s[0];
if (!caseSensitive)
firstChar = toupper(firstChar);
firstChar = static_cast<char>(toupper(firstChar));
int pos = startPos;
while (forward ? (pos < endSearch) : (pos >= endSearch)) {
char ch = CharAt(pos);
@@ -646,15 +774,15 @@ void Document::ChangeCase(Range r, bool makeUpperCase) {
for (int pos=r.start; pos<r.end; pos++) {
char ch = CharAt(pos);
if (dbcsCodePage && IsDBCS(pos)) {
pos++;
pos += LenChar(pos);
} else {
if (makeUpperCase) {
if (islower(ch)) {
ChangeChar(pos, toupper(ch));
ChangeChar(pos, static_cast<char>(toupper(ch)));
}
} else {
if (isupper(ch)) {
ChangeChar(pos, tolower(ch));
ChangeChar(pos, static_cast<char>(tolower(ch)));
}
}
}
@@ -795,5 +923,3 @@ void Document::NotifyModified(DocModification mh) {
watchers[i].watcher->NotifyModified(this, mh, watchers[i].userData);
}
}

View File

@@ -74,9 +74,10 @@ private:
CellBuffer cb;
bool wordchars[256];
int stylingPos;
int stylingMask;
char stylingMask;
int endStyled;
int enteredCount;
int enteredReadOnlyCount;
WatcherWithUserData *watchers;
int lenWatchers;
@@ -86,8 +87,11 @@ public:
int stylingBitsMask;
int eolMode;
// dbcsCodePage can also be SC_CP_UTF8 to enable UTF-8 mode
int dbcsCodePage;
int tabInChars;
int indentInChars;
bool useTabs;
Document();
virtual ~Document();
@@ -98,6 +102,7 @@ public:
int LineFromPosition(int pos);
int ClampPositionIntoDocument(int pos);
bool IsCrLf(int pos);
int LenChar(int pos);
int MovePositionOutsideChar(int pos, int moveDir, bool checkLineEnd=true);
// Gateways to modifying document
@@ -115,6 +120,10 @@ public:
void EndUndoAction() { cb.EndUndoAction(); }
void SetSavePoint();
bool IsSavePoint() { return cb.IsSavePoint(); }
int GetLineIndentation(int line);
void SetLineIndentation(int line, int indent);
int GetLineIndentPosition(int line);
void Indent(bool forwards, int lineBottom, int lineTop);
void ConvertLineEnds(int eolModeSet);
void SetReadOnly(bool set) { cb.SetReadOnly(set); }
@@ -183,6 +192,8 @@ private:
void NotifyModifyAttempt();
void NotifySavePoint(bool atSavePoint);
void NotifyModified(DocModification mh);
int IndentSize() { return indentInChars ? indentInChars : tabInChars; }
};
// To optimise processing of document modifications by DocWatchers, a hint is passed indicating the
@@ -209,6 +220,16 @@ public:
line(0),
foldLevelNow(0),
foldLevelPrev(0) {}
DocModification(int modificationType_, const Action &act, int linesAdded_=0) :
modificationType(modificationType_),
position(act.position / 2),
length(act.lenData),
linesAdded(linesAdded_),
text(act.data),
line(0),
foldLevelNow(0),
foldLevelPrev(0) {}
};
// A class that wants to receive notifications from a Document must be derived from DocWatcher

View File

@@ -0,0 +1,174 @@
// SciTE - Scintilla based Text Editor
// Accessor.cxx - rapid easy access to contents of a Scintilla
// Copyright 1998-2000 by Neil Hodgson <neilh@scintilla.org>
// The License.txt file describes the conditions under which this software may be distributed.
#include <stdlib.h>
#include <ctype.h>
#include <stdio.h>
#include "Platform.h"
#include "PropSet.h"
#include "SVector.h"
#include "Accessor.h"
#include "DocumentAccessor.h"
#include "CellBuffer.h"
#include "Scintilla.h"
#include "Document.h"
DocumentAccessor::~DocumentAccessor() {
}
bool DocumentAccessor::InternalIsLeadByte(char ch) {
#if PLAT_GTK
// TODO: support DBCS under GTK+
return false;
#elif PLAT_WIN
if (SC_CP_UTF8 == codePage)
// For lexing, all characters >= 0x80 are treated the
// same so none is considered a lead byte.
return false;
else
return IsDBCSLeadByteEx(codePage, ch);
#elif PLAT_WX
return false;
#endif
}
void DocumentAccessor::Fill(int position) {
if (lenDoc == -1)
lenDoc = pdoc->Length();
startPos = position - slopSize;
if (startPos + bufferSize > lenDoc)
startPos = lenDoc - bufferSize;
if (startPos < 0)
startPos = 0;
endPos = startPos + bufferSize;
if (endPos > lenDoc)
endPos = lenDoc;
pdoc->GetCharRange(buf, startPos, endPos-startPos);
buf[endPos-startPos] = '\0';
}
char DocumentAccessor::StyleAt(int position) {
return pdoc->StyleAt(position);
}
int DocumentAccessor::GetLine(int position) {
return pdoc->LineFromPosition(position);
}
int DocumentAccessor::LineStart(int line) {
return pdoc->LineStart(line);
}
int DocumentAccessor::LevelAt(int line) {
return pdoc->GetLevel(line);
}
int DocumentAccessor::Length() {
if (lenDoc == -1)
lenDoc = pdoc->Length();
return lenDoc;
}
int DocumentAccessor::GetLineState(int line) {
return pdoc->GetLineState(line);
}
int DocumentAccessor::SetLineState(int line, int state) {
return pdoc->SetLineState(line, state);
}
void DocumentAccessor::StartAt(unsigned int start, char chMask) {
pdoc->StartStyling(start, chMask);
}
void DocumentAccessor::StartSegment(unsigned int pos) {
startSeg = pos;
}
void DocumentAccessor::ColourTo(unsigned int pos, int chAttr) {
// Only perform styling if non empty range
if (pos != startSeg - 1) {
if (pos < startSeg) {
Platform::DebugPrintf("Bad colour positions %d - %d\n", startSeg, pos);
}
if (validLen + (pos - startSeg + 1) >= bufferSize)
Flush();
if (validLen + (pos - startSeg + 1) >= bufferSize) {
// Too big for buffer so send directly
pdoc->SetStyleFor(pos - startSeg + 1, static_cast<char>(chAttr));
} else {
if (chAttr != chWhile)
chFlags = 0;
chAttr |= chFlags;
for (unsigned int i = startSeg; i <= pos; i++) {
styleBuf[validLen++] = static_cast<char>(chAttr);
}
}
}
startSeg = pos+1;
}
void DocumentAccessor::SetLevel(int line, int level) {
pdoc->SetLevel(line, level);
}
void DocumentAccessor::Flush() {
startPos = extremePosition;
lenDoc = -1;
if (validLen > 0) {
pdoc->SetStyles(validLen, styleBuf);
validLen = 0;
}
}
int DocumentAccessor::IndentAmount(int line, int *flags, PFNIsCommentLeader pfnIsCommentLeader) {
int end = Length();
int spaceFlags = 0;
// Determines the indentation level of the current line and also checks for consistent
// indentation compared to the previous line.
// Indentation is judged consistent when the indentation whitespace of each line lines
// the same or the indentation of one line is a prefix of the other.
int pos = LineStart(line);
char ch = (*this)[pos];
int indent = 0;
bool inPrevPrefix = line > 0;
int posPrev = inPrevPrefix ? LineStart(line-1) : 0;
while ((ch == ' ' || ch == '\t') && (pos < end)) {
if (inPrevPrefix) {
char chPrev = (*this)[posPrev++];
if (chPrev == ' ' || chPrev == '\t') {
if (chPrev != ch)
spaceFlags |= wsInconsistent;
} else {
inPrevPrefix = false;
}
}
if (ch == ' ') {
spaceFlags |= wsSpace;
indent++;
} else { // Tab
spaceFlags |= wsTab;
if (spaceFlags & wsSpace)
spaceFlags |= wsSpaceTab;
indent = (indent / 8 + 1) * 8;
}
ch = (*this)[++pos];
}
*flags = spaceFlags;
indent += SC_FOLDLEVELBASE;
// if completely empty line or the start of a comment...
if (isspace(ch) || (pfnIsCommentLeader && (*pfnIsCommentLeader)(*this, pos, end-pos)) )
return indent | SC_FOLDLEVELWHITEFLAG;
else
return indent;
}

View File

@@ -0,0 +1,49 @@
// DocumentAccessor.h - implementation of BufferAccess and StylingAccess on a Scintilla rapid easy access to contents of a Scintilla
// Copyright 1998-2000 by Neil Hodgson <neilh@scintilla.org>
// The License.txt file describes the conditions under which this software may be distributed.
class Document;
class DocumentAccessor : public Accessor {
// Private so DocumentAccessor objects can not be copied
DocumentAccessor(const DocumentAccessor &source) : Accessor(), props(source.props) {}
DocumentAccessor &operator=(const DocumentAccessor &) { return *this; }
protected:
Document *pdoc;
PropSet &props;
int lenDoc;
char styleBuf[bufferSize];
int validLen;
char chFlags;
char chWhile;
unsigned int startSeg;
bool InternalIsLeadByte(char ch);
void Fill(int position);
public:
DocumentAccessor(Document *pdoc_, PropSet &props_) :
Accessor(), pdoc(pdoc_), props(props_),
lenDoc(-1), validLen(0), chFlags(0) {
}
~DocumentAccessor();
char StyleAt(int position);
int GetLine(int position);
int LineStart(int line);
int LevelAt(int line);
int Length();
void Flush();
int GetLineState(int line);
int SetLineState(int line, int state);
int GetPropertyInt(const char *key, int defaultValue=0) {
return props.GetInt(key, defaultValue);
}
void StartAt(unsigned int start, char chMask=31);
void SetFlags(char chFlags_, char chWhile_) {chFlags = chFlags_; chWhile = chWhile_; };
unsigned int GetStartSegment() { return startSeg; }
void StartSegment(unsigned int pos);
void ColourTo(unsigned int pos, int chAttr);
void SetLevel(int line, int level);
int IndentAmount(int line, int *flags, PFNIsCommentLeader pfnIsCommentLeader = 0);
};

View File

@@ -69,6 +69,7 @@ Editor::Editor() {
xOffset = 0;
xCaretMargin = 50;
horizontalScrollBarVisible = true;
currentPos = 0;
anchor = 0;
@@ -189,7 +190,7 @@ bool IsControlCharacter(char ch) {
return ch >= 0 && ch < ' ';
}
const char *ControlCharacterString(char ch) {
const char *ControlCharacterString(unsigned char ch) {
const char *reps[] = {
"NUL", "SOH", "STX", "ETX", "EOT", "ENQ", "ACK", "BEL",
"BS", "HT", "LF", "VT", "FF", "CR", "SO", "SI",
@@ -210,6 +211,7 @@ Point Editor::LocationFromPosition(unsigned int pos) {
//Platform::DebugPrintf("line=%d\n", line);
Surface surface;
surface.Init();
surface.SetUnicodeMode(SC_CP_UTF8 == pdoc->dbcsCodePage);
Point pt;
pt.y = (lineVisible - topLine) * vs.lineHeight; // + half a lineheight?
unsigned int posLineStart = pdoc->LineStart(line);
@@ -252,6 +254,7 @@ int Editor::PositionFromLocation(Point pt) {
//Platform::DebugPrintf("Position of (%d,%d) line = %d top=%d\n", pt.x, pt.y, line, topLine);
Surface surface;
surface.Init();
surface.SetUnicodeMode(SC_CP_UTF8 == pdoc->dbcsCodePage);
unsigned int posLineStart = pdoc->LineStart(line);
LineLayout ll;
@@ -273,6 +276,7 @@ int Editor::PositionFromLineX(int line, int x) {
//Platform::DebugPrintf("Position of (%d,%d) line = %d top=%d\n", pt.x, pt.y, line, topLine);
Surface surface;
surface.Init();
surface.SetUnicodeMode(SC_CP_UTF8 == pdoc->dbcsCodePage);
unsigned int posLineStart = pdoc->LineStart(line);
LineLayout ll;
@@ -485,7 +489,7 @@ void Editor::ScrollTo(int line) {
}
}
void Editor::ScrollText(int linesToMove) {
void Editor::ScrollText(int /* linesToMove */) {
//Platform::DebugPrintf("Editor::ScrollText %d\n", linesToMove);
Redraw();
}
@@ -499,6 +503,19 @@ void Editor::HorizontalScrollTo(int xPos) {
Redraw();
}
void Editor::MoveCaretInsideView() {
PRectangle rcClient = GetTextRectangle();
Point pt = LocationFromPosition(currentPos);
if (pt.y < rcClient.top) {
MovePositionTo(PositionFromLocation(
Point(lastXChosen, rcClient.top)));
} else if ((pt.y + vs.lineHeight - 1) > rcClient.bottom) {
int yOfLastLineFullyDisplayed = rcClient.top + (LinesOnScreen()-1) * vs.lineHeight;
MovePositionTo(PositionFromLocation(
Point(lastXChosen, rcClient.top + yOfLastLineFullyDisplayed)));
}
}
void Editor::EnsureCaretVisible(bool useMargin) {
//Platform::DebugPrintf("EnsureCaretVisible %d\n", xOffset);
PRectangle rcClient = GetTextRectangle();
@@ -652,11 +669,10 @@ void Editor::PaintSelMargin(Surface *surfWindow, PRectangle &rc) {
sprintf(number, "%d", line + 1);
if (foldFlags & 64)
sprintf(number, "%X", pdoc->GetLevel(line));
int xpos = 0;
PRectangle rcNumber=rcMarker;
// Right justify
int width = surface->WidthText(vs.styles[STYLE_LINENUMBER].font, number, strlen(number));
xpos = rcNumber.right - width - 3;
int xpos = rcNumber.right - width - 3;
rcNumber.left = xpos;
if ((visibleLine < cs.LinesDisplayed()) && cs.GetVisible(line)) {
surface->DrawText(rcNumber, vs.styles[STYLE_LINENUMBER].font,
@@ -720,8 +736,8 @@ void Editor::LayoutLine(int line, Surface *surface, ViewStyle &vstyle, LineLayou
styleByte = pdoc->StyleAt(charInDoc);
if (vstyle.viewEOL || ((chDoc != '\r') && (chDoc != '\n'))) {
ll.chars[numCharsInLine] = chDoc;
ll.styles[numCharsInLine] = styleByte & styleMask;
ll.indicators[numCharsInLine] = styleByte & ~styleMask;
ll.styles[numCharsInLine] = static_cast<char>(styleByte & styleMask);
ll.indicators[numCharsInLine] = static_cast<char>(styleByte & ~styleMask);
numCharsInLine++;
}
}
@@ -1017,14 +1033,13 @@ void Editor::Paint(Surface *surfaceWindow, PRectangle rcArea) {
}
//Platform::DebugPrintf("start display %d, offset = %d\n", pdoc->Length(), xOffset);
Surface *surface = 0;
if (rcArea.right > vs.fixedColumnWidth) {
Surface *surface = surfaceWindow;
if (bufferedDraw) {
surface = &pixmapLine;
} else {
surface = surfaceWindow;
}
surface->SetUnicodeMode(SC_CP_UTF8 == pdoc->dbcsCodePage);
int visibleLine = topLine + screenLinePaintFirst;
int line = cs.DocFromDisplay(visibleLine);
@@ -1060,9 +1075,11 @@ void Editor::Paint(Surface *surfaceWindow, PRectangle rcArea) {
// Highlight the current braces if any
if ((braces[0] >= posLineStart) && (braces[0] < posLineEnd))
ll.styles[braces[0] - posLineStart] = bracesMatchStyle;
ll.styles[braces[0] - posLineStart] =
static_cast<char>(bracesMatchStyle);
if ((braces[1] >= posLineStart) && (braces[1] < posLineEnd))
ll.styles[braces[1] - posLineStart] = bracesMatchStyle;
ll.styles[braces[1] - posLineStart] =
static_cast<char>(bracesMatchStyle);
// Draw the line
if (cs.GetVisible(line))
@@ -1086,9 +1103,10 @@ void Editor::Paint(Surface *surfaceWindow, PRectangle rcArea) {
// Draw the Caret
if (line == lineCaret) {
int xposCaret = ll.positions[posCaret - posLineStart] + xStart;
int offset = Platform::Minimum(posCaret - posLineStart, LineLayout::maxLineLength);
int xposCaret = ll.positions[offset] + xStart;
int widthOverstrikeCaret =
ll.positions[posCaret - posLineStart + 1] - ll.positions[posCaret - posLineStart];
ll.positions[offset + 1] - ll.positions[offset];
if (posCaret == pdoc->Length()) // At end of document
widthOverstrikeCaret = vs.aveCharWidth;
if ((posCaret - posLineStart) >= ll.numCharsInLine) // At end of line
@@ -1163,8 +1181,10 @@ long Editor::FormatRange(bool draw, FORMATRANGE *pfr) {
Surface *surface = new Surface();
surface->Init(pfr->hdc);
surface->SetUnicodeMode(SC_CP_UTF8 == pdoc->dbcsCodePage);
Surface *surfaceMeasure = new Surface();
surfaceMeasure->Init(pfr->hdcTarget);
surfaceMeasure->SetUnicodeMode(SC_CP_UTF8 == pdoc->dbcsCodePage);
ViewStyle vsPrint(vs);
@@ -1270,6 +1290,10 @@ long Editor::FormatRange(bool draw, FORMATRANGE *pfr) {
return endPosPrint;
}
// Empty method is overridden on GTK+ to show / hide scrollbars
void Editor::ReconfigureScrollBars() {
}
void Editor::SetScrollBarsTo(PRectangle) {
RefreshStyleData();
@@ -1295,6 +1319,13 @@ void Editor::SetScrollBars() {
}
void Editor::AddChar(char ch) {
char s[2];
s[0] = ch;
s[1] = '\0';
AddCharUTF(s, 1);
}
void Editor::AddCharUTF(char *s, unsigned int len) {
bool wasSelection = currentPos != anchor;
ClearSelection();
if (inOverstrike && !wasSelection) {
@@ -1304,11 +1335,11 @@ void Editor::AddChar(char ch) {
}
}
}
pdoc->InsertChar(currentPos, ch);
SetEmptySelection(currentPos + 1);
pdoc->InsertString(currentPos, s, len);
SetEmptySelection(currentPos + len);
EnsureCaretVisible();
SetLastXChosen();
NotifyChar(ch);
NotifyChar(s[0]);
}
void Editor::ClearSelection() {
@@ -1429,7 +1460,7 @@ void Editor::DelCharBack() {
void Editor::NotifyFocus(bool) {
}
void Editor::NotifyStyleNeeded(int endStyleNeeded) {
void Editor::NotifyStyleToNeeded(int endStyleNeeded) {
SCNotification scn;
scn.nmhdr.code = SCN_STYLENEEDED;
scn.position = endStyleNeeded;
@@ -1437,7 +1468,7 @@ void Editor::NotifyStyleNeeded(int endStyleNeeded) {
}
void Editor::NotifyStyleNeeded(Document*, void *, int endStyleNeeded) {
NotifyStyleNeeded(endStyleNeeded);
NotifyStyleToNeeded(endStyleNeeded);
}
void Editor::NotifyChar(char ch) {
@@ -1582,13 +1613,17 @@ void Editor::NotifyModified(Document*, DocModification mh, void *) {
}
}
}
if (mh.modificationType & SC_MOD_BEFOREINSERT) {
NotifyNeedShown(mh.position, 0);
} else if (mh.modificationType & SC_MOD_BEFOREDELETE) {
NotifyNeedShown(mh.position, mh.length);
}
if (mh.linesAdded != 0) {
// Update contraction state for inserted and removed lines
// lineOfPos should be calculated in context of state before modification, shouldn't it
int lineOfPos = pdoc->LineFromPosition(mh.position);
if (mh.linesAdded > 0) {
NotifyNeedShown(mh.position, mh.length);
cs.InsertLines(lineOfPos, mh.linesAdded);
} else {
cs.DeleteLines(lineOfPos, -mh.linesAdded);
@@ -1642,7 +1677,7 @@ void Editor::NotifyModified(Document*, DocModification mh, void *) {
}
}
void Editor::NotifyDeleted(Document *document, void *userData) {
void Editor::NotifyDeleted(Document *, void *) {
/* Do nothing */
}
@@ -1806,6 +1841,10 @@ int Editor::KeyCommand(UINT iMessage) {
MovePositionTo(PositionFromLocation(
Point(lastXChosen, pt.y + vs.lineHeight)), true);
break;
case SCI_LINESCROLLDOWN:
ScrollTo(topLine + 1);
MoveCaretInsideView();
break;
case SCI_LINEUP:
MovePositionTo(PositionFromLocation(
Point(lastXChosen, pt.y - vs.lineHeight)));
@@ -1814,6 +1853,10 @@ int Editor::KeyCommand(UINT iMessage) {
MovePositionTo(PositionFromLocation(
Point(lastXChosen, pt.y - vs.lineHeight)), true);
break;
case SCI_LINESCROLLUP:
ScrollTo(topLine - 1);
MoveCaretInsideView();
break;
case SCI_CHARLEFT:
if (SelectionEmpty()) {
MovePositionTo(MovePositionSoVisible(currentPos - 1, -1));
@@ -1909,6 +1952,7 @@ int Editor::KeyCommand(UINT iMessage) {
break;
case SCI_DELETEBACK:
DelCharBack();
SetLastXChosen();
EnsureCaretVisible();
break;
case SCI_TAB:
@@ -1961,6 +2005,7 @@ int Editor::KeyCommand(UINT iMessage) {
int startWord = pdoc->NextWordStart(currentPos, -1);
pdoc->DeleteChars(startWord, currentPos - startWord);
MovePositionTo(startWord);
SetLastXChosen();
}
break;
case SCI_DELWORDRIGHT: {
@@ -2628,12 +2673,13 @@ char BraceOpposite(char ch) {
// TODO: should be able to extend styled region to find matching brace
// TODO: may need to make DBCS safe
// so should be moved into Document
int Editor::BraceMatch(int position, int maxReStyle) {
int Editor::BraceMatch(int position, int /*maxReStyle*/) {
char chBrace = pdoc->CharAt(position);
char chSeek = BraceOpposite(chBrace);
if (!chSeek)
if (chSeek == '\0')
return - 1;
char styBrace = pdoc->StyleAt(position) & pdoc->stylingBitsMask;
char styBrace = static_cast<char>(
pdoc->StyleAt(position) & pdoc->stylingBitsMask);
int direction = -1;
if (chBrace == '(' || chBrace == '[' || chBrace == '{' || chBrace == '<')
direction = 1;
@@ -2641,7 +2687,7 @@ int Editor::BraceMatch(int position, int maxReStyle) {
position = position + direction;
while ((position >= 0) && (position < pdoc->Length())) {
char chAtPos = pdoc->CharAt(position);
char styAtPos = pdoc->StyleAt(position) & pdoc->stylingBitsMask;
char styAtPos = static_cast<char>(pdoc->StyleAt(position) & pdoc->stylingBitsMask);
if ((position > pdoc->GetEndStyled()) || (styAtPos == styBrace)) {
if (chAtPos == chBrace)
depth++;
@@ -2750,6 +2796,11 @@ void Editor::EnsureLineVisible(int line) {
}
}
static bool ValidMargin(WPARAM wParam) {
return wParam < ViewStyle::margins;
}
LRESULT Editor::WndProc(UINT iMessage, WPARAM wParam, LPARAM lParam) {
//Platform::DebugPrintf("S start wnd proc %d %d %d\n",iMessage, wParam, lParam);
@@ -3313,11 +3364,11 @@ LRESULT Editor::WndProc(UINT iMessage, WPARAM wParam, LPARAM lParam) {
break;
case SCI_STARTSTYLING:
pdoc->StartStyling(wParam, lParam);
pdoc->StartStyling(wParam, static_cast<char>(lParam));
break;
case SCI_SETSTYLING:
pdoc->SetStyleFor(wParam, lParam);
pdoc->SetStyleFor(wParam, static_cast<char>(lParam));
break;
case SCI_SETSTYLINGEX: // Specify a complete styling buffer
@@ -3345,6 +3396,44 @@ LRESULT Editor::WndProc(UINT iMessage, WPARAM wParam, LPARAM lParam) {
InvalidateStyleRedraw();
break;
case SCI_GETTABWIDTH:
return pdoc->tabInChars;
case SCI_SETINDENT:
pdoc->indentInChars = wParam;
InvalidateStyleRedraw();
break;
case SCI_GETINDENT:
return pdoc->indentInChars;
case SCI_SETUSETABS:
pdoc->useTabs = wParam;
InvalidateStyleRedraw();
break;
case SCI_GETUSETABS:
return pdoc->useTabs;
case SCI_SETLINEINDENTATION:
pdoc->SetLineIndentation(wParam, lParam);
break;
case SCI_GETLINEINDENTATION:
return pdoc->GetLineIndentation(wParam);
case SCI_GETLINEINDENTPOSITION:
return pdoc->GetLineIndentPosition(wParam);
case SCI_SETHSCROLLBAR :
horizontalScrollBarVisible = wParam;
SetScrollBars();
ReconfigureScrollBars();
break;
case SCI_GETHSCROLLBAR:
return horizontalScrollBarVisible;
case SCI_SETCODEPAGE:
pdoc->dbcsCodePage = wParam;
break;
@@ -3416,53 +3505,53 @@ LRESULT Editor::WndProc(UINT iMessage, WPARAM wParam, LPARAM lParam) {
return -1;
case SCI_SETMARGINTYPEN:
if (wParam >= 0 && wParam < ViewStyle::margins) {
if (ValidMargin(wParam)) {
vs.ms[wParam].symbol = (lParam == SC_MARGIN_SYMBOL);
InvalidateStyleRedraw();
}
break;
case SCI_GETMARGINTYPEN:
if (wParam >= 0 && wParam < ViewStyle::margins)
if (ValidMargin(wParam))
return vs.ms[wParam].symbol ? SC_MARGIN_SYMBOL : SC_MARGIN_NUMBER;
else
return 0;
case SCI_SETMARGINWIDTHN:
if (wParam >= 0 && wParam < ViewStyle::margins) {
if (ValidMargin(wParam)) {
vs.ms[wParam].width = lParam;
InvalidateStyleRedraw();
}
break;
case SCI_GETMARGINWIDTHN:
if (wParam >= 0 && wParam < ViewStyle::margins)
if (ValidMargin(wParam))
return vs.ms[wParam].width;
else
return 0;
case SCI_SETMARGINMASKN:
if (wParam >= 0 && wParam < ViewStyle::margins) {
if (ValidMargin(wParam)) {
vs.ms[wParam].mask = lParam;
InvalidateStyleRedraw();
}
break;
case SCI_GETMARGINMASKN:
if (wParam >= 0 && wParam < ViewStyle::margins)
if (ValidMargin(wParam))
return vs.ms[wParam].mask;
else
return 0;
case SCI_SETMARGINSENSITIVEN:
if (wParam >= 0 && wParam < ViewStyle::margins) {
if (ValidMargin(wParam)) {
vs.ms[wParam].sensitive = lParam;
InvalidateStyleRedraw();
}
break;
case SCI_GETMARGINSENSITIVEN:
if (wParam >= 0 && wParam < ViewStyle::margins)
if (ValidMargin(wParam))
return vs.ms[wParam].sensitive ? 1 : 0;
else
return 0;
@@ -3606,7 +3695,6 @@ LRESULT Editor::WndProc(UINT iMessage, WPARAM wParam, LPARAM lParam) {
case SCI_SEARCHNEXT:
case SCI_SEARCHPREV:
return SearchText(iMessage, wParam, lParam);
break;
case SCI_SETCARETPOLICY:
caretPolicy = wParam;
@@ -3745,6 +3833,8 @@ LRESULT Editor::WndProc(UINT iMessage, WPARAM wParam, LPARAM lParam) {
case SCI_LINETRANSPOSE:
case SCI_LOWERCASE:
case SCI_UPPERCASE:
case SCI_LINESCROLLDOWN:
case SCI_LINESCROLLUP:
return KeyCommand(iMessage);
case SCI_BRACEHIGHLIGHT:
@@ -3808,6 +3898,9 @@ LRESULT Editor::WndProc(UINT iMessage, WPARAM wParam, LPARAM lParam) {
SetSelection(currentPos, anchor); // Ensure selection inside document
return 0;
case SCI_SELECTIONISRECTANGLE:
return (selType == selRectangle) ? 1 : 0;
#ifdef MACRO_SUPPORT
case SCI_STARTRECORD:
recordingMacro = 1;

View File

@@ -38,6 +38,9 @@ public:
};
class Editor : public DocWatcher {
// Private so Editor objects can not be copied
Editor(const Editor &) : DocWatcher() {}
Editor &operator=(const Editor &) { return *this; }
protected: // ScintillaBase subclass needs access to much of Editor
// On GTK+, Scintilla is a container widget holding two scroll bars and a drawing area
@@ -61,13 +64,14 @@ protected: // ScintillaBase subclass needs access to much of Editor
int xOffset; // Horizontal scrolled amount in pixels
int xCaretMargin; // Ensure this many pixels visible on both sides of caret
bool horizontalScrollBarVisible;
Surface pixmapLine;
Surface pixmapSelMargin;
Surface pixmapSelPattern;
// Intellimouse support - currently only implemented for Windows
unsigned int ucWheelScrollLines;
short cWheelDelta; //wheel delta from roll
int cWheelDelta; //wheel delta from roll
KeyMap kmap;
@@ -171,6 +175,7 @@ protected: // ScintillaBase subclass needs access to much of Editor
void ScrollTo(int line);
virtual void ScrollText(int linesToMove);
void HorizontalScrollTo(int xPos);
void MoveCaretInsideView();
void EnsureCaretVisible(bool useMargin=true);
void ShowCaretAtCurrentPosition();
void DropCaret();
@@ -186,10 +191,12 @@ protected: // ScintillaBase subclass needs access to much of Editor
virtual void SetVerticalScrollPos() = 0;
virtual void SetHorizontalScrollPos() = 0;
virtual bool ModifyScrollBars(int nMax, int nPage) = 0;
virtual void ReconfigureScrollBars();
void SetScrollBarsTo(PRectangle rsClient);
void SetScrollBars();
virtual void AddChar(char ch);
void AddChar(char ch);
virtual void AddCharUTF(char *s, unsigned int len);
void ClearSelection();
void ClearAll();
void Cut();
@@ -207,7 +214,7 @@ protected: // ScintillaBase subclass needs access to much of Editor
virtual void NotifyChange() = 0;
virtual void NotifyFocus(bool focus);
virtual void NotifyParent(SCNotification scn) = 0;
virtual void NotifyStyleNeeded(int endStyleNeeded);
virtual void NotifyStyleToNeeded(int endStyleNeeded);
void NotifyChar(char ch);
void NotifySavePoint(bool isSavePoint);
void NotifyModifyAttempt();

View File

@@ -61,56 +61,58 @@ UINT KeyMap::Find(int key, int modifiers) {
}
KeyToCommand KeyMap::MapDefault[] = {
VK_DOWN, SCI_NORM, SCI_LINEDOWN,
VK_DOWN, SCI_SHIFT, SCI_LINEDOWNEXTEND,
VK_UP, SCI_NORM, SCI_LINEUP,
VK_UP, SCI_SHIFT, SCI_LINEUPEXTEND,
VK_LEFT, SCI_NORM, SCI_CHARLEFT,
VK_LEFT, SCI_SHIFT, SCI_CHARLEFTEXTEND,
VK_LEFT, SCI_CTRL, SCI_WORDLEFT,
VK_LEFT, SCI_CSHIFT, SCI_WORDLEFTEXTEND,
VK_RIGHT, SCI_NORM, SCI_CHARRIGHT,
VK_RIGHT, SCI_SHIFT, SCI_CHARRIGHTEXTEND,
VK_RIGHT, SCI_CTRL, SCI_WORDRIGHT,
VK_RIGHT, SCI_CSHIFT, SCI_WORDRIGHTEXTEND,
VK_HOME, SCI_NORM, SCI_VCHOME,
VK_HOME, SCI_SHIFT, SCI_VCHOMEEXTEND,
VK_HOME, SCI_CTRL, SCI_DOCUMENTSTART,
VK_HOME, SCI_CSHIFT, SCI_DOCUMENTSTARTEXTEND,
VK_END, SCI_NORM, SCI_LINEEND,
VK_END, SCI_SHIFT, SCI_LINEENDEXTEND,
VK_END, SCI_CTRL, SCI_DOCUMENTEND,
VK_END, SCI_CSHIFT, SCI_DOCUMENTENDEXTEND,
VK_PRIOR, SCI_NORM, SCI_PAGEUP,
VK_PRIOR, SCI_SHIFT, SCI_PAGEUPEXTEND,
VK_NEXT, SCI_NORM, SCI_PAGEDOWN,
VK_NEXT, SCI_SHIFT, SCI_PAGEDOWNEXTEND,
VK_DELETE, SCI_NORM, WM_CLEAR,
VK_DELETE, SCI_SHIFT, WM_CUT,
VK_DELETE, SCI_CTRL, SCI_DELWORDRIGHT,
VK_INSERT, SCI_NORM, SCI_EDITTOGGLEOVERTYPE,
VK_INSERT, SCI_SHIFT, WM_PASTE,
VK_INSERT, SCI_CTRL, WM_COPY,
VK_ESCAPE, SCI_NORM, SCI_CANCEL,
VK_BACK, SCI_NORM, SCI_DELETEBACK,
VK_BACK, SCI_CTRL, SCI_DELWORDLEFT,
'Z', SCI_CTRL, WM_UNDO,
'Y', SCI_CTRL, SCI_REDO,
'X', SCI_CTRL, WM_CUT,
'C', SCI_CTRL, WM_COPY,
'V', SCI_CTRL, WM_PASTE,
'A', SCI_CTRL, SCI_SELECTALL,
VK_TAB, SCI_NORM, SCI_TAB,
VK_TAB, SCI_SHIFT, SCI_BACKTAB,
VK_RETURN, SCI_NORM, SCI_NEWLINE,
VK_ADD, SCI_CTRL, SCI_ZOOMIN,
VK_SUBTRACT, SCI_CTRL, SCI_ZOOMOUT,
{VK_DOWN, SCI_NORM, SCI_LINEDOWN},
{VK_DOWN, SCI_SHIFT, SCI_LINEDOWNEXTEND},
{VK_DOWN, SCI_CTRL, SCI_LINESCROLLDOWN},
{VK_UP, SCI_NORM, SCI_LINEUP},
{VK_UP, SCI_SHIFT, SCI_LINEUPEXTEND},
{VK_UP, SCI_CTRL, SCI_LINESCROLLUP},
{VK_LEFT, SCI_NORM, SCI_CHARLEFT},
{VK_LEFT, SCI_SHIFT, SCI_CHARLEFTEXTEND},
{VK_LEFT, SCI_CTRL, SCI_WORDLEFT},
{VK_LEFT, SCI_CSHIFT, SCI_WORDLEFTEXTEND},
{VK_RIGHT, SCI_NORM, SCI_CHARRIGHT},
{VK_RIGHT, SCI_SHIFT, SCI_CHARRIGHTEXTEND},
{VK_RIGHT, SCI_CTRL, SCI_WORDRIGHT},
{VK_RIGHT, SCI_CSHIFT, SCI_WORDRIGHTEXTEND},
{VK_HOME, SCI_NORM, SCI_VCHOME},
{VK_HOME, SCI_SHIFT, SCI_VCHOMEEXTEND},
{VK_HOME, SCI_CTRL, SCI_DOCUMENTSTART},
{VK_HOME, SCI_CSHIFT, SCI_DOCUMENTSTARTEXTEND},
{VK_END, SCI_NORM, SCI_LINEEND},
{VK_END, SCI_SHIFT, SCI_LINEENDEXTEND},
{VK_END, SCI_CTRL, SCI_DOCUMENTEND},
{VK_END, SCI_CSHIFT, SCI_DOCUMENTENDEXTEND},
{VK_PRIOR, SCI_NORM, SCI_PAGEUP},
{VK_PRIOR, SCI_SHIFT, SCI_PAGEUPEXTEND},
{VK_NEXT, SCI_NORM, SCI_PAGEDOWN},
{VK_NEXT, SCI_SHIFT, SCI_PAGEDOWNEXTEND},
{VK_DELETE, SCI_NORM, WM_CLEAR},
{VK_DELETE, SCI_SHIFT, WM_CUT},
{VK_DELETE, SCI_CTRL, SCI_DELWORDRIGHT},
{VK_INSERT, SCI_NORM, SCI_EDITTOGGLEOVERTYPE},
{VK_INSERT, SCI_SHIFT, WM_PASTE},
{VK_INSERT, SCI_CTRL, WM_COPY},
{VK_ESCAPE, SCI_NORM, SCI_CANCEL},
{VK_BACK, SCI_NORM, SCI_DELETEBACK},
{VK_BACK, SCI_CTRL, SCI_DELWORDLEFT},
{'Z', SCI_CTRL, WM_UNDO},
{'Y', SCI_CTRL, SCI_REDO},
{'X', SCI_CTRL, WM_CUT},
{'C', SCI_CTRL, WM_COPY},
{'V', SCI_CTRL, WM_PASTE},
{'A', SCI_CTRL, SCI_SELECTALL},
{VK_TAB, SCI_NORM, SCI_TAB},
{VK_TAB, SCI_SHIFT, SCI_BACKTAB},
{VK_RETURN, SCI_NORM, SCI_NEWLINE},
{VK_ADD, SCI_CTRL, SCI_ZOOMIN},
{VK_SUBTRACT, SCI_CTRL, SCI_ZOOMOUT},
//'L', SCI_CTRL, SCI_FORMFEED,
'L', SCI_CTRL, SCI_LINECUT,
'L', SCI_CSHIFT, SCI_LINEDELETE,
'T', SCI_CTRL, SCI_LINETRANSPOSE,
'U', SCI_CTRL, SCI_LOWERCASE,
'U', SCI_CSHIFT, SCI_UPPERCASE,
0,0,0,
{'L', SCI_CTRL, SCI_LINECUT},
{'L', SCI_CSHIFT, SCI_LINEDELETE},
{'T', SCI_CTRL, SCI_LINETRANSPOSE},
{'U', SCI_CTRL, SCI_LOWERCASE},
{'U', SCI_CSHIFT, SCI_UPPERCASE},
{0,0,0},
};

View File

@@ -26,7 +26,7 @@ LexerModule::LexerModule(int language_, LexerFunction fn_) :
}
void LexerModule::Colourise(unsigned int startPos, int lengthDoc, int initStyle,
int language, WordList *keywordlists[], StylingContext &styler) {
int language, WordList *keywordlists[], Accessor &styler) {
LexerModule *lm = base;
while (lm) {
if (lm->language == language) {
@@ -43,5 +43,3 @@ void LexerModule::Colourise(unsigned int startPos, int lengthDoc, int initStyle,
styler.ColourTo(startPos + lengthDoc - 1, 0);
}
}

View File

@@ -17,7 +17,7 @@
#include "Scintilla.h"
#include "SciLexer.h"
static bool classifyWordCpp(unsigned int start, unsigned int end, WordList &keywords, StylingContext &styler) {
static bool classifyWordCpp(unsigned int start, unsigned int end, WordList &keywords, Accessor &styler) {
char s[100];
bool wordIsNumber = isdigit(styler[start]) || (styler[start] == '.');
bool wordIsUUID = false;
@@ -39,38 +39,47 @@ static bool classifyWordCpp(unsigned int start, unsigned int end, WordList &keyw
}
static void ColouriseCppDoc(unsigned int startPos, int length, int initStyle, WordList *keywordlists[],
StylingContext &styler) {
Accessor &styler) {
WordList &keywords = *keywordlists[0];
styler.StartAt(startPos);
bool fold = styler.GetPropSet().GetInt("fold");
bool fold = styler.GetPropertyInt("fold");
int lineCurrent = styler.GetLine(startPos);
int levelPrev = styler.LevelAt(lineCurrent) & SC_FOLDLEVELNUMBERMASK;
int levelCurrent = levelPrev;
int state = initStyle;
if (state == SCE_C_STRINGEOL) // Does not leak onto next line
state = SCE_C_DEFAULT;
char chPrev = ' ';
char chNext = styler[startPos];
unsigned int lengthDoc = startPos + length;
int visChars = 0;
styler.StartSegment(startPos);
bool lastWordWasUUID = false;
for (unsigned int i = startPos; i <= lengthDoc; i++) {
for (unsigned int i = startPos; i < lengthDoc; i++) {
char ch = chNext;
chNext = styler.SafeGetCharAt(i + 1);
if ((fold) && ((ch == '\r' && chNext != '\n') || (ch == '\n'))) {
int lev = levelPrev;
if (visChars == 0)
lev |= SC_FOLDLEVELWHITEFLAG;
if ((levelCurrent > levelPrev) && (visChars > 0))
lev |= SC_FOLDLEVELHEADERFLAG;
styler.SetLevel(lineCurrent, lev);
lineCurrent++;
visChars = 0;
levelPrev = levelCurrent;
if ((ch == '\r' && chNext != '\n') || (ch == '\n')) {
// End of line
if (state == SCE_C_STRINGEOL) {
styler.ColourTo(i, state);
state = SCE_C_DEFAULT;
}
if (fold) {
int lev = levelPrev;
if (visChars == 0)
lev |= SC_FOLDLEVELWHITEFLAG;
if ((levelCurrent > levelPrev) && (visChars > 0))
lev |= SC_FOLDLEVELHEADERFLAG;
styler.SetLevel(lineCurrent, lev);
lineCurrent++;
visChars = 0;
levelPrev = levelCurrent;
}
}
if (!isspace(ch))
visChars++;
@@ -82,12 +91,6 @@ static void ColouriseCppDoc(unsigned int startPos, int length, int initStyle, Wo
continue;
}
if (state == SCE_C_STRINGEOL) {
if (ch != '\r' && ch != '\n') {
styler.ColourTo(i-1, state);
state = SCE_C_DEFAULT;
}
}
if (state == SCE_C_DEFAULT) {
if (iswordstart(ch)) {
styler.ColourTo(i-1, state);
@@ -148,7 +151,7 @@ static void ColouriseCppDoc(unsigned int startPos, int length, int initStyle, Wo
}
} else {
if (state == SCE_C_PREPROCESSOR) {
if ((ch == '\r' || ch == '\n') && (chPrev != '\\')) {
if ((ch == '\r' || ch == '\n') && !(chPrev == '\\' || chPrev == '\r')) {
styler.ColourTo(i-1, state);
state = SCE_C_DEFAULT;
}
@@ -163,7 +166,7 @@ static void ColouriseCppDoc(unsigned int startPos, int length, int initStyle, Wo
}
} else if (state == SCE_C_COMMENTDOC) {
if (ch == '/' && chPrev == '*') {
if (((i > styler.GetStartSegment() + 3) || (
if (((i > styler.GetStartSegment() + 2) || (
(initStyle == SCE_C_COMMENTDOC) &&
(styler.GetStartSegment() == static_cast<unsigned int>(startPos))))) {
styler.ColourTo(i, state);
@@ -177,7 +180,7 @@ static void ColouriseCppDoc(unsigned int startPos, int length, int initStyle, Wo
}
} else if (state == SCE_C_STRING) {
if ((ch == '\r' || ch == '\n') && (chPrev != '\\')) {
styler.ColourTo(i-1, state);
styler.ColourTo(i-1, SCE_C_STRINGEOL);
state = SCE_C_STRINGEOL;
} else if (ch == '\\') {
if (chNext == '\"' || chNext == '\'' || chNext == '\\') {
@@ -194,7 +197,7 @@ static void ColouriseCppDoc(unsigned int startPos, int length, int initStyle, Wo
}
} else if (state == SCE_C_CHARACTER) {
if ((ch == '\r' || ch == '\n') && (chPrev != '\\')) {
styler.ColourTo(i-1, state);
styler.ColourTo(i-1, SCE_C_STRINGEOL);
state = SCE_C_STRINGEOL;
} else if (ch == '\\') {
if (chNext == '\"' || chNext == '\'' || chNext == '\\') {

View File

@@ -18,11 +18,11 @@
#include "SciLexer.h"
enum { eScriptNone, eScriptJS, eScriptVBS, eScriptPython };
static int segIsScriptingIndicator(StylingContext &styler, unsigned int start, unsigned int end, int prevValue) {
static int segIsScriptingIndicator(Accessor &styler, unsigned int start, unsigned int end, int prevValue) {
char s[100];
s[0] = '\0';
for (unsigned int i = 0; i < end - start + 1 && i < 30; i++) {
s[i] = tolower(styler[start + i]);
s[i] = static_cast<char>(tolower(styler[start + i]));
s[i + 1] = '\0';
}
//Platform::DebugPrintf("Scripting indicator [%s]\n", s);
@@ -38,7 +38,7 @@ static int segIsScriptingIndicator(StylingContext &styler, unsigned int start, u
return prevValue;
}
static void classifyAttribHTML(unsigned int start, unsigned int end, WordList &keywords, StylingContext &styler) {
static void classifyAttribHTML(unsigned int start, unsigned int end, WordList &keywords, Accessor &styler) {
bool wordIsNumber = isdigit(styler[start]) || (styler[start] == '.') ||
(styler[start] == '-') || (styler[start] == '#');
char chAttr = SCE_H_ATTRIBUTEUNKNOWN;
@@ -48,7 +48,7 @@ static void classifyAttribHTML(unsigned int start, unsigned int end, WordList &k
char s[100];
s[0] = '\0';
for (unsigned int i = 0; i < end - start + 1 && i < 30; i++) {
s[i] = tolower(styler[start + i]);
s[i] = static_cast<char>(tolower(styler[start + i]));
s[i + 1] = '\0';
}
if (keywords.InList(s))
@@ -58,14 +58,14 @@ static void classifyAttribHTML(unsigned int start, unsigned int end, WordList &k
}
static int classifyTagHTML(unsigned int start, unsigned int end,
WordList &keywords, StylingContext &styler) {
WordList &keywords, Accessor &styler) {
char s[100];
// Copy after the '<'
unsigned int i = 0;
for (unsigned int cPos=start; cPos <= end && i < 30; cPos++) {
char ch = styler[cPos];
if (ch != '<')
s[i++] = tolower(ch);
s[i++] = static_cast<char>(tolower(ch));
}
s[i] = '\0';
char chAttr = SCE_H_TAGUNKNOWN;
@@ -86,7 +86,7 @@ static int classifyTagHTML(unsigned int start, unsigned int end,
}
static void classifyWordHTJS(unsigned int start, unsigned int end,
WordList &keywords, StylingContext &styler) {
WordList &keywords, Accessor &styler) {
char s[100];
bool wordIsNumber = isdigit(styler[start]) || (styler[start] == '.');
for (unsigned int i = 0; i < end - start + 1 && i < 30; i++) {
@@ -104,7 +104,7 @@ static void classifyWordHTJS(unsigned int start, unsigned int end,
}
static void classifyWordHTJSA(unsigned int start, unsigned int end,
WordList &keywords, StylingContext &styler) {
WordList &keywords, Accessor &styler) {
char s[100];
bool wordIsNumber = isdigit(styler[start]) || (styler[start] == '.');
for (unsigned int i = 0; i < end - start + 1 && i < 30; i++) {
@@ -121,11 +121,11 @@ static void classifyWordHTJSA(unsigned int start, unsigned int end,
styler.ColourTo(end, chAttr);
}
static int classifyWordHTVB(unsigned int start, unsigned int end, WordList &keywords, StylingContext &styler) {
static int classifyWordHTVB(unsigned int start, unsigned int end, WordList &keywords, Accessor &styler) {
char s[100];
bool wordIsNumber = isdigit(styler[start]) || (styler[start] == '.');
for (unsigned int i = 0; i < end - start + 1 && i < 30; i++) {
s[i] = tolower(styler[start + i]);
s[i] = static_cast<char>(tolower(styler[start + i]));
s[i + 1] = '\0';
}
char chAttr = SCE_HB_IDENTIFIER;
@@ -145,11 +145,11 @@ static int classifyWordHTVB(unsigned int start, unsigned int end, WordList &keyw
return SCE_HB_DEFAULT;
}
static int classifyWordHTVBA(unsigned int start, unsigned int end, WordList &keywords, StylingContext &styler) {
static int classifyWordHTVBA(unsigned int start, unsigned int end, WordList &keywords, Accessor &styler) {
char s[100];
bool wordIsNumber = isdigit(styler[start]) || (styler[start] == '.');
for (unsigned int i = 0; i < end - start + 1 && i < 30; i++) {
s[i] = tolower(styler[start + i]);
s[i] = static_cast<char>(tolower(styler[start + i]));
s[i + 1] = '\0';
}
char chAttr = SCE_HBA_IDENTIFIER;
@@ -169,7 +169,7 @@ static int classifyWordHTVBA(unsigned int start, unsigned int end, WordList &key
return SCE_HBA_DEFAULT;
}
static void classifyWordHTPy(unsigned int start, unsigned int end, WordList &keywords, StylingContext &styler, char *prevWord) {
static void classifyWordHTPy(unsigned int start, unsigned int end, WordList &keywords, Accessor &styler, char *prevWord) {
char s[100];
bool wordIsNumber = isdigit(styler[start]);
for (unsigned int i = 0; i < end - start + 1 && i < 30; i++) {
@@ -189,7 +189,7 @@ static void classifyWordHTPy(unsigned int start, unsigned int end, WordList &key
strcpy(prevWord, s);
}
static void classifyWordHTPyA(unsigned int start, unsigned int end, WordList &keywords, StylingContext &styler, char *prevWord) {
static void classifyWordHTPyA(unsigned int start, unsigned int end, WordList &keywords, Accessor &styler, char *prevWord) {
char s[100];
bool wordIsNumber = isdigit(styler[start]);
for (unsigned int i = 0; i < end - start + 1 && i < 30; i++) {
@@ -226,7 +226,7 @@ static bool isLineEnd(char ch) {
}
static void ColouriseHyperTextDoc(unsigned int startPos, int length, int initStyle, WordList *keywordlists[],
StylingContext &styler) {
Accessor &styler) {
WordList &keywords=*keywordlists[0];
WordList &keywords2=*keywordlists[1];
@@ -261,7 +261,7 @@ static void ColouriseHyperTextDoc(unsigned int startPos, int length, int initSty
char chPrev2 = ' ';
styler.StartSegment(startPos);
int lengthDoc = startPos + length;
for (int i = startPos; i <= lengthDoc; i++) {
for (int i = startPos; i < lengthDoc; i++) {
char ch = styler[i];
char chNext = styler.SafeGetCharAt(i + 1);
char chNext2 = styler.SafeGetCharAt(i + 2);

View File

@@ -17,7 +17,7 @@
#include "Scintilla.h"
#include "SciLexer.h"
static void ColouriseBatchLine(char *lineBuffer, int endLine, StylingContext &styler) {
static void ColouriseBatchLine(char *lineBuffer, int endLine, Accessor &styler) {
if (0 == strncmp(lineBuffer, "REM", 3)) {
styler.ColourTo(endLine, 1);
} else if (0 == strncmp(lineBuffer, "rem", 3)) {
@@ -33,7 +33,7 @@ static void ColouriseBatchLine(char *lineBuffer, int endLine, StylingContext &st
}
}
static void ColouriseBatchDoc(unsigned int startPos, int length, int, WordList *[], StylingContext &styler) {
static void ColouriseBatchDoc(unsigned int startPos, int length, int, WordList *[], Accessor &styler) {
char lineBuffer[1024];
styler.StartAt(startPos);
styler.StartSegment(startPos);
@@ -49,7 +49,7 @@ static void ColouriseBatchDoc(unsigned int startPos, int length, int, WordList *
ColouriseBatchLine(lineBuffer, startPos + length, styler);
}
static void ColourisePropsLine(char *lineBuffer, int lengthLine, int startLine, int endPos, StylingContext &styler) {
static void ColourisePropsLine(char *lineBuffer, int lengthLine, int startLine, int endPos, Accessor &styler) {
int i = 0;
while (isspace(lineBuffer[i]) && (i < lengthLine)) // Skip initial spaces
i++;
@@ -75,7 +75,7 @@ static void ColourisePropsLine(char *lineBuffer, int lengthLine, int startLine,
}
}
static void ColourisePropsDoc(unsigned int startPos, int length, int, WordList *[], StylingContext &styler) {
static void ColourisePropsDoc(unsigned int startPos, int length, int, WordList *[], Accessor &styler) {
char lineBuffer[1024];
styler.StartAt(startPos);
styler.StartSegment(startPos);
@@ -96,7 +96,7 @@ static void ColourisePropsDoc(unsigned int startPos, int length, int, WordList *
ColourisePropsLine(lineBuffer, linePos, startLine, startPos + length, styler);
}
static void ColouriseMakeLine(char *lineBuffer, int lengthLine, int endPos, StylingContext &styler) {
static void ColouriseMakeLine(char *lineBuffer, int lengthLine, int endPos, Accessor &styler) {
int i = 0;
while (isspace(lineBuffer[i]) && (i < lengthLine))
i++;
@@ -107,7 +107,7 @@ static void ColouriseMakeLine(char *lineBuffer, int lengthLine, int endPos, Styl
}
}
static void ColouriseMakeDoc(unsigned int startPos, int length, int, WordList *[], StylingContext &styler) {
static void ColouriseMakeDoc(unsigned int startPos, int length, int, WordList *[], Accessor &styler) {
char lineBuffer[1024];
styler.StartAt(startPos);
styler.StartSegment(startPos);
@@ -123,7 +123,7 @@ static void ColouriseMakeDoc(unsigned int startPos, int length, int, WordList *[
ColouriseMakeLine(lineBuffer, linePos, startPos + length, styler);
}
static void ColouriseErrorListLine(char *lineBuffer, int lengthLine, int endPos, StylingContext &styler) {
static void ColouriseErrorListLine(char *lineBuffer, int lengthLine, int endPos, Accessor &styler) {
if (lineBuffer[0] == '>') {
// Command or return status
styler.ColourTo(endPos, 4);
@@ -158,7 +158,6 @@ static void ColouriseErrorListLine(char *lineBuffer, int lengthLine, int endPos,
state = 14;
} else if (state == 11 && lineBuffer[i] == ')') {
state = 12;
break;
} else if (state == 12 && lineBuffer[i] == ':') {
state = 13;
} else if (state == 14 && lineBuffer[i] == ')') {
@@ -170,7 +169,7 @@ static void ColouriseErrorListLine(char *lineBuffer, int lengthLine, int endPos,
}
if (state == 3) {
styler.ColourTo(endPos, 2);
} else if ((state == 14) || (state == 15)) {
} else if ((state == 13) || (state == 14) || (state == 15)) {
styler.ColourTo(endPos, 3);
} else {
styler.ColourTo(endPos, 0);
@@ -178,7 +177,7 @@ static void ColouriseErrorListLine(char *lineBuffer, int lengthLine, int endPos,
}
}
static void ColouriseErrorListDoc(unsigned int startPos, int length, int, WordList *[], StylingContext &styler) {
static void ColouriseErrorListDoc(unsigned int startPos, int length, int, WordList *[], Accessor &styler) {
char lineBuffer[1024];
styler.StartAt(startPos);
styler.StartSegment(startPos);

View File

@@ -31,7 +31,7 @@ inline bool isPerlOperator(char ch) {
return false;
}
static int classifyWordPerl(unsigned int start, unsigned int end, WordList &keywords, StylingContext &styler) {
static int classifyWordPerl(unsigned int start, unsigned int end, WordList &keywords, Accessor &styler) {
char s[100];
bool wordIsNumber = isdigit(styler[start]) || (styler[start] == '.');
for (unsigned int i = 0; i < end - start + 1 && i < 30; i++) {
@@ -54,7 +54,7 @@ static bool isEndVar(char ch) {
ch != '_' && ch != '\'';
}
static bool isMatch(StylingContext &styler, int lengthDoc, int pos, const char *val) {
static bool isMatch(Accessor &styler, int lengthDoc, int pos, const char *val) {
if ((pos + static_cast<int>(strlen(val))) >= lengthDoc) {
return false;
}
@@ -67,16 +67,6 @@ static bool isMatch(StylingContext &styler, int lengthDoc, int pos, const char *
return true;
}
static bool isOKQuote(char ch) {
if (isalnum(ch))
return false;
if (isspace(ch))
return false;
if (iscntrl(ch))
return false;
return true;
}
static char opposite(char ch) {
if (ch == '(')
return ')';
@@ -90,7 +80,7 @@ static char opposite(char ch) {
}
static void ColourisePerlDoc(unsigned int startPos, int length, int initStyle,
WordList *keywordlists[], StylingContext &styler) {
WordList *keywordlists[], Accessor &styler) {
// Lexer for perl often has to backtrack to start of current style to determine
// which characters are being used as quotes, how deeply nested is the
@@ -120,7 +110,7 @@ static void ColourisePerlDoc(unsigned int startPos, int length, int initStyle,
char chPrev = ' ';
char chNext = styler[startPos];
styler.StartSegment(startPos);
for (int i = startPos; i <= lengthDoc; i++) {
for (int i = startPos; i < lengthDoc; i++) {
char ch = chNext;
chNext = styler.SafeGetCharAt(i + 1);
char chNext2 = styler.SafeGetCharAt(i + 2);

View File

@@ -17,7 +17,7 @@
#include "Scintilla.h"
#include "SciLexer.h"
static void classifyWordPy(unsigned int start, unsigned int end, WordList &keywords, StylingContext &styler, char *prevWord) {
static void ClassifyWordPy(unsigned int start, unsigned int end, WordList &keywords, Accessor &styler, char *prevWord) {
char s[100];
bool wordIsNumber = isdigit(styler[start]);
for (unsigned int i = 0; i < end - start + 1 && i < 30; i++) {
@@ -37,56 +37,70 @@ static void classifyWordPy(unsigned int start, unsigned int end, WordList &keywo
strcpy(prevWord, s);
}
static bool IsPyComment(StylingContext &styler, int pos, int len) {
static bool IsPyComment(Accessor &styler, int pos, int len) {
return len>0 && styler[pos]=='#';
}
static void ColourisePyDoc(unsigned int startPos, int length, int initStyle,
WordList *keywordlists[], StylingContext &styler) {
WordList *keywordlists[], Accessor &styler) {
int lengthDoc = startPos + length;
// Backtrack to previous line in case need to fix its fold status or tab whinging
int lineCurrent = styler.GetLine(startPos);
if (startPos > 0) {
if (lineCurrent > 0) {
lineCurrent--;
startPos = styler.LineStart(lineCurrent);
}
}
// Python uses a different mask because bad indentation is marked by oring with 32
styler.StartAt(startPos, 127);
WordList &keywords = *keywordlists[0];
//Platform::DebugPrintf("Python coloured\n");
bool fold = styler.GetPropSet().GetInt("fold");
int whingeLevel = styler.GetPropSet().GetInt("tab.timmy.whinge.level");
bool fold = styler.GetPropertyInt("fold");
int whingeLevel = styler.GetPropertyInt("tab.timmy.whinge.level");
char prevWord[200];
prevWord[0] = '\0';
if (length == 0)
return ;
int lineCurrent = styler.GetLine(startPos);
int spaceFlags = 0;
// TODO: Need to check previous line for indentation for both folding and bad indentation
int indentCurrent = styler.IndentAmount(lineCurrent, &spaceFlags, IsPyComment);
int state = initStyle & 31;
int indentCurrent = styler.IndentAmount(lineCurrent, &spaceFlags, IsPyComment);
if ((state == SCE_P_TRIPLE) || (state == SCE_P_TRIPLEDOUBLE))
indentCurrent |= SC_FOLDLEVELWHITEFLAG;
char chPrev = ' ';
char chPrev2 = ' ';
char chNext = styler[startPos];
char chNext2 = styler[startPos];
styler.StartSegment(startPos);
int lengthDoc = startPos + length;
bool atStartLine = true;
for (int i = startPos; i <= lengthDoc; i++) {
for (int i = startPos; i < lengthDoc; i++) {
if (atStartLine) {
char chBad = static_cast<char>(64);
char chGood = static_cast<char>(0);
char chFlags = chGood;
if (whingeLevel == 1) {
styler.SetFlags((spaceFlags & wsInconsistent) ? 64 : 0, state);
chFlags = (spaceFlags & wsInconsistent) ? chBad : chGood;
} else if (whingeLevel == 2) {
styler.SetFlags((spaceFlags & wsSpaceTab) ? 64 : 0, state);
chFlags = (spaceFlags & wsSpaceTab) ? chBad : chGood;
} else if (whingeLevel == 3) {
styler.SetFlags((spaceFlags & wsSpace) ? 64 : 0, state);
chFlags = (spaceFlags & wsSpace) ? chBad : chGood;
} else if (whingeLevel == 4) {
styler.SetFlags((spaceFlags & wsTab) ? 64 : 0, state);
chFlags = (spaceFlags & wsTab) ? chBad : chGood;
}
styler.SetFlags(chFlags, static_cast<char>(state));
atStartLine = false;
}
char ch = chNext;
chNext = styler.SafeGetCharAt(i + 1);
chNext2 = styler.SafeGetCharAt(i + 2);
char chNext2 = styler.SafeGetCharAt(i + 2);
if ((ch == '\r' && chNext != '\n') || (ch == '\n') || (i == lengthDoc)) {
if ((state == SCE_P_DEFAULT) || (state == SCE_P_TRIPLE) || (state == SCE_P_TRIPLEDOUBLE)) {
@@ -97,6 +111,8 @@ static void ColourisePyDoc(unsigned int startPos, int length, int initStyle,
int lev = indentCurrent;
int indentNext = styler.IndentAmount(lineCurrent + 1, &spaceFlags, IsPyComment);
if ((state == SCE_P_TRIPLE) || (state == SCE_P_TRIPLEDOUBLE))
indentNext |= SC_FOLDLEVELWHITEFLAG;
if (!(indentCurrent & SC_FOLDLEVELWHITEFLAG)) {
// Only non whitespace lines can be headers
if ((indentCurrent & SC_FOLDLEVELNUMBERMASK) < (indentNext & SC_FOLDLEVELNUMBERMASK)) {
@@ -167,7 +183,7 @@ static void ColourisePyDoc(unsigned int startPos, int length, int initStyle,
}
} else if (state == SCE_P_WORD) {
if (!iswordchar(ch)) {
classifyWordPy(styler.GetStartSegment(), i - 1, keywords, styler, prevWord);
ClassifyWordPy(styler.GetStartSegment(), i - 1, keywords, styler, prevWord);
state = SCE_P_DEFAULT;
if (ch == '#') {
state = chNext == '#' ? SCE_P_COMMENTBLOCK : SCE_P_COMMENTLINE;
@@ -245,7 +261,7 @@ static void ColourisePyDoc(unsigned int startPos, int length, int initStyle,
chPrev = ch;
}
if (state == SCE_P_WORD) {
classifyWordPy(styler.GetStartSegment(), lengthDoc, keywords, styler, prevWord);
ClassifyWordPy(styler.GetStartSegment(), lengthDoc, keywords, styler, prevWord);
} else {
styler.ColourTo(lengthDoc, state);
}

View File

@@ -17,11 +17,11 @@
#include "Scintilla.h"
#include "SciLexer.h"
static void classifyWordSQL(unsigned int start, unsigned int end, WordList &keywords, StylingContext &styler) {
static void classifyWordSQL(unsigned int start, unsigned int end, WordList &keywords, Accessor &styler) {
char s[100];
bool wordIsNumber = isdigit(styler[start]) || (styler[start] == '.');
for (unsigned int i = 0; i < end - start + 1 && i < 30; i++) {
s[i] = toupper(styler[start + i]);
s[i] = static_cast<char>(toupper(styler[start + i]));
s[i + 1] = '\0';
}
char chAttr = SCE_C_IDENTIFIER;
@@ -35,29 +35,27 @@ static void classifyWordSQL(unsigned int start, unsigned int end, WordList &keyw
}
static void ColouriseSQLDoc(unsigned int startPos, int length,
int initStyle, WordList *keywordlists[], StylingContext &styler) {
int initStyle, WordList *keywordlists[], Accessor &styler) {
WordList &keywords = *keywordlists[0];
styler.StartAt(startPos);
bool fold = styler.GetPropSet().GetInt("fold");
bool fold = styler.GetPropertyInt("fold");
int lineCurrent = styler.GetLine(startPos);
int spaceFlags = 0;
int indentCurrent = 0;
int state = initStyle;
char chPrev = ' ';
char chNext = styler[startPos];
styler.StartSegment(startPos);
unsigned int lengthDoc = startPos + length;
bool prevCr = false;
for (unsigned int i = startPos; i <= lengthDoc; i++) {
for (unsigned int i = startPos; i < lengthDoc; i++) {
char ch = chNext;
chNext = styler.SafeGetCharAt(i + 1);
if ((ch == '\r' && chNext != '\n') || (ch == '\n')) {
indentCurrent = styler.IndentAmount(lineCurrent, &spaceFlags);
int indentCurrent = styler.IndentAmount(lineCurrent, &spaceFlags);
int lev = indentCurrent;
if (!(indentCurrent & SC_FOLDLEVELWHITEFLAG)) {
// Only non whitespace lines can be headers

View File

@@ -17,12 +17,12 @@
#include "Scintilla.h"
#include "SciLexer.h"
static int classifyWordVB(unsigned int start, unsigned int end, WordList &keywords, StylingContext &styler) {
static int classifyWordVB(unsigned int start, unsigned int end, WordList &keywords, Accessor &styler) {
char s[100];
bool wordIsNumber = isdigit(styler[start]) || (styler[start] == '.');
for (unsigned int i = 0; i < end - start + 1 && i < 30; i++) {
s[i] = tolower(styler[start + i]);
s[i] = static_cast<char>(tolower(styler[start + i]));
s[i + 1] = '\0';
}
char chAttr = SCE_C_DEFAULT;
@@ -43,7 +43,7 @@ static int classifyWordVB(unsigned int start, unsigned int end, WordList &keywor
}
static void ColouriseVBDoc(unsigned int startPos, int length, int initStyle,
WordList *keywordlists[], StylingContext &styler) {
WordList *keywordlists[], Accessor &styler) {
WordList &keywords = *keywordlists[0];

View File

@@ -51,20 +51,6 @@ void LineMarker::Draw(Surface *surface, PRectangle &rc) {
} else if (markType == SC_MARK_PLUS) {
int armSize = dimOn2-2;
Point xpts[] = {
Point(centreX - armSize, centreY),
Point(centreX, centreY),
Point(centreX, centreY - armSize),
Point(centreX, centreY - armSize),
Point(centreX, centreY),
Point(centreX + armSize, centreY),
Point(centreX + armSize, centreY),
Point(centreX, centreY),
Point(centreX, centreY + armSize),
Point(centreX, centreY + armSize),
Point(centreX, centreY),
Point(centreX - armSize, centreY),
};
Point pts[] = {
Point(centreX - armSize, centreY - 1),
Point(centreX - 1, centreY - 1),
@@ -90,12 +76,6 @@ void LineMarker::Draw(Surface *surface, PRectangle &rc) {
Point(centreX + armSize, centreY +1),
Point(centreX - armSize, centreY + 1),
};
Point xpts[] = {
Point(centreX - armSize, centreY),
Point(centreX + armSize, centreY),
Point(centreX + armSize, centreY),
Point(centreX - armSize, centreY),
};
surface->Polygon(pts, sizeof(pts) / sizeof(pts[0]),
fore.allocated, back.allocated);

View File

@@ -39,7 +39,7 @@ static bool GetFullLine(const char *&fpc, int &lenData, char *s, int len) {
fpc++;
lenData--;
}
*s++ = '\0';
*s = '\0';
return true;
}
} else if ((ch == '\\') && (lenData > 0) && ((*fpc == '\r') || (*fpc == '\n'))) {
@@ -122,7 +122,7 @@ SString PropSet::Get(const char *key) {
int PropSet::GetInt(const char *key, int defaultValue) {
SString val = Get(key);
if (val.length())
return Get(key).value();
return val.value();
else
return defaultValue;
}
@@ -376,7 +376,7 @@ bool WordList::InList(const char *s) {
for (int i = 0; words[i][0]; i++)
len++;
SortWordList(words, len);
for (int k = 0; k < (sizeof(starts) / sizeof(starts[0])); k++)
for (unsigned int k = 0; k < (sizeof(starts) / sizeof(starts[0])); k++)
starts[k] = -1;
for (int l = len - 1; l >= 0; l--) {
unsigned char indexChar = words[l][0];

View File

@@ -15,6 +15,8 @@
#include "SciLexer.h"
#include "PropSet.h"
#include "Accessor.h"
#include "WindowAccessor.h"
#include "DocumentAccessor.h"
#include "KeyWords.h"
#endif
#include "ContractionState.h"
@@ -50,11 +52,11 @@ void ScintillaBase::RefreshColourPalette(Palette &pal, bool want) {
ct.RefreshColourPalette(pal, want);
}
void ScintillaBase::AddChar(char ch) {
void ScintillaBase::AddCharUTF(char *s, unsigned int len) {
bool acActiveBeforeCharAdded = ac.Active();
Editor::AddChar(ch);
Editor::AddCharUTF(s, len);
if (acActiveBeforeCharAdded)
AutoCompleteChanged(ch);
AutoCompleteChanged(s[0]);
}
void ScintillaBase::Command(int cmdId) {
@@ -276,7 +278,8 @@ void ScintillaBase::Colourise(int start, int end) {
end = lengthDoc;
int len = end - start;
StylingContext styler(wMain.GetID(), props);
//WindowAccessor styler(wMain.GetID(), props);
DocumentAccessor styler(pdoc, props);
int styleStart = 0;
if (start > 0)
@@ -288,7 +291,7 @@ void ScintillaBase::Colourise(int start, int end) {
}
#endif
void ScintillaBase::NotifyStyleNeeded(int endStyleNeeded) {
void ScintillaBase::NotifyStyleToNeeded(int endStyleNeeded) {
#ifdef SCI_LEXER
if (lexLanguage != SCLEX_CONTAINER) {
int endStyled = Platform::SendScintilla(wMain.GetID(), SCI_GETENDSTYLED, 0, 0);
@@ -298,7 +301,7 @@ void ScintillaBase::NotifyStyleNeeded(int endStyleNeeded) {
return;
}
#endif
Editor::NotifyStyleNeeded(endStyleNeeded);
Editor::NotifyStyleToNeeded(endStyleNeeded);
}
LRESULT ScintillaBase::WndProc(UINT iMessage, WPARAM wParam, LPARAM lParam) {
@@ -321,10 +324,21 @@ LRESULT ScintillaBase::WndProc(UINT iMessage, WPARAM wParam, LPARAM lParam) {
AutoCompleteCompleted();
break;
case SCI_AUTOCSETSEPARATOR:
ac.SetSeparator(wParam);
break;
case SCI_AUTOCGETSEPARATOR:
return ac.GetSeparator();
case SCI_AUTOCSTOPS:
ac.SetStopChars(reinterpret_cast<char *>(lParam));
break;
case SCI_AUTOCSELECT:
ac.Select(reinterpret_cast<char *>(lParam));
break;
case SCI_CALLTIPSHOW: {
AutoCompleteCancel();
if (!ct.wCallTip.Created()) {
@@ -384,7 +398,7 @@ LRESULT ScintillaBase::WndProc(UINT iMessage, WPARAM wParam, LPARAM lParam) {
break;
case SCI_SETKEYWORDS:
if ((wParam >= 0) && (wParam < numWordLists)) {
if (wParam < numWordLists) {
keyWordLists[wParam]->Clear();
keyWordLists[wParam]->Set(reinterpret_cast<const char *>(lParam));
}

View File

@@ -7,6 +7,9 @@
#define SCINTILLABASE_H
class ScintillaBase : public Editor {
// Private so ScintillaBase objects can not be copied
ScintillaBase(const ScintillaBase &) : Editor() {}
ScintillaBase &operator=(const ScintillaBase &) { return *this; }
protected:
// Enumeration of commands and child windows
enum {
@@ -42,7 +45,7 @@ protected:
virtual void RefreshColourPalette(Palette &pal, bool want);
virtual void AddChar(char ch);
virtual void AddCharUTF(char *s, unsigned int len);
void Command(int cmdId);
virtual int KeyCommand(UINT iMessage);
@@ -59,7 +62,7 @@ protected:
virtual void ButtonDown(Point pt, unsigned int curTime, bool shift, bool ctrl, bool alt);
virtual void NotifyStyleNeeded(int endStyleNeeded);
virtual void NotifyStyleToNeeded(int endStyleNeeded);
public:
// Public so scintilla_send_message can use it
virtual LRESULT WndProc(UINT iMessage, WPARAM wParam, LPARAM lParam);

View File

@@ -16,6 +16,18 @@ Style::Style() {
false, false, false);
}
Style::Style(const Style &source) {
Clear(Colour(0,0,0), Colour(0xff,0xff,0xff),
0, 0,
false, false, false);
fore.desired = source.fore.desired;
back.desired = source.back.desired;
bold = source.bold;
italic = source.italic;
size = source.size;
eolFilled = source.eolFilled;
}
Style::~Style() {
if (aliasOfDefaultFont)
font.SetID(0);
@@ -78,7 +90,7 @@ void Style::Realise(Surface &surface, int zoomLevel, Style *defaultStyle) {
font.SetID(0);
else
font.Release();
int deviceHeight = (sizeZoomed * surface.LogPixelsY()) / 72;
int deviceHeight = surface.DeviceHeightFont(sizeZoomed);
aliasOfDefaultFont = defaultStyle &&
(EquivalentFontTo(defaultStyle) || !fontName);
if (aliasOfDefaultFont) {
@@ -99,5 +111,3 @@ void Style::Realise(Surface &surface, int zoomLevel, Style *defaultStyle) {
aveCharWidth = surface.AverageCharWidth(font);
spaceWidth = surface.WidthChar(font, ' ');
}

View File

@@ -26,6 +26,7 @@ public:
unsigned int spaceWidth;
Style();
Style(const Style &source);
~Style();
Style &operator=(const Style &source);
void Clear(Colour fore_, Colour back_,

View File

@@ -0,0 +1,77 @@
// UniConversion.h - functions to handle UFT-8 and UCS-2 strings
// Copyright 1998-2000 by Neil Hodgson <neilh@scintilla.org>
// The License.txt file describes the conditions under which this software may be distributed.
#include <stdlib.h>
#include "UniConversion.h"
unsigned int UTF8Length(const wchar_t *uptr, unsigned int tlen) {
unsigned int len = 0;
for (unsigned int i = 0; i < tlen && uptr[i]; i++) {
unsigned int uch = uptr[i];
if (uch < 0x80)
len++;
else if (uch < 0x800)
len+=2;
else
len +=3;
}
return len;
}
void UTF8FromUCS2(const wchar_t *uptr, unsigned int tlen, char *putf, unsigned int len) {
int k = 0;
for (unsigned int i = 0; i < tlen && uptr[i]; i++) {
unsigned int uch = uptr[i];
if (uch < 0x80) {
putf[k++] = static_cast<char>(uch);
} else if (uch < 0x800) {
putf[k++] = static_cast<char>(0xC0 | (uch >> 6));
putf[k++] = static_cast<char>(0x80 | (uch & 0x3f));
} else {
putf[k++] = static_cast<char>(0xE0 | (uch >> 12));
putf[k++] = static_cast<char>(0x80 | ((uch >> 6) & 0x3f));
putf[k++] = static_cast<char>(0x80 | (uch & 0x3f));
}
}
putf[len] = '\0';
}
unsigned int UCS2Length(const char *s, unsigned int len) {
unsigned int ulen = 0;
for (unsigned int i=0;i<len;i++) {
unsigned char ch = static_cast<unsigned char>(s[i]);
if ((ch < 0x80) || (ch > (0x80 + 0x40)))
ulen++;
}
return ulen;
}
unsigned int UCS2FromUTF8(const char *s, unsigned int len, wchar_t *tbuf, unsigned int tlen) {
#ifdef USE_API
return ::MultiByteToWideChar(CP_UTF8, 0, s, len, tbuf, tlen);
#else
unsigned int ui=0;
const unsigned char *us = reinterpret_cast<const unsigned char *>(s);
unsigned int i=0;
while ((i<len) && (ui<tlen)) {
unsigned char ch = us[i++];
if (ch < 0x80) {
tbuf[ui] = ch;
} else if (ch < 0x80 + 0x40 + 0x20) {
tbuf[ui] = static_cast<wchar_t>((ch & 0x1F) << 6);
ch = us[i++];
tbuf[ui] = static_cast<wchar_t>(tbuf[ui] + (ch & 0x7F));
} else {
tbuf[ui] = static_cast<wchar_t>((ch & 0xF) << 12);
ch = us[i++];
tbuf[ui] = static_cast<wchar_t>(tbuf[ui] + ((ch & 0x7F) << 6));
ch = us[i++];
tbuf[ui] = static_cast<wchar_t>(tbuf[ui] + (ch & 0x7F));
}
ui++;
}
return ui;
#endif
}

View File

@@ -0,0 +1,9 @@
// UniConversion.h - functions to handle UFT-8 and UCS-2 strings
// Copyright 1998-2000 by Neil Hodgson <neilh@scintilla.org>
// The License.txt file describes the conditions under which this software may be distributed.
unsigned int UTF8Length(const wchar_t *uptr, unsigned int tlen);
void UTF8FromUCS2(const wchar_t *uptr, unsigned int tlen, char *putf, unsigned int len);
unsigned int UCS2Length(const char *s, unsigned int len);
unsigned int UCS2FromUTF8(const char *s, unsigned int len, wchar_t *tbuf, unsigned int tlen);

View File

@@ -225,5 +225,3 @@ void ViewStyle::ClearStyles() {
void ViewStyle::SetStyleFontName(int styleIndex, const char *name) {
styles[styleIndex].fontName = fontNames.Save(name);
}

View File

@@ -11,20 +11,29 @@
#include "PropSet.h"
#include "Accessor.h"
#include "WindowAccessor.h"
#include "Scintilla.h"
bool Accessor::InternalIsLeadByte(char ch) {
WindowAccessor::~WindowAccessor() {
}
bool WindowAccessor::InternalIsLeadByte(char ch) {
#if PLAT_GTK
// TODO: support DBCS under GTK+
return false;
#elif PLAT_WIN
return IsDBCSLeadByteEx(codePage, ch);
if (SC_CP_UTF8 == codePage)
// For lexing, all characters >= 0x80 are treated the
// same so none is considered a lead byte.
return false;
else
return IsDBCSLeadByteEx(codePage, ch);
#elif PLAT_WX
return false;
#endif
}
void Accessor::Fill(int position) {
void WindowAccessor::Fill(int position) {
if (lenDoc == -1)
lenDoc = Platform::SendScintilla(id, WM_GETTEXTLENGTH, 0, 0);
startPos = position - slopSize;
@@ -40,46 +49,46 @@ void Accessor::Fill(int position) {
Platform::SendScintilla(id, EM_GETTEXTRANGE, 0, reinterpret_cast<LPARAM>(&tr));
}
char Accessor::StyleAt(int position) {
char WindowAccessor::StyleAt(int position) {
return static_cast<char>(Platform::SendScintilla(
id, SCI_GETSTYLEAT, position, 0));
}
int Accessor::GetLine(int position) {
int WindowAccessor::GetLine(int position) {
return Platform::SendScintilla(id, EM_LINEFROMCHAR, position, 0);
}
int Accessor::LineStart(int line) {
int WindowAccessor::LineStart(int line) {
return Platform::SendScintilla(id, EM_LINEINDEX, line, 0);
}
int Accessor::LevelAt(int line) {
int WindowAccessor::LevelAt(int line) {
return Platform::SendScintilla(id, SCI_GETFOLDLEVEL, line, 0);
}
int Accessor::Length() {
int WindowAccessor::Length() {
if (lenDoc == -1)
lenDoc = Platform::SendScintilla(id, WM_GETTEXTLENGTH, 0, 0);
return lenDoc;
}
int Accessor::GetLineState(int line) {
int WindowAccessor::GetLineState(int line) {
return Platform::SendScintilla(id, SCI_GETLINESTATE, line);
}
int Accessor::SetLineState(int line, int state) {
int WindowAccessor::SetLineState(int line, int state) {
return Platform::SendScintilla(id, SCI_SETLINESTATE, line, state);
}
void StylingContext::StartAt(unsigned int start, char chMask) {
void WindowAccessor::StartAt(unsigned int start, char chMask) {
Platform::SendScintilla(id, SCI_STARTSTYLING, start, chMask);
}
void StylingContext::StartSegment(unsigned int pos) {
void WindowAccessor::StartSegment(unsigned int pos) {
startSeg = pos;
}
void StylingContext::ColourTo(unsigned int pos, int chAttr) {
void WindowAccessor::ColourTo(unsigned int pos, int chAttr) {
// Only perform styling if non empty range
if (pos != startSeg - 1) {
if (pos < startSeg) {
@@ -96,22 +105,20 @@ void StylingContext::ColourTo(unsigned int pos, int chAttr) {
chFlags = 0;
chAttr |= chFlags;
for (unsigned int i = startSeg; i <= pos; i++) {
styleBuf[validLen++] = chAttr;
styleBuf[validLen++] = static_cast<char>(chAttr);
}
}
}
startSeg = pos+1;
}
int StylingContext::GetLine(int position) {
return Platform::SendScintilla(id, EM_LINEFROMCHAR, position, 0);
}
void StylingContext::SetLevel(int line, int level) {
void WindowAccessor::SetLevel(int line, int level) {
Platform::SendScintilla(id, SCI_SETFOLDLEVEL, line, level);
}
void StylingContext::Flush() {
void WindowAccessor::Flush() {
startPos = extremePosition;
lenDoc = -1;
if (validLen > 0) {
Platform::SendScintilla(id, SCI_SETSTYLINGEX, validLen,
reinterpret_cast<LPARAM>(styleBuf));
@@ -119,7 +126,7 @@ void StylingContext::Flush() {
}
}
int StylingContext::IndentAmount(int line, int *flags, PFNIsCommentLeader pfnIsCommentLeader) {
int WindowAccessor::IndentAmount(int line, int *flags, PFNIsCommentLeader pfnIsCommentLeader) {
int end = Length();
int spaceFlags = 0;

View File

@@ -116,7 +116,7 @@ wxStyledTextCtrl::~wxStyledTextCtrl() {
//----------------------------------------------------------------------
inline long wxStyledTextCtrl::SendMsg(int msg, long wp, long lp) {
long wxStyledTextCtrl::SendMsg(int msg, long wp, long lp) {
return m_swx->WndProc(msg, wp, lp);
}
@@ -146,8 +146,9 @@ wxString wxStyledTextCtrl::GetLine(int line) {
int len = GetLineLength(line);
char* buff = text.GetWriteBuf(len+1);
*((WORD*)buff) = len+1;
*((WORD*)buff) = len;
SendMsg(EM_GETLINE, line, (long)buff);
buff[len] = 0;
text.UngetWriteBuf();
return text;
}
@@ -426,16 +427,16 @@ int wxStyledTextCtrl::GetCurrentLine() {
}
wxString wxStyledTextCtrl::GetCurrentLineText(/*int* linePos*/) {
wxString wxStyledTextCtrl::GetCurrentLineText(int* linePos) {
wxString text;
int len = GetLineLength(GetCurrentLine());
char* buff = text.GetWriteBuf(len+1);
int pos = SendMsg(SCI_GETCURLINE, len+1, (long)buff);
int pos = SendMsg(SCI_GETCURLINE, len, (long)buff);
text.UngetWriteBuf();
/* if (linePos)
*linePos = pos; */
if (linePos)
*linePos = pos;
return text;
}
@@ -457,7 +458,7 @@ int wxStyledTextCtrl::LineFromPoint(wxPoint pt) {
wxPoint wxStyledTextCtrl::PointFromPosition(int pos) {
Point pt;
SendMsg(EM_POSFROMCHAR, pos, (long)&pt);
SendMsg(EM_POSFROMCHAR, (long)&pt, pos);
return wxPoint(pt.x, pt.y);
}
@@ -538,6 +539,27 @@ int wxStyledTextCtrl::GetSelectionType() {
}
int wxStyledTextCtrl::GetLinesOnScreen() {
return SendMsg(SCI_LINESONSCREEN);
}
bool wxStyledTextCtrl::IsSelectionRectangle() {
return SendMsg(SCI_SELECTIONISRECTANGLE) != 0;
}
void wxStyledTextCtrl::SetUseHorizontalScrollBar(bool use) {
SendMsg(SCI_SETHSCROLLBAR, use);
}
bool wxStyledTextCtrl::GetUseHorizontalScrollBar() {
return SendMsg(SCI_GETHSCROLLBAR) != 0;
}
//----------------------------------------------------------------------
@@ -645,6 +667,16 @@ void wxStyledTextCtrl::SetStyleBytes(int length, char* styleBytes) {
}
void wxStyledTextCtrl::SetLineState(int line, int value) {
SendMsg(SCI_SETLINESTATE, line, value);
}
int wxStyledTextCtrl::GetLineState(int line) {
return SendMsg(SCI_GETLINESTATE, line);
}
//----------------------------------------------------------------------
// Style Definition
@@ -905,11 +937,41 @@ void wxStyledTextCtrl::SetTabWidth(int numChars) {
}
void wxStyledTextCtrl::SetIndent(int numChars) {
SendMsg(SCI_SETINDENT, numChars);
}
void wxStyledTextCtrl::SetUseTabs(bool usetabs) {
SendMsg(SCI_SETUSETABS, usetabs);
}
void wxStyledTextCtrl::SetLineIndentation(int line, int indentation) {
SendMsg(SCI_SETLINEINDENTATION, line, indentation);
}
int wxStyledTextCtrl:: GetLineIndentation(int line) {
return SendMsg(SCI_GETLINEINDENTATION, line);
}
int wxStyledTextCtrl::GetLineIndentationPos(int line) {
return SendMsg(SCI_GETLINEINDENTPOSITION, line);
}
void wxStyledTextCtrl::SetWordChars(const wxString& wordChars) {
SendMsg(SCI_SETTABWIDTH, 0, (long)wordChars.c_str());
}
void wxStyledTextCtrl::SetUsePop(bool usepopup) {
SendMsg(SCI_USEPOPUP, usepopup);
}
//----------------------------------------------------------------------
// Brace highlighting
@@ -1053,6 +1115,21 @@ void wxStyledTextCtrl::AutoCompStopChars(const wxString& stopChars) {
}
void wxStyledTextCtrl::AutoCompSetSeparator(char separator) {
SendMsg(SCI_AUTOCSETSEPARATOR, separator);
}
char wxStyledTextCtrl::AutoCompGetSeparator() {
return SendMsg(SCI_AUTOCGETSEPARATOR);
}
void wxStyledTextCtrl::AutoCompSelect(const wxString& stringtoselect) {
SendMsg(SCI_AUTOCSELECT, (long)stringtoselect.c_str());
}
//----------------------------------------------------------------------
// Call tips