mirror of
https://github.com/fltk/fltk.git
synced 2026-05-31 22:04:26 +08:00
Local undo per Fl_Text_Buffer and Fl_Input_ (#557)
This commit is contained in:
@@ -38,6 +38,8 @@
|
|||||||
#define FL_MULTILINE_INPUT_WRAP (FL_MULTILINE_INPUT | FL_INPUT_WRAP)
|
#define FL_MULTILINE_INPUT_WRAP (FL_MULTILINE_INPUT | FL_INPUT_WRAP)
|
||||||
#define FL_MULTILINE_OUTPUT_WRAP (FL_MULTILINE_INPUT | FL_INPUT_READONLY | FL_INPUT_WRAP)
|
#define FL_MULTILINE_OUTPUT_WRAP (FL_MULTILINE_INPUT | FL_INPUT_READONLY | FL_INPUT_WRAP)
|
||||||
|
|
||||||
|
class Fl_Input_Undo_Action;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
This class provides a low-overhead text input field.
|
This class provides a low-overhead text input field.
|
||||||
|
|
||||||
@@ -144,6 +146,9 @@ class FL_EXPORT Fl_Input_ : public Fl_Widget {
|
|||||||
/** \internal color of the text cursor */
|
/** \internal color of the text cursor */
|
||||||
Fl_Color cursor_color_;
|
Fl_Color cursor_color_;
|
||||||
|
|
||||||
|
/** \internal local undo event */
|
||||||
|
Fl_Input_Undo_Action* undo_;
|
||||||
|
|
||||||
/** \internal Horizontal cursor position in pixels while moving up or down. */
|
/** \internal Horizontal cursor position in pixels while moving up or down. */
|
||||||
static double up_down_pos;
|
static double up_down_pos;
|
||||||
|
|
||||||
|
|||||||
@@ -60,6 +60,7 @@
|
|||||||
|
|
||||||
#include "Fl_Export.H"
|
#include "Fl_Export.H"
|
||||||
|
|
||||||
|
class Fl_Text_Undo_Action;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
\class Fl_Text_Selection
|
\class Fl_Text_Selection
|
||||||
@@ -836,6 +837,7 @@ protected:
|
|||||||
int mPreferredGapSize; /**< the default allocation for the text gap is 1024
|
int mPreferredGapSize; /**< the default allocation for the text gap is 1024
|
||||||
bytes and should only be increased if frequent
|
bytes and should only be increased if frequent
|
||||||
and large changes in buffer size are expected */
|
and large changes in buffer size are expected */
|
||||||
|
Fl_Text_Undo_Action* mUndo; /**< local undo event */
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|||||||
+78
-60
@@ -33,6 +33,45 @@ extern void fl_draw(const char*, int, float, float);
|
|||||||
|
|
||||||
////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
|
class Fl_Input_Undo_Action {
|
||||||
|
public:
|
||||||
|
Fl_Input_Undo_Action() :
|
||||||
|
undobuffer(NULL),
|
||||||
|
undobufferlength(0),
|
||||||
|
undoat(0),
|
||||||
|
undocut(0),
|
||||||
|
undoinsert(0),
|
||||||
|
undoyankcut(0)
|
||||||
|
{ }
|
||||||
|
~Fl_Input_Undo_Action() {
|
||||||
|
if (undobuffer)
|
||||||
|
::free(undobuffer);
|
||||||
|
}
|
||||||
|
|
||||||
|
char *undobuffer;
|
||||||
|
int undobufferlength;
|
||||||
|
int undoat; // points after insertion
|
||||||
|
int undocut; // number of characters deleted there
|
||||||
|
int undoinsert; // number of characters inserted
|
||||||
|
int undoyankcut; // length of valid contents of buffer, even if undocut=0
|
||||||
|
|
||||||
|
/*
|
||||||
|
Resize the undo buffer to match at least the requested size.
|
||||||
|
*/
|
||||||
|
void undobuffersize(int n)
|
||||||
|
{
|
||||||
|
if (n > undobufferlength) {
|
||||||
|
undobufferlength = n + 128;
|
||||||
|
undobuffer = (char *)realloc(undobuffer, undobufferlength);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void clear() {
|
||||||
|
undocut = undoinsert = 0;
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
/** \internal
|
/** \internal
|
||||||
Converts a given text segment into the text that will be rendered on screen.
|
Converts a given text segment into the text that will be rendered on screen.
|
||||||
|
|
||||||
@@ -723,26 +762,6 @@ int Fl_Input_::copy(int clipboard) {
|
|||||||
|
|
||||||
#define MAXFLOATSIZE 40
|
#define MAXFLOATSIZE 40
|
||||||
|
|
||||||
static char* undobuffer;
|
|
||||||
static int undobufferlength;
|
|
||||||
static Fl_Input_* undowidget;
|
|
||||||
static int undoat; // points after insertion
|
|
||||||
static int undocut; // number of characters deleted there
|
|
||||||
static int undoinsert; // number of characters inserted
|
|
||||||
static int yankcut; // length of valid contents of buffer, even if undocut=0
|
|
||||||
|
|
||||||
static void undobuffersize(int n) {
|
|
||||||
if (n > undobufferlength) {
|
|
||||||
if (undobuffer) {
|
|
||||||
do {undobufferlength *= 2;} while (undobufferlength < n);
|
|
||||||
undobuffer = (char*)realloc(undobuffer, undobufferlength);
|
|
||||||
} else {
|
|
||||||
undobufferlength = n+9;
|
|
||||||
undobuffer = (char*)malloc(undobufferlength);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
Append text at the end.
|
Append text at the end.
|
||||||
|
|
||||||
@@ -860,45 +879,43 @@ int Fl_Input_::replace(int b, int e, const char* text, int ilen) {
|
|||||||
put_in_buffer(size_+ilen);
|
put_in_buffer(size_+ilen);
|
||||||
|
|
||||||
if (e>b) {
|
if (e>b) {
|
||||||
if (undowidget == this && b == undoat) {
|
if (b == undo_->undoat) {
|
||||||
undobuffersize(undocut+(e-b));
|
undo_->undobuffersize(undo_->undocut+(e-b));
|
||||||
memcpy(undobuffer+undocut, value_+b, e-b);
|
memcpy(undo_->undobuffer+undo_->undocut, value_+b, e-b);
|
||||||
undocut += e-b;
|
undo_->undocut += e-b;
|
||||||
} else if (undowidget == this && e == undoat && !undoinsert) {
|
} else if (e == undo_->undoat && !undo_->undoinsert) {
|
||||||
undobuffersize(undocut+(e-b));
|
undo_->undobuffersize(undo_->undocut+(e-b));
|
||||||
memmove(undobuffer+(e-b), undobuffer, undocut);
|
memmove(undo_->undobuffer+(e-b), undo_->undobuffer, undo_->undocut);
|
||||||
memcpy(undobuffer, value_+b, e-b);
|
memcpy(undo_->undobuffer, value_+b, e-b);
|
||||||
undocut += e-b;
|
undo_->undocut += e-b;
|
||||||
} else if (undowidget == this && e == undoat && (e-b)<undoinsert) {
|
} else if (e == undo_->undoat && (e-b)<undo_->undoinsert) {
|
||||||
undoinsert -= e-b;
|
undo_->undoinsert -= e-b;
|
||||||
} else {
|
} else {
|
||||||
undobuffersize(e-b);
|
undo_->undobuffersize(e-b);
|
||||||
memcpy(undobuffer, value_+b, e-b);
|
memcpy(undo_->undobuffer, value_+b, e-b);
|
||||||
undocut = e-b;
|
undo_->undocut = e-b;
|
||||||
undoinsert = 0;
|
undo_->undoinsert = 0;
|
||||||
}
|
}
|
||||||
memmove(buffer+b, buffer+e, size_-e+1);
|
memmove(buffer+b, buffer+e, size_-e+1);
|
||||||
size_ -= e-b;
|
size_ -= e-b;
|
||||||
undowidget = this;
|
undo_->undoat = b;
|
||||||
undoat = b;
|
if (input_type() == FL_SECRET_INPUT) undo_->undoyankcut = 0; else undo_->undoyankcut = undo_->undocut;
|
||||||
if (input_type() == FL_SECRET_INPUT) yankcut = 0; else yankcut = undocut;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if (ilen) {
|
if (ilen) {
|
||||||
if (undowidget == this && b == undoat)
|
if (b == undo_->undoat)
|
||||||
undoinsert += ilen;
|
undo_->undoinsert += ilen;
|
||||||
else {
|
else {
|
||||||
undocut = 0;
|
undo_->undocut = 0;
|
||||||
undoinsert = ilen;
|
undo_->undoinsert = ilen;
|
||||||
}
|
}
|
||||||
memmove(buffer+b+ilen, buffer+b, size_-b+1);
|
memmove(buffer+b+ilen, buffer+b, size_-b+1);
|
||||||
memcpy(buffer+b, text, ilen);
|
memcpy(buffer+b, text, ilen);
|
||||||
size_ += ilen;
|
size_ += ilen;
|
||||||
}
|
}
|
||||||
undowidget = this;
|
|
||||||
om = mark_;
|
om = mark_;
|
||||||
op = position_;
|
op = position_;
|
||||||
mark_ = position_ = undoat = b+ilen;
|
mark_ = position_ = undo_->undoat = b+ilen;
|
||||||
|
|
||||||
// Insertions into the word at the end of the line will cause it to
|
// Insertions into the word at the end of the line will cause it to
|
||||||
// wrap to the next line, so we must indicate that the changes may start
|
// wrap to the next line, so we must indicate that the changes may start
|
||||||
@@ -922,7 +939,7 @@ int Fl_Input_::replace(int b, int e, const char* text, int ilen) {
|
|||||||
|
|
||||||
minimal_update(b);
|
minimal_update(b);
|
||||||
|
|
||||||
mark_ = position_ = undoat;
|
mark_ = position_ = undo_->undoat;
|
||||||
|
|
||||||
set_changed();
|
set_changed();
|
||||||
if (when()&FL_WHEN_CHANGED) do_callback();
|
if (when()&FL_WHEN_CHANGED) do_callback();
|
||||||
@@ -938,33 +955,33 @@ int Fl_Input_::replace(int b, int e, const char* text, int ilen) {
|
|||||||
*/
|
*/
|
||||||
int Fl_Input_::undo() {
|
int Fl_Input_::undo() {
|
||||||
was_up_down = 0;
|
was_up_down = 0;
|
||||||
if ( undowidget != this || (!undocut && !undoinsert) ) return 0;
|
if (!undo_->undocut && !undo_->undoinsert) return 0;
|
||||||
|
|
||||||
int ilen = undocut;
|
int ilen = undo_->undocut;
|
||||||
int xlen = undoinsert;
|
int xlen = undo_->undoinsert;
|
||||||
int b = undoat-xlen;
|
int b = undo_->undoat-xlen;
|
||||||
int b1 = b;
|
int b1 = b;
|
||||||
|
|
||||||
put_in_buffer(size_+ilen);
|
put_in_buffer(size_+ilen);
|
||||||
|
|
||||||
if (ilen) {
|
if (ilen) {
|
||||||
memmove(buffer+b+ilen, buffer+b, size_-b+1);
|
memmove(buffer+b+ilen, buffer+b, size_-b+1);
|
||||||
memcpy(buffer+b, undobuffer, ilen);
|
memcpy(buffer+b, undo_->undobuffer, ilen);
|
||||||
size_ += ilen;
|
size_ += ilen;
|
||||||
b += ilen;
|
b += ilen;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (xlen) {
|
if (xlen) {
|
||||||
undobuffersize(xlen);
|
undo_->undobuffersize(xlen);
|
||||||
memcpy(undobuffer, buffer+b, xlen);
|
memcpy(undo_->undobuffer, buffer+b, xlen);
|
||||||
memmove(buffer+b, buffer+b+xlen, size_-xlen-b+1);
|
memmove(buffer+b, buffer+b+xlen, size_-xlen-b+1);
|
||||||
size_ -= xlen;
|
size_ -= xlen;
|
||||||
}
|
}
|
||||||
|
|
||||||
undocut = xlen;
|
undo_->undocut = xlen;
|
||||||
if (xlen) yankcut = xlen;
|
if (xlen) undo_->undoyankcut = xlen;
|
||||||
undoinsert = ilen;
|
undo_->undoinsert = ilen;
|
||||||
undoat = b;
|
undo_->undoat = b;
|
||||||
mark_ = b /* -ilen */;
|
mark_ = b /* -ilen */;
|
||||||
position_ = b;
|
position_ = b;
|
||||||
|
|
||||||
@@ -988,8 +1005,8 @@ int Fl_Input_::undo() {
|
|||||||
*/
|
*/
|
||||||
int Fl_Input_::copy_cuts() {
|
int Fl_Input_::copy_cuts() {
|
||||||
// put the yank buffer into the X clipboard
|
// put the yank buffer into the X clipboard
|
||||||
if (!yankcut || input_type()==FL_SECRET_INPUT) return 0;
|
if (!undo_->undoyankcut || input_type()==FL_SECRET_INPUT) return 0;
|
||||||
Fl::copy(undobuffer, yankcut, 1);
|
Fl::copy(undo_->undobuffer, undo_->undoyankcut, 1);
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -1151,6 +1168,7 @@ Fl_Input_::Fl_Input_(int X, int Y, int W, int H, const char* l)
|
|||||||
xscroll_ = yscroll_ = 0;
|
xscroll_ = yscroll_ = 0;
|
||||||
maximum_size_ = 32767;
|
maximum_size_ = 32767;
|
||||||
shortcut_ = 0;
|
shortcut_ = 0;
|
||||||
|
undo_ = new Fl_Input_Undo_Action();
|
||||||
set_flag(SHORTCUT_LABEL);
|
set_flag(SHORTCUT_LABEL);
|
||||||
set_flag(MAC_USE_ACCENTS_MENU);
|
set_flag(MAC_USE_ACCENTS_MENU);
|
||||||
set_flag(NEEDS_KEYBOARD);
|
set_flag(NEEDS_KEYBOARD);
|
||||||
@@ -1217,7 +1235,7 @@ void Fl_Input_::put_in_buffer(int len) {
|
|||||||
*/
|
*/
|
||||||
int Fl_Input_::static_value(const char* str, int len) {
|
int Fl_Input_::static_value(const char* str, int len) {
|
||||||
clear_changed();
|
clear_changed();
|
||||||
if (undowidget == this) undowidget = 0;
|
undo_->clear();
|
||||||
if (str == value_ && len == size_) return 0;
|
if (str == value_ && len == size_) return 0;
|
||||||
if (len) { // non-empty new value:
|
if (len) { // non-empty new value:
|
||||||
if (xscroll_ || yscroll_) {
|
if (xscroll_ || yscroll_) {
|
||||||
@@ -1318,7 +1336,7 @@ void Fl_Input_::resize(int X, int Y, int W, int H) {
|
|||||||
from the parent Fl_Group.
|
from the parent Fl_Group.
|
||||||
*/
|
*/
|
||||||
Fl_Input_::~Fl_Input_() {
|
Fl_Input_::~Fl_Input_() {
|
||||||
if (undowidget == this) undowidget = 0;
|
delete undo_;
|
||||||
if (bufsize) free((void*)buffer);
|
if (bufsize) free((void*)buffer);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
+86
-61
@@ -66,32 +66,44 @@ static int min(int i1, int i2)
|
|||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
class Fl_Text_Undo_Action {
|
||||||
|
public:
|
||||||
|
Fl_Text_Undo_Action() :
|
||||||
|
undobuffer(NULL),
|
||||||
|
undobufferlength(0),
|
||||||
|
undoat(0),
|
||||||
|
undocut(0),
|
||||||
|
undoinsert(0),
|
||||||
|
undoyankcut(0)
|
||||||
|
{ }
|
||||||
|
~Fl_Text_Undo_Action() {
|
||||||
|
if (undobuffer)
|
||||||
|
::free(undobuffer);
|
||||||
|
}
|
||||||
|
|
||||||
static char *undobuffer;
|
char *undobuffer;
|
||||||
static int undobufferlength;
|
int undobufferlength;
|
||||||
static Fl_Text_Buffer *undowidget;
|
int undoat; // points after insertion
|
||||||
static int undoat; // points after insertion
|
int undocut; // number of characters deleted there
|
||||||
static int undocut; // number of characters deleted there
|
int undoinsert; // number of characters inserted
|
||||||
static int undoinsert; // number of characters inserted
|
int undoyankcut; // length of valid contents of buffer, even if undocut=0
|
||||||
static int undoyankcut; // length of valid contents of buffer, even if undocut=0
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
Resize the undo buffer to match at least the requested size.
|
Resize the undo buffer to match at least the requested size.
|
||||||
*/
|
*/
|
||||||
static void undobuffersize(int n)
|
void undobuffersize(int n)
|
||||||
{
|
{
|
||||||
if (n > undobufferlength) {
|
if (n > undobufferlength) {
|
||||||
if (undobuffer) {
|
undobufferlength = n + 128;
|
||||||
do {
|
undobuffer = (char *)realloc(undobuffer, undobufferlength);
|
||||||
undobufferlength *= 2;
|
|
||||||
} while (undobufferlength < n);
|
|
||||||
undobuffer = (char *) realloc(undobuffer, undobufferlength);
|
|
||||||
} else {
|
|
||||||
undobufferlength = n + 9;
|
|
||||||
undobuffer = (char *) malloc(undobufferlength);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
void clear() {
|
||||||
|
undocut = undoinsert = 0;
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
|
||||||
static void def_transcoding_warning_action(Fl_Text_Buffer *text)
|
static void def_transcoding_warning_action(Fl_Text_Buffer *text)
|
||||||
{
|
{
|
||||||
@@ -123,6 +135,7 @@ Fl_Text_Buffer::Fl_Text_Buffer(int requestedSize, int preferredGapSize)
|
|||||||
mPredeleteCbArgs = NULL;
|
mPredeleteCbArgs = NULL;
|
||||||
mCursorPosHint = 0;
|
mCursorPosHint = 0;
|
||||||
mCanUndo = 1;
|
mCanUndo = 1;
|
||||||
|
mUndo = new Fl_Text_Undo_Action();
|
||||||
input_file_was_transcoded = 0;
|
input_file_was_transcoded = 0;
|
||||||
transcoding_warning_action = def_transcoding_warning_action;
|
transcoding_warning_action = def_transcoding_warning_action;
|
||||||
}
|
}
|
||||||
@@ -142,6 +155,7 @@ Fl_Text_Buffer::~Fl_Text_Buffer()
|
|||||||
delete[] mPredeleteProcs;
|
delete[] mPredeleteProcs;
|
||||||
delete[] mPredeleteCbArgs;
|
delete[] mPredeleteCbArgs;
|
||||||
}
|
}
|
||||||
|
delete mUndo;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@@ -190,6 +204,9 @@ void Fl_Text_Buffer::text(const char *t)
|
|||||||
/* Call the saved display routine(s) to update the screen */
|
/* Call the saved display routine(s) to update the screen */
|
||||||
call_modify_callbacks(0, deletedLength, insertedLength, 0, deletedText);
|
call_modify_callbacks(0, deletedLength, insertedLength, 0, deletedText);
|
||||||
free((void *) deletedText);
|
free((void *) deletedText);
|
||||||
|
|
||||||
|
if (mCanUndo)
|
||||||
|
mUndo->clear();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@@ -449,36 +466,39 @@ void Fl_Text_Buffer::copy(Fl_Text_Buffer * fromBuf, int fromStart,
|
|||||||
*/
|
*/
|
||||||
int Fl_Text_Buffer::undo(int *cursorPos)
|
int Fl_Text_Buffer::undo(int *cursorPos)
|
||||||
{
|
{
|
||||||
if (undowidget != this || (!undocut && !undoinsert && !mCanUndo))
|
if (!mCanUndo)
|
||||||
return 0;
|
return 0;
|
||||||
|
|
||||||
int ilen = undocut;
|
if (!mUndo->undocut && !mUndo->undoinsert)
|
||||||
int xlen = undoinsert;
|
return 0;
|
||||||
int b = undoat - xlen;
|
|
||||||
|
|
||||||
if (xlen && undoyankcut && !ilen) {
|
int ilen = mUndo->undocut;
|
||||||
ilen = undoyankcut;
|
int xlen = mUndo->undoinsert;
|
||||||
|
int b = mUndo->undoat - xlen;
|
||||||
|
|
||||||
|
if (xlen && mUndo->undoyankcut && !ilen) {
|
||||||
|
ilen = mUndo->undoyankcut;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (xlen && ilen) {
|
if (xlen && ilen) {
|
||||||
undobuffersize(ilen + 1);
|
mUndo->undobuffersize(ilen + 1);
|
||||||
undobuffer[ilen] = 0;
|
mUndo->undobuffer[ilen] = 0;
|
||||||
char *tmp = fl_strdup(undobuffer);
|
char *tmp = fl_strdup(mUndo->undobuffer);
|
||||||
replace(b, undoat, tmp);
|
replace(b, mUndo->undoat, tmp);
|
||||||
if (cursorPos)
|
if (cursorPos)
|
||||||
*cursorPos = mCursorPosHint;
|
*cursorPos = mCursorPosHint;
|
||||||
free(tmp);
|
free(tmp);
|
||||||
} else if (xlen) {
|
} else if (xlen) {
|
||||||
remove(b, undoat);
|
remove(b, mUndo->undoat);
|
||||||
if (cursorPos)
|
if (cursorPos)
|
||||||
*cursorPos = mCursorPosHint;
|
*cursorPos = mCursorPosHint;
|
||||||
} else if (ilen) {
|
} else if (ilen) {
|
||||||
undobuffersize(ilen + 1);
|
mUndo->undobuffersize(ilen + 1);
|
||||||
undobuffer[ilen] = 0;
|
mUndo->undobuffer[ilen] = 0;
|
||||||
insert(undoat, undobuffer);
|
insert(mUndo->undoat, mUndo->undobuffer);
|
||||||
if (cursorPos)
|
if (cursorPos)
|
||||||
*cursorPos = mCursorPosHint;
|
*cursorPos = mCursorPosHint;
|
||||||
undoyankcut = 0;
|
mUndo->undoyankcut = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
return 1;
|
return 1;
|
||||||
@@ -490,10 +510,17 @@ int Fl_Text_Buffer::undo(int *cursorPos)
|
|||||||
*/
|
*/
|
||||||
void Fl_Text_Buffer::canUndo(char flag)
|
void Fl_Text_Buffer::canUndo(char flag)
|
||||||
{
|
{
|
||||||
|
if (flag) {
|
||||||
|
if (!mCanUndo) {
|
||||||
|
mUndo = new Fl_Text_Undo_Action();
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
if (mCanUndo) {
|
||||||
|
delete mUndo;
|
||||||
|
mUndo = NULL;
|
||||||
|
}
|
||||||
|
}
|
||||||
mCanUndo = flag;
|
mCanUndo = flag;
|
||||||
// disabling undo also clears the last undo operation!
|
|
||||||
if (!mCanUndo && undowidget==this)
|
|
||||||
undowidget = 0;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@@ -1190,15 +1217,14 @@ int Fl_Text_Buffer::insert_(int pos, const char *text)
|
|||||||
update_selections(pos, 0, insertedLength);
|
update_selections(pos, 0, insertedLength);
|
||||||
|
|
||||||
if (mCanUndo) {
|
if (mCanUndo) {
|
||||||
if (undowidget == this && undoat == pos && undoinsert) {
|
if (mUndo->undoat == pos && mUndo->undoinsert) {
|
||||||
undoinsert += insertedLength;
|
mUndo->undoinsert += insertedLength;
|
||||||
} else {
|
} else {
|
||||||
undoinsert = insertedLength;
|
mUndo->undoinsert = insertedLength;
|
||||||
undoyankcut = (undoat == pos) ? undocut : 0;
|
mUndo->undoyankcut = (mUndo->undoat == pos) ? mUndo->undocut : 0;
|
||||||
}
|
}
|
||||||
undoat = pos + insertedLength;
|
mUndo->undoat = pos + insertedLength;
|
||||||
undocut = 0;
|
mUndo->undocut = 0;
|
||||||
undowidget = this;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
return insertedLength;
|
return insertedLength;
|
||||||
@@ -1214,34 +1240,33 @@ void Fl_Text_Buffer::remove_(int start, int end)
|
|||||||
/* if the gap is not contiguous to the area to remove, move it there */
|
/* if the gap is not contiguous to the area to remove, move it there */
|
||||||
|
|
||||||
if (mCanUndo) {
|
if (mCanUndo) {
|
||||||
if (undowidget == this && undoat == end && undocut) {
|
if (mUndo->undoat == end && mUndo->undocut) {
|
||||||
undobuffersize(undocut + end - start + 1);
|
mUndo->undobuffersize(mUndo->undocut + end - start + 1);
|
||||||
memmove(undobuffer + end - start, undobuffer, undocut);
|
memmove(mUndo->undobuffer + end - start, mUndo->undobuffer, mUndo->undocut);
|
||||||
undocut += end - start;
|
mUndo->undocut += end - start;
|
||||||
} else {
|
} else {
|
||||||
undocut = end - start;
|
mUndo->undocut = end - start;
|
||||||
undobuffersize(undocut);
|
mUndo->undobuffersize(mUndo->undocut);
|
||||||
}
|
}
|
||||||
undoat = start;
|
mUndo->undoat = start;
|
||||||
undoinsert = 0;
|
mUndo->undoinsert = 0;
|
||||||
undoyankcut = 0;
|
mUndo->undoyankcut = 0;
|
||||||
undowidget = this;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if (start > mGapStart) {
|
if (start > mGapStart) {
|
||||||
if (mCanUndo)
|
if (mCanUndo)
|
||||||
memcpy(undobuffer, mBuf + (mGapEnd - mGapStart) + start,
|
memcpy(mUndo->undobuffer, mBuf + (mGapEnd - mGapStart) + start,
|
||||||
end - start);
|
end - start);
|
||||||
move_gap(start);
|
move_gap(start);
|
||||||
} else if (end < mGapStart) {
|
} else if (end < mGapStart) {
|
||||||
if (mCanUndo)
|
if (mCanUndo)
|
||||||
memcpy(undobuffer, mBuf + start, end - start);
|
memcpy(mUndo->undobuffer, mBuf + start, end - start);
|
||||||
move_gap(end);
|
move_gap(end);
|
||||||
} else {
|
} else {
|
||||||
int prelen = mGapStart - start;
|
int prelen = mGapStart - start;
|
||||||
if (mCanUndo) {
|
if (mCanUndo) {
|
||||||
memcpy(undobuffer, mBuf + start, prelen);
|
memcpy(mUndo->undobuffer, mBuf + start, prelen);
|
||||||
memcpy(undobuffer + prelen, mBuf + mGapEnd, end - start - prelen);
|
memcpy(mUndo->undobuffer + prelen, mBuf + mGapEnd, end - start - prelen);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user