1 // Permission is hereby granted, free of charge, to any person obtaining
2 // a copy of this software and associated documentation files (the
3 // "Software"), to deal in the Software without restriction, including
4 // without limitation the rights to use, copy, modify, merge, publish,
5 // distribute, sublicense, and/or sell copies of the Software, and to
6 // permit persons to whom the Software is furnished to do so, subject to
7 // the following conditions:
9 // The above copyright notice and this permission notice shall be
10 // included in all copies or substantial portions of the Software.
12 // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
13 // EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
14 // MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
15 // NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
16 // LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
17 // OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
18 // WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
20 // Copyright (c) 2004 Novell, Inc. (http://www.novell.com)
23 // Peter Bartok pbartok@novell.com
32 using System.Drawing.Text;
35 namespace System.Windows.Forms {
36 public abstract class TextBoxBase : Control {
37 #region Local Variables
38 internal HorizontalAlignment alignment;
39 internal bool accepts_tab;
40 internal bool accepts_return;
41 internal bool auto_size;
42 internal CharacterCasing character_casing;
44 internal bool hide_selection;
45 internal int max_length;
46 internal bool modified;
47 internal bool multiline;
48 internal bool read_only;
49 internal bool word_wrap;
50 internal Document document;
51 internal LineTag caret_tag; // tag our cursor is in
52 internal int caret_pos; // position on the line our cursor is in (can be 0 = beginning of line)
53 internal int viewport_x; // left visible pixel
54 internal int viewport_y; // top visible pixel
55 internal HScrollBar hscroll;
56 internal VScrollBar vscroll;
57 internal ScrollBars scrollbars;
58 internal bool grabbed;
59 internal bool richtext;
60 internal Rectangle text_bounds;
63 internal static bool draw_lines = false;
66 #endregion // Local Variables
68 #region Private Constructor
69 // Constructor will go when complete, only for testing - pdb
70 public TextBoxBase() {
71 alignment = HorizontalAlignment.Left;
72 accepts_return = false;
75 border_style = BorderStyle.Fixed3D;
76 character_casing = CharacterCasing.Normal;
78 hide_selection = true;
85 document = new Document(this);
86 text_bounds = Rectangle.Empty;
88 MouseDown += new MouseEventHandler(TextBoxBase_MouseDown);
89 MouseUp += new MouseEventHandler(TextBoxBase_MouseUp);
90 MouseMove += new MouseEventHandler(TextBoxBase_MouseMove);
91 SizeChanged += new EventHandler(TextBoxBase_SizeChanged);
92 FontChanged += new EventHandler(TextBoxBase_FontOrColorChanged);
93 ForeColorChanged += new EventHandler(TextBoxBase_FontOrColorChanged);
96 scrollbars = ScrollBars.None;
98 hscroll = new HScrollBar();
99 hscroll.ValueChanged +=new EventHandler(hscroll_ValueChanged);
100 hscroll.Enabled = true;
101 hscroll.Visible = false;
103 vscroll = new VScrollBar();
104 vscroll.Visible = false;
106 this.Controls.Add(hscroll);
107 this.Controls.Add(vscroll);
109 //SetStyle(ControlStyles.ResizeRedraw, true);
110 SetStyle(ControlStyles.AllPaintingInWmPaint, true);
111 SetStyle(ControlStyles.UserPaint, true);
113 #endregion // Private Constructor
115 #region Private and Internal Methods
116 internal string CaseAdjust(string s) {
117 if (character_casing == CharacterCasing.Normal) {
120 if (character_casing == CharacterCasing.Lower) {
126 #endregion // Private and Internal Methods
128 #region Public Instance Properties
129 public bool AcceptsTab {
135 if (value != accepts_tab) {
137 OnAcceptsTabChanged(EventArgs.Empty);
142 public virtual bool AutoSize {
148 if (value != auto_size) {
151 if (PreferredHeight != Height) {
152 Height = PreferredHeight;
155 OnAutoSizeChanged(EventArgs.Empty);
160 public override System.Drawing.Color BackColor {
162 return base.BackColor;
165 base.BackColor = value;
169 public override System.Drawing.Image BackgroundImage {
171 return base.BackgroundImage;
174 base.BackgroundImage = value;
178 public BorderStyle BorderStyle {
184 if (value != border_style) {
185 border_style = value;
186 OnBorderStyleChanged(EventArgs.Empty);
191 public bool CanUndo {
197 public override System.Drawing.Color ForeColor {
199 return base.ForeColor;
202 base.ForeColor = value;
206 public bool HideSelection {
208 return hide_selection;
212 if (value != hide_selection) {
213 hide_selection = value;
214 OnHideSelectionChanged(EventArgs.Empty);
216 if (hide_selection) {
217 document.selection_visible = false;
219 document.selection_visible = true;
221 document.InvalidateSelectionArea();
226 public string[] Lines {
233 lines = new string[l];
235 for (i = 1; i <= l; i++) {
236 lines[i - 1] = document.GetLine(i).text.ToString();
250 brush = ThemeEngine.Current.ResPool.GetSolidBrush(this.ForeColor);
252 for (i = 0; i < l; i++) {
253 document.Add(i+1, CaseAdjust(value[i]), alignment, Font, brush);
255 document.RecalculateDocument(CreateGraphics());
256 OnTextChanged(EventArgs.Empty);
260 public virtual int MaxLength {
266 if (value != max_length) {
272 public bool Modified {
278 if (value != modified) {
280 OnModifiedChanged(EventArgs.Empty);
285 public virtual bool Multiline {
291 if (value != multiline) {
294 // Make sure we update our size; the user may have already set the size before going to multiline
295 if (text_bounds != Rectangle.Empty) {
296 SetBoundsCore(text_bounds.X, text_bounds.Y, text_bounds.Width, text_bounds.Height, BoundsSpecified.All);
299 OnMultilineChanged(EventArgs.Empty);
302 document.multiline = multiline;
306 public int PreferredHeight {
308 return this.Font.Height + 7; // FIXME - consider border style as well
312 public bool ReadOnly {
318 if (value != read_only) {
320 OnReadOnlyChanged(EventArgs.Empty);
325 public virtual string SelectedText {
327 return document.GetSelection();
331 document.ReplaceSelection(CaseAdjust(value));
332 OnTextChanged(EventArgs.Empty);
336 public virtual int SelectionLength {
338 return document.SelectionLength();
348 start = document.LineTagToCharIndex(document.selection_start.line, document.selection_start.pos);
350 document.CharIndexToLineTag(start + value, out line, out tag, out pos);
351 document.SetSelectionEnd(line, pos);
352 document.PositionCaret(line, pos);
354 document.SetSelectionEnd(document.selection_start.line, document.selection_start.pos);
355 document.PositionCaret(document.selection_start.line, document.selection_start.pos);
360 public int SelectionStart {
364 index = document.LineTagToCharIndex(document.selection_start.line, document.selection_start.pos);
374 document.CharIndexToLineTag(value, out line, out tag, out pos);
375 document.SetSelectionStart(line, pos);
379 public override string Text {
381 if (document == null || document.Root == null || document.Root.text == null) {
386 return document.Root.text.ToString();
391 sb = new StringBuilder();
393 for (i = 1; i < document.Lines; i++) {
394 sb.Append(document.GetLine(i).text.ToString() + Environment.NewLine);
397 return sb.ToString();
407 lines = value.Split(new char[] {'\n'});
408 for (int i = 0; i < lines.Length; i++) {
409 if (lines[i].EndsWith("\r")) {
410 lines[i] = lines[i].Substring(0, lines[i].Length - 1);
415 line = document.GetLine(1);
416 document.SetSelectionStart(line, 0);
418 line = document.GetLine(document.Lines);
419 document.SetSelectionEnd(line, line.text.Length);
420 document.PositionCaret(line, line.text.Length);
423 document.Add(1, CaseAdjust(value), alignment, Font, ThemeEngine.Current.ResPool.GetSolidBrush(ForeColor));
424 document.RecalculateDocument(CreateGraphics());
425 line = document.GetLine(1);
426 document.SetSelectionStart(line, 0);
427 document.SetSelectionEnd(line, value.Length);
428 document.PositionCaret(line, value.Length);
431 OnTextChanged(EventArgs.Empty);
435 public virtual int TextLength {
437 if (document == null || document.Root == null || document.Root.text == null) {
442 return document.Root.text.Length;
448 for (i = 1; i < document.Lines; i++) {
449 total += document.GetLine(i).text.Length + Environment.NewLine.Length;
457 public bool WordWrap {
463 if (value != word_wrap) {
468 #endregion // Public Instance Properties
470 #region Protected Instance Properties
471 protected override CreateParams CreateParams {
473 return base.CreateParams;
477 protected override System.Drawing.Size DefaultSize {
479 return base.DefaultSize;
482 #endregion // Protected Instance Properties
484 #region Public Instance Methods
485 public void AppendText(string text) {
491 // Break the string into separate lines
492 lines = text.Split(new char[] {'\n'});
493 linecount = lines.Length;
494 for (int i = 0; i < linecount; i++) {
495 if (lines[i].EndsWith("\r")) {
496 lines[i] = lines[i].Substring(0, lines[i].Length - 1);
500 // Grab the formatting for the last element
501 document.MoveCaret(CaretDirection.CtrlEnd);
503 // Insert the first line
504 document.InsertString(document.CaretLine, document.CaretPosition, lines[0]);
506 for (int i = 1; i < linecount; i++) {
507 document.Add(document.CaretLine.LineNo+i, CaseAdjust(lines[i]), alignment, document.CaretTag.font, document.CaretTag.color);
510 document.RecalculateDocument(CreateGraphics());
511 document.MoveCaret(CaretDirection.CtrlEnd);
514 document.MoveCaret(CaretDirection.CtrlEnd);
515 document.InsertStringAtCaret(text, true);
518 OnTextChanged(EventArgs.Empty);
521 public void Clear() {
523 throw new NotImplementedException();
526 public void ClearUndo() {
528 throw new NotImplementedException();
533 throw new NotImplementedException();
538 throw new NotImplementedException();
541 public void Paste() {
543 throw new NotImplementedException();
546 public void ScrollToCaret() {
548 throw new NotImplementedException();
551 public void Select(int start, int length) {
552 SelectionStart = start;
553 SelectionLength = length;
557 public void SelectAll() {
560 last = document.GetLine(document.Lines);
561 document.SetSelectionStart(document.GetLine(1), 0);
562 document.SetSelectionEnd(last, last.text.Length);
565 public override string ToString() {
570 sb = new StringBuilder();
572 end = document.Lines;
574 for (i = 1; i < end; i++) {
575 sb.Append(document.GetLine(i).text.ToString() + "\n");
578 return sb.ToString();
584 #endregion // Public Instance Methods
586 #region Protected Instance Methods
587 protected override void CreateHandle() {
588 base.CreateHandle ();
591 protected override bool IsInputKey(Keys keyData) {
594 if (multiline && (accepts_return || ((keyData & Keys.Control) != 0))) {
611 protected virtual void OnAcceptsTabChanged(EventArgs e) {
612 if (AcceptsTabChanged != null) {
613 AcceptsTabChanged(this, e);
617 protected virtual void OnAutoSizeChanged(EventArgs e) {
618 if (AutoSizeChanged != null) {
619 AutoSizeChanged(this, e);
623 protected virtual void OnBorderStyleChanged(EventArgs e) {
624 if (BorderStyleChanged != null) {
625 BorderStyleChanged(this, e);
629 protected override void OnFontChanged(EventArgs e) {
630 base.OnFontChanged (e);
633 if (PreferredHeight != Height) {
634 Height = PreferredHeight;
639 protected override void OnHandleCreated(EventArgs e) {
640 base.OnHandleCreated (e);
643 protected override void OnHandleDestroyed(EventArgs e) {
644 base.OnHandleDestroyed (e);
647 protected virtual void OnHideSelectionChanged(EventArgs e) {
648 if (HideSelectionChanged != null) {
649 HideSelectionChanged(this, e);
653 protected virtual void OnModifiedChanged(EventArgs e) {
654 if (ModifiedChanged != null) {
655 ModifiedChanged(this, e);
659 protected virtual void OnMultilineChanged(EventArgs e) {
660 if (MultilineChanged != null) {
661 MultilineChanged(this, e);
665 protected virtual void OnReadOnlyChanged(EventArgs e) {
666 if (ReadOnlyChanged != null) {
667 ReadOnlyChanged(this, e);
671 protected override bool ProcessDialogKey(Keys keyData) {
672 return base.ProcessDialogKey (keyData);
675 protected override void SetBoundsCore(int x, int y, int width, int height, BoundsSpecified specified) {
676 // Make sure we don't get sized bigger than we want to be
679 if (height > PreferredHeight) {
680 text_bounds = new Rectangle(x, y, width, height);
681 text_bounds.Height = PreferredHeight;
685 base.SetBoundsCore (x, y, width, height, specified);
688 protected override void WndProc(ref Message m) {
689 switch ((Msg)m.Msg) {
691 PaintEventArgs paint_event;
693 paint_event = XplatUI.PaintEventStart(Handle);
695 PaintControl(paint_event);
696 XplatUI.PaintEventEnd(Handle);
701 case Msg.WM_SETFOCUS: {
703 document.CaretHasFocus();
704 Console.WriteLine("Creating caret");
709 case Msg.WM_KILLFOCUS: {
711 document.CaretLostFocus();
712 Console.WriteLine("Destroying caret");
717 case Msg.WM_KEYDOWN: {
718 switch ((Keys)(m.WParam.ToInt32())) {
720 document.SetSelectionToCaret(true);
722 if ((Control.ModifierKeys & Keys.Control) != 0) {
723 document.MoveCaret(CaretDirection.WordBack);
725 document.MoveCaret(CaretDirection.CharBack);
731 document.SetSelectionToCaret(true);
733 if ((Control.ModifierKeys & Keys.Control) != 0) {
734 document.MoveCaret(CaretDirection.WordForward);
736 document.MoveCaret(CaretDirection.CharForward);
742 document.SetSelectionToCaret(true);
743 document.MoveCaret(CaretDirection.LineUp);
748 document.SetSelectionToCaret(true);
749 document.MoveCaret(CaretDirection.LineDown);
754 document.SetSelectionToCaret(true);
756 if ((Control.ModifierKeys & Keys.Control) != 0) {
757 document.MoveCaret(CaretDirection.CtrlHome);
759 document.MoveCaret(CaretDirection.Home);
765 document.SetSelectionToCaret(true);
767 if ((Control.ModifierKeys & Keys.Control) != 0) {
768 document.MoveCaret(CaretDirection.CtrlEnd);
770 document.MoveCaret(CaretDirection.End);
776 if (multiline && (accepts_return || ((Control.ModifierKeys & Keys.Control) != 0))) {
777 if (document.selection_visible) {
778 document.ReplaceSelection("");
780 document.SetSelectionToCaret(true);
782 document.Split(document.CaretLine, document.CaretTag, document.CaretPosition);
783 OnTextChanged(EventArgs.Empty);
784 document.UpdateView(document.CaretLine, 2, 0);
785 document.MoveCaret(CaretDirection.CharForward);
793 document.InsertChar(document.CaretLine, document.CaretPosition, '\t');
794 if (document.selection_visible) {
795 document.ReplaceSelection("");
797 document.SetSelectionToCaret(true);
799 OnTextChanged(EventArgs.Empty);
808 // delete only deletes on the line, doesn't do the combine
809 if (document.selection_visible) {
810 document.ReplaceSelection("");
812 document.SetSelectionToCaret(true);
813 if (document.CaretPosition == 0) {
814 if (document.CaretLine.LineNo > 1) {
818 line = document.GetLine(document.CaretLine.LineNo - 1);
819 new_caret_pos = line.text.Length;
821 document.Combine(line, document.CaretLine);
822 document.UpdateView(line, 1, 0);
823 document.PositionCaret(line, new_caret_pos);
824 document.UpdateCaret();
825 OnTextChanged(EventArgs.Empty);
828 document.DeleteChar(document.CaretTag, document.CaretPosition, false);
829 document.MoveCaret(CaretDirection.CharBack);
830 OnTextChanged(EventArgs.Empty);
836 // delete only deletes on the line, doesn't do the combine
837 if (document.CaretPosition == document.CaretLine.text.Length) {
838 if (document.CaretLine.LineNo < document.Lines) {
841 line = document.GetLine(document.CaretLine.LineNo + 1);
842 document.Combine(document.CaretLine, line);
843 document.UpdateView(document.CaretLine, 2, 0);
844 OnTextChanged(EventArgs.Empty);
850 check_first = document.GetLine(document.CaretLine.LineNo);
851 check_second = document.GetLine(check_first.line_no + 1);
853 Console.WriteLine("Post-UpdateView: Y of first line: {0}, second line: {1}", check_first.Y, check_second.Y);
856 // Caret doesn't move
859 document.DeleteChar(document.CaretTag, document.CaretPosition, true);
860 OnTextChanged(EventArgs.Empty);
870 if (m.WParam.ToInt32() >= 32) { // FIXME, tabs should probably go through
871 if (document.selection_visible) {
872 document.ReplaceSelection("");
875 switch (character_casing) {
876 case CharacterCasing.Normal: {
877 document.InsertCharAtCaret((char)m.WParam, true);
878 OnTextChanged(EventArgs.Empty);
882 case CharacterCasing.Lower: {
883 document.InsertCharAtCaret(Char.ToLower((char)m.WParam), true);
884 OnTextChanged(EventArgs.Empty);
888 case CharacterCasing.Upper: {
889 document.InsertCharAtCaret(Char.ToUpper((char)m.WParam), true);
890 OnTextChanged(EventArgs.Empty);
906 #endregion // Protected Instance Methods
909 public event EventHandler AcceptsTabChanged;
910 public event EventHandler AutoSizeChanged;
911 public event EventHandler BorderStyleChanged;
912 public event EventHandler Click;
913 public event EventHandler HideSelectionChanged;
914 public event EventHandler ModifiedChanged;
915 public event EventHandler MultilineChanged;
916 public event PaintEventHandler Paint;
917 public event EventHandler ReadOnlyChanged;
920 #region Private Methods
921 internal Document Document {
933 private void PaintControl(PaintEventArgs pevent) {
935 pevent.Graphics.FillRectangle(ThemeEngine.Current.ResPool.GetSolidBrush(BackColor), pevent.ClipRectangle);
936 //pevent.Graphics.TextRenderingHint=TextRenderingHint.AntiAlias;
938 // Draw the viewable document
939 document.Draw(pevent.Graphics, pevent.ClipRectangle);
941 Rectangle rect = ClientRectangle;
944 pevent.Graphics.DrawRectangle(ThemeEngine.Current.ResPool.GetPen(ThemeEngine.Current.ColorButtonShadow), rect);
947 switch (scrollbars) {
948 case ScrollBars.Both: {
951 case ScrollBars.Vertical: {
954 case ScrollBars.Horizontal: {
956 hscroll.Maximum = document.Width - this.Width;
968 p = new Pen(Color.Red, 1);
970 // First, figure out from what line to what line we need to draw
971 start = document.GetLineByPixel(pevent.ClipRectangle.Top - viewport_y, false).line_no;
972 end = document.GetLineByPixel(pevent.ClipRectangle.Bottom - viewport_y, false).line_no;
974 //Console.WriteLine("Starting drawing on line '{0}'", document.GetLine(start));
975 //Console.WriteLine("Ending drawing on line '{0}'", document.GetLine(end));
978 while (line_no <= end) {
979 line = document.GetLine(line_no);
982 for (int i = 0; i < line.text.Length; i++) {
983 pevent.Graphics.DrawLine(p, (int)line.widths[i] - document.ViewPortX, line.Y - document.ViewPortY, (int)line.widths[i] - document.ViewPortX, line.Y + line.height - document.ViewPortY);
992 private void TextBoxBase_MouseDown(object sender, MouseEventArgs e) {
997 if (e.Button == MouseButtons.Left) {
998 document.PositionCaret(e.X, e.Y);
999 document.SetSelectionToCaret(true);
1000 this.grabbed = true;
1001 this.Capture = true;
1006 if (e.Button == MouseButtons.Right) {
1007 draw_lines = !draw_lines;
1009 Console.WriteLine("SelectedText: {0}, length {1}", this.SelectedText, this.SelectionLength);
1010 Console.WriteLine("Selection start: {0}", this.SelectionStart);
1012 this.SelectionStart = 10;
1013 this.SelectionLength = 5;
1018 tag = document.FindTag(e.X, e.Y, out pos, false);
1020 Console.WriteLine("Click found tag {0}, character {1}", tag, pos);
1023 case 4: LineTag.FormatText(tag.line, pos, (pos+10)<line.Text.Length ? 10 : line.Text.Length - pos+1, new Font("impact", 20, FontStyle.Bold, GraphicsUnit.Pixel), ThemeEngine.Current.ResPool.GetSolidBrush(Color.Red)); break;
1024 case 1: LineTag.FormatText(tag.line, pos, (pos+10)<line.Text.Length ? 10 : line.Text.Length - pos+1, new Font("arial unicode ms", 24, FontStyle.Italic, GraphicsUnit.Pixel), ThemeEngine.Current.ResPool.GetSolidBrush(Color.DarkGoldenrod)); break;
1025 case 2: LineTag.FormatText(tag.line, pos, (pos+10)<line.Text.Length ? 10 : line.Text.Length - pos+1, new Font("arial", 10, FontStyle.Regular, GraphicsUnit.Pixel), ThemeEngine.Current.ResPool.GetSolidBrush(Color.Aquamarine)); break;
1026 case 3: LineTag.FormatText(tag.line, pos, (pos+10)<line.Text.Length ? 10 : line.Text.Length - pos+1, new Font("times roman", 16, FontStyle.Underline, GraphicsUnit.Pixel), ThemeEngine.Current.ResPool.GetSolidBrush(Color.Turquoise)); break;
1027 case 0: LineTag.FormatText(tag.line, pos, (pos+10)<line.Text.Length ? 10 : line.Text.Length - pos+1, new Font("times roman", 64, FontStyle.Italic | FontStyle.Bold, GraphicsUnit.Pixel), ThemeEngine.Current.ResPool.GetSolidBrush(Color.LightSeaGreen)); break;
1028 case 5: LineTag.FormatText(tag.line, pos, (pos+10)<line.Text.Length ? 10 : line.Text.Length - pos+1, ((TextBoxBase)sender).Font, ThemeEngine.Current.ResPool.GetSolidBrush(ForeColor)); break;
1035 // Update/Recalculate what we see
1036 document.UpdateView(line, 0);
1038 // Make sure our caret is properly positioned and sized
1039 document.AlignCaret();
1043 private void TextBoxBase_MouseUp(object sender, MouseEventArgs e) {
1044 this.Capture = false;
1045 this.grabbed = false;
1046 if (e.Button == MouseButtons.Left) {
1047 document.PositionCaret(e.X + viewport_x, e.Y + viewport_y);
1048 document.SetSelectionToCaret(false);
1049 document.DisplayCaret();
1053 #endregion // Private Methods
1056 private void TextBoxBase_SizeChanged(object sender, EventArgs e) {
1058 // First, check which scrollbars we need
1060 hscroll.Bounds = new Rectangle (ClientRectangle.Left, ClientRectangle.Bottom - hscroll.Height, Width, hscroll.Height);
1064 private void hscroll_ValueChanged(object sender, EventArgs e) {
1065 XplatUI.ScrollWindow(this.Handle, document.ViewPortX-this.hscroll.Value, 0, true);
1066 document.ViewPortX = this.hscroll.Value;
1067 document.UpdateCaret();
1068 Console.WriteLine("Dude scrolled");
1071 private void TextBoxBase_MouseMove(object sender, MouseEventArgs e) {
1072 // FIXME - handle auto-scrolling if mouse is to the right/left of the window
1074 document.PositionCaret(e.X + viewport_x, e.Y + viewport_y);
1075 document.SetSelectionToCaret(false);
1076 document.DisplayCaret();
1080 private void TextBoxBase_FontOrColorChanged(object sender, EventArgs e) {
1084 // Font changes apply to the whole document
1085 for (int i = 1; i <= document.Lines; i++) {
1086 line = document.GetLine(i);
1087 LineTag.FormatText(line, 1, line.text.Length, Font, ThemeEngine.Current.ResPool.GetSolidBrush(ForeColor));
1088 document.UpdateView(line, 0);
1090 // Make sure the caret height is matching the new font height
1091 document.AlignCaret();