mirror of
https://github.com/fltk/fltk.git
synced 2026-06-07 09:13:58 +08:00
STR 2158: partially solved. This commit is huge, I admit. I recoded most of Fl_Text_Buffer and large chunks of Fl_Text_Display to make it UTF-8 safe. Rendering of all left-to-right scripts works well on OS X for all tested fonts. International input works AFAIK. Copy and paste of UTF-8 data works. ----> what's not working yet though is line wrapping. Also, text search for internationsl characters is not working yet.
git-svn-id: file:///fltk/svn/fltk/branches/branch-1.3@7792 ea41ed52-d2ee-0310-a9c1-e6b18d33e121
This commit is contained in:
+103
-252
File diff suppressed because it is too large
Load Diff
+113
-37
@@ -46,37 +46,53 @@
|
||||
by the Fl_Text_Buffer
|
||||
class.
|
||||
*/
|
||||
class FL_EXPORT Fl_Text_Display: public Fl_Group {
|
||||
class FL_EXPORT Fl_Text_Display: public Fl_Group
|
||||
{
|
||||
public:
|
||||
/** text display cursor shapes enumeration */
|
||||
|
||||
/**
|
||||
text display cursor shapes enumeration
|
||||
*/
|
||||
enum {
|
||||
NORMAL_CURSOR, CARET_CURSOR, DIM_CURSOR,
|
||||
BLOCK_CURSOR, HEAVY_CURSOR
|
||||
};
|
||||
|
||||
/**
|
||||
the character position is the left edge of a character wheras
|
||||
the cursor is thought to be between the centers of to consecutive
|
||||
characters.
|
||||
*/
|
||||
enum {
|
||||
CURSOR_POS, CHARACTER_POS
|
||||
};
|
||||
|
||||
/** drag types- they match Fl::event_clicks() so that single clicking to
|
||||
/**
|
||||
drag types- they match Fl::event_clicks() so that single clicking to
|
||||
start a collection selects by character, double clicking selects by
|
||||
word and triple clicking selects by line.
|
||||
*/
|
||||
enum {
|
||||
DRAG_CHAR = 0, DRAG_WORD = 1, DRAG_LINE = 2
|
||||
};
|
||||
|
||||
friend void fl_text_drag_me(int pos, Fl_Text_Display* d);
|
||||
|
||||
typedef void (*Unfinished_Style_Cb)(int, void *);
|
||||
|
||||
/** style attributes - currently not implemented! */
|
||||
/**
|
||||
style attributes - currently not implemented!
|
||||
*/
|
||||
enum {
|
||||
ATTR_NONE = 0,
|
||||
ATTR_UNDERLINE = 1,
|
||||
ATTR_HIDDEN = 2
|
||||
};
|
||||
/** This structure associates the color,font,size of a string to draw
|
||||
with an attribute mask matching attr */
|
||||
|
||||
/**
|
||||
This structure associates the color,font,size of a string to draw
|
||||
with an attribute mask matching attr
|
||||
*/
|
||||
struct Style_Table_Entry {
|
||||
Fl_Color color;
|
||||
Fl_Font font;
|
||||
@@ -89,23 +105,30 @@ class FL_EXPORT Fl_Text_Display: public Fl_Group {
|
||||
|
||||
virtual int handle(int e);
|
||||
void buffer(Fl_Text_Buffer* buf);
|
||||
|
||||
/**
|
||||
Sets or gets the current text buffer associated with the text widget.
|
||||
Multiple text widgets can be associated with the same text buffer.
|
||||
*/
|
||||
void buffer(Fl_Text_Buffer& buf) { buffer(&buf); }
|
||||
|
||||
/**
|
||||
Gets the current text buffer associated with the text widget.
|
||||
Multiple text widgets can be associated with the same text buffer.
|
||||
*/
|
||||
Fl_Text_Buffer* buffer() const { return mBuffer; }
|
||||
|
||||
void redisplay_range(int start, int end);
|
||||
void scroll(int topLineNum, int horizOffset);
|
||||
void insert(const char* text);
|
||||
void overstrike(const char* text);
|
||||
void insert_position(int newPos);
|
||||
/** Gets the position of the text insertion cursor for text display */
|
||||
|
||||
/**
|
||||
Gets the position of the text insertion cursor for text display
|
||||
*/
|
||||
int insert_position() const { return mCursorPos; }
|
||||
|
||||
int in_selection(int x, int y) const;
|
||||
void show_insert_position();
|
||||
int move_right();
|
||||
@@ -120,24 +143,52 @@ class FL_EXPORT Fl_Text_Display: public Fl_Group {
|
||||
void next_word(void);
|
||||
void previous_word(void);
|
||||
void show_cursor(int b = 1);
|
||||
/** Hides the text cursor */
|
||||
|
||||
/**
|
||||
Hides the text cursor
|
||||
*/
|
||||
void hide_cursor() { show_cursor(0); }
|
||||
|
||||
void cursor_style(int style);
|
||||
/** Sets or gets the text cursor color. */
|
||||
|
||||
/**
|
||||
Sets or gets the text cursor color.
|
||||
*/
|
||||
Fl_Color cursor_color() const {return mCursor_color;}
|
||||
/** Sets or gets the text cursor color. */
|
||||
|
||||
/**
|
||||
Sets or gets the text cursor color.
|
||||
*/
|
||||
void cursor_color(Fl_Color n) {mCursor_color = n;}
|
||||
/** Sets or gets the width/height of the scrollbars. */
|
||||
|
||||
/**
|
||||
Sets or gets the width/height of the scrollbars.
|
||||
*/
|
||||
int scrollbar_width() const { return scrollbar_width_; }
|
||||
/** Sets or gets the width/height of the scrollbars. */
|
||||
|
||||
/**
|
||||
Sets or gets the width/height of the scrollbars.
|
||||
*/
|
||||
void scrollbar_width(int W) { scrollbar_width_ = W; }
|
||||
/** Gets the scrollbar alignment type */
|
||||
|
||||
/**
|
||||
Gets the scrollbar alignment type
|
||||
*/
|
||||
Fl_Align scrollbar_align() const { return scrollbar_align_; }
|
||||
/** Sets the scrollbar alignment type */
|
||||
|
||||
/**
|
||||
Sets the scrollbar alignment type
|
||||
*/
|
||||
void scrollbar_align(Fl_Align a) { scrollbar_align_ = a; }
|
||||
/** Moves the insert position to the beginning of the current word. */
|
||||
|
||||
/**
|
||||
Moves the insert position to the beginning of the current word.
|
||||
*/
|
||||
int word_start(int pos) const { return buffer()->word_start(pos); }
|
||||
/** Moves the insert position to the end of the current word. */
|
||||
|
||||
/**
|
||||
Moves the insert position to the end of the current word.
|
||||
*/
|
||||
int word_end(int pos) const { return buffer()->word_end(pos); }
|
||||
|
||||
|
||||
@@ -147,26 +198,48 @@ class FL_EXPORT Fl_Text_Display: public Fl_Group {
|
||||
Unfinished_Style_Cb unfinishedHighlightCB,
|
||||
void *cbArg);
|
||||
|
||||
int position_style(int lineStartPos, int lineLen, int lineIndex,
|
||||
int dispIndex) const;
|
||||
/** \todo FIXME : get set methods pointing on shortcut_
|
||||
have no effects as shortcut_ is unused in this class and derived! */
|
||||
int position_style(int lineStartPos, int lineLen, int lineIndex) const;
|
||||
|
||||
/**
|
||||
\todo FIXME : get set methods pointing on shortcut_
|
||||
have no effects as shortcut_ is unused in this class and derived!
|
||||
*/
|
||||
int shortcut() const {return shortcut_;}
|
||||
/** \todo FIXME : get set methods pointing on shortcut_
|
||||
have no effects as shortcut_ is unused in this class and derived! */
|
||||
|
||||
/**
|
||||
\todo FIXME : get set methods pointing on shortcut_
|
||||
have no effects as shortcut_ is unused in this class and derived!
|
||||
*/
|
||||
void shortcut(int s) {shortcut_ = s;}
|
||||
|
||||
/** Gets the default font used when drawing text in the widget. */
|
||||
/**
|
||||
Gets the default font used when drawing text in the widget.
|
||||
*/
|
||||
Fl_Font textfont() const {return textfont_;}
|
||||
/** Sets the default font used when drawing text in the widget. */
|
||||
|
||||
/**
|
||||
Sets the default font used when drawing text in the widget.
|
||||
*/
|
||||
void textfont(Fl_Font s) {textfont_ = s;}
|
||||
/** Gets the default size of text in the widget. */
|
||||
|
||||
/**
|
||||
Gets the default size of text in the widget.
|
||||
*/
|
||||
Fl_Fontsize textsize() const {return textsize_;}
|
||||
/** Sets the default size of text in the widget. */
|
||||
|
||||
/**
|
||||
Sets the default size of text in the widget.
|
||||
*/
|
||||
void textsize(Fl_Fontsize s) {textsize_ = s;}
|
||||
/** Gets the default color of text in the widget. */
|
||||
|
||||
/**
|
||||
Gets the default color of text in the widget.
|
||||
*/
|
||||
Fl_Color textcolor() const {return textcolor_;}
|
||||
/** Sets the default color of text in the widget. */
|
||||
|
||||
/**
|
||||
Sets the default color of text in the widget.
|
||||
*/
|
||||
void textcolor(Fl_Color n) {textcolor_ = n;}
|
||||
|
||||
int wrapped_column(int row, int column) const;
|
||||
@@ -187,14 +260,21 @@ class FL_EXPORT Fl_Text_Display: public Fl_Group {
|
||||
void draw_cursor(int, int);
|
||||
|
||||
void draw_string(int style, int x, int y, int toX, const char *string,
|
||||
int nChars);
|
||||
int nChars) const;
|
||||
|
||||
void draw_vline(int visLineNum, int leftClip, int rightClip,
|
||||
int leftCharIndex, int rightCharIndex);
|
||||
|
||||
int find_x(const char *s, int len, int style, int x) const;
|
||||
enum { DRAW_LINE, FIND_INDEX, GET_WIDTH };
|
||||
int handle_vline(int mode,
|
||||
int lineStart, int lineLen, int leftChar, int rightChar,
|
||||
int topClip, int bottomClip,
|
||||
int leftClip, int rightClip) const;
|
||||
|
||||
void draw_line_numbers(bool clearAll);
|
||||
|
||||
void clear_rect(int style, int x, int y, int width, int height);
|
||||
void clear_rect(int style, int x, int y, int width, int height) const;
|
||||
void display_insert();
|
||||
|
||||
void offset_line_starts(int newTopLineNum);
|
||||
@@ -253,9 +333,7 @@ class FL_EXPORT Fl_Text_Display: public Fl_Group {
|
||||
int *nextLineStart) const;
|
||||
int measure_proportional_character(const char *s, int colNum, int pos) const;
|
||||
int wrap_uses_character(int lineEndPos) const;
|
||||
int range_touches_selection(const Fl_Text_Selection *sel, int rangeStart,
|
||||
int rangeEnd) const;
|
||||
#ifndef FL_DOXYGEN
|
||||
|
||||
int damage_range1_start, damage_range1_end;
|
||||
int damage_range2_start, damage_range2_end;
|
||||
int mCursorPos;
|
||||
@@ -303,8 +381,6 @@ class FL_EXPORT Fl_Text_Display: public Fl_Group {
|
||||
|
||||
int mMaxsize;
|
||||
|
||||
int mFixedFontWidth; /* Font width if all current fonts are
|
||||
fixed and match in width, else -1 */
|
||||
int mSuppressResync; /* Suppress resynchronization of line
|
||||
starts during buffer updates */
|
||||
int mNLinesDeleted; /* Number of lines deleted during
|
||||
@@ -332,9 +408,9 @@ class FL_EXPORT Fl_Text_Display: public Fl_Group {
|
||||
// The following are not presently used from the original NEdit code,
|
||||
// but are being put here so that future versions of Fl_Text_Display
|
||||
// can implement line numbers without breaking binary compatibility.
|
||||
|
||||
/* Line number margin and width */
|
||||
int mLineNumLeft, mLineNumWidth;
|
||||
/* Line number margin and width */
|
||||
#endif
|
||||
};
|
||||
|
||||
#endif
|
||||
|
||||
+455
-1242
File diff suppressed because it is too large
Load Diff
+203
-373
File diff suppressed because it is too large
Load Diff
@@ -255,7 +255,7 @@ int Fl_Text_Editor::kf_backspace(int, Fl_Text_Editor* e) {
|
||||
if (!e->buffer()->selected() && e->move_left()) {
|
||||
int l = 1;
|
||||
// FIXME: character is ucs-4
|
||||
char c = e->buffer()->character(e->insert_position());
|
||||
char c = e->buffer()->char_at(e->insert_position());
|
||||
if (c & 0x80 && c & 0x40) {
|
||||
l = fl_utf8len(c);
|
||||
}
|
||||
@@ -451,7 +451,7 @@ int Fl_Text_Editor::kf_delete(int, Fl_Text_Editor* e) {
|
||||
if (!e->buffer()->selected()) {
|
||||
int l = 1;
|
||||
// FIXME: character is ucs-4
|
||||
char c = e->buffer()->character(e->insert_position());
|
||||
char c = e->buffer()->char_at(e->insert_position());
|
||||
if (c & 0x80 && c & 0x40) {
|
||||
l = fl_utf8len(c);
|
||||
}
|
||||
|
||||
+56
-4
@@ -66,12 +66,13 @@ Fl_Text_Buffer *stylebuf = 0;
|
||||
Fl_Text_Display::Style_Table_Entry
|
||||
styletable[] = { // Style table
|
||||
{ FL_BLACK, FL_COURIER, TS }, // A - Plain
|
||||
{ FL_DARK_GREEN, FL_COURIER_ITALIC, TS }, // B - Line comments
|
||||
{ FL_DARK_GREEN, FL_COURIER_ITALIC, TS }, // C - Block comments
|
||||
{ FL_DARK_GREEN, FL_HELVETICA_ITALIC, TS }, // B - Line comments
|
||||
{ FL_DARK_GREEN, FL_HELVETICA_ITALIC, TS }, // C - Block comments
|
||||
{ FL_BLUE, FL_COURIER, TS }, // D - Strings
|
||||
{ FL_DARK_RED, FL_COURIER, TS }, // E - Directives
|
||||
{ FL_DARK_RED, FL_COURIER_BOLD, TS }, // F - Types
|
||||
{ FL_BLUE, FL_COURIER_BOLD, TS } // G - Keywords
|
||||
{ FL_BLUE, FL_COURIER_BOLD, TS }, // G - Keywords
|
||||
{ FL_MAGENTA, FL_HELVETICA, TS-2 } // H - Font height test
|
||||
};
|
||||
const char *code_keywords[] = { // List of known C/C++ keywords...
|
||||
"and",
|
||||
@@ -200,6 +201,8 @@ style_parse(const char *text,
|
||||
if (length == 0) break;
|
||||
} else if (strncmp(text, "/*", 2) == 0) {
|
||||
current = 'C';
|
||||
} else if (strncmp(text, "[", 1) == 0) {
|
||||
current = 'H';
|
||||
} else if (strncmp(text, "\\\"", 2) == 0) {
|
||||
// Quoted quote...
|
||||
*style++ = current;
|
||||
@@ -261,6 +264,14 @@ style_parse(const char *text,
|
||||
current = 'A';
|
||||
col += 2;
|
||||
continue;
|
||||
} else if (current == 'H' && strncmp(text, "]", 1) == 0) {
|
||||
// Close a font test style
|
||||
*style++ = current;
|
||||
text ++;
|
||||
length --;
|
||||
current = 'A';
|
||||
col += 1;
|
||||
continue;
|
||||
} else if (current == 'D') {
|
||||
// Continuing in string...
|
||||
if (strncmp(text, "\\\"", 2) == 0) {
|
||||
@@ -793,7 +804,48 @@ Fl_Window* new_view() {
|
||||
|
||||
int main(int argc, char **argv) {
|
||||
textbuf = new Fl_Text_Buffer;
|
||||
textbuf->text("Rügenwälder Ruß.");
|
||||
textbuf->text(
|
||||
"void saveas_cb() {\n"
|
||||
" Fl_Native_File_Chooser fnfc;\n"
|
||||
" fnfc.title(\"Save File As?\");\n"
|
||||
" fnfc.type(Fl_Native_File_Chooser::BROWSE_SAVE_FILE);\n"
|
||||
" if ( fnfc.show() ) return;\n"
|
||||
" save_file(fnfc.filename());\n"
|
||||
"}\n\n"
|
||||
"// Falsches Üben von Xylophonmusik quält jeden größeren Zwerg\n"
|
||||
"// (= Wrongful practicing of xylophone music tortures every larger dwarf)\n"
|
||||
"\n"
|
||||
"// Zwölf Boxkämpfer jagten Eva quer über den Sylter Deich\n"
|
||||
"// (= Twelve boxing fighters hunted Eva across the dike of Sylt)\n"
|
||||
"\n"
|
||||
"Heizöl/*rückstoß*/abdämpfung\n"
|
||||
"(= fuel oil recoil absorber)\n"
|
||||
"\n"
|
||||
"Hiragana: //(Iroha)\n"
|
||||
"\n"
|
||||
"いろはにほへとちりぬるを\n"
|
||||
"わかよたれそつねならむ\n"
|
||||
"うゐのおくやまけふこえて\n"
|
||||
"あさきゆめみしゑひもせす\n"
|
||||
"\n"
|
||||
"Katakana:\n"
|
||||
"\n"
|
||||
"イロハニホヘト チ/*リヌルヲ ワカヨタ*/レソ ツネナラム\n"
|
||||
"ウヰノオクヤマ ケフコエテ アサキユメミシ ヱヒモセスン\n"
|
||||
"\n"
|
||||
"Right-to-left script does not work yet:\n"
|
||||
"? דג סקרן שט בים מאוכזב ולפתע מצא לו חברה איך הקליטה\n"
|
||||
"\n"
|
||||
"// いろはにほへと ちりぬるを わかよ\n"
|
||||
"/* たれそ つねならむ うゐのおくやま */\n"
|
||||
"けふこえて あさきゆめみし ゑひも\n"
|
||||
"せす\n\n"
|
||||
"Even colours and [sweet perfume] / Will eventually fade /\n"
|
||||
"Even our world / Is not eternal /\n"
|
||||
"The deep mountains of vanity / Cross them today /\n"
|
||||
"And superficial dreams / Shall no longer delude you.\n"
|
||||
"(from Iroha-uta)"
|
||||
);
|
||||
style_init();
|
||||
|
||||
Fl_Window* window = new_view();
|
||||
|
||||
Reference in New Issue
Block a user