]> git.saurik.com Git - wxWidgets.git/blob - src/generic/caret.cpp
second merge of the 2.2 branch (RL)
[wxWidgets.git] / src / generic / caret.cpp
1 ///////////////////////////////////////////////////////////////////////////////
2 // Name: generic/caret.cpp
3 // Purpose: generic wxCaret class implementation
4 // Author: Vadim Zeitlin (original code by Robert Roebling)
5 // Modified by:
6 // Created: 25.05.99
7 // RCS-ID: $Id$
8 // Copyright: (c) wxWindows team
9 // Licence: wxWindows licence
10 ///////////////////////////////////////////////////////////////////////////////
11
12 // ============================================================================
13 // declarations
14 // ============================================================================
15
16 // ----------------------------------------------------------------------------
17 // headers
18 // ----------------------------------------------------------------------------
19
20 #ifdef __GNUG__
21 #pragma implementation "caret.h"
22 #endif
23
24 // For compilers that support precompilation, includes "wx.h".
25 #include "wx/wxprec.h"
26
27 #ifdef __BORLANDC__
28 #pragma hdrstop
29 #endif
30
31 #ifndef WX_PRECOMP
32 #include "wx/window.h"
33 #include "wx/dcclient.h"
34 #endif //WX_PRECOMP
35
36 #include "wx/caret.h"
37
38 // ----------------------------------------------------------------------------
39 // global variables for this module
40 // ----------------------------------------------------------------------------
41
42 // the blink time (common to all carets for MSW compatibility)
43 static int gs_blinkTime = 500; // in milliseconds
44
45 // ============================================================================
46 // implementation
47 // ============================================================================
48
49 // ----------------------------------------------------------------------------
50 // timer stuff
51 // ----------------------------------------------------------------------------
52
53 wxCaretTimer::wxCaretTimer(wxCaret *caret)
54 {
55 m_caret = caret;
56 }
57
58 void wxCaretTimer::Notify()
59 {
60 m_caret->OnTimer();
61 }
62
63 void wxCaret::OnTimer()
64 {
65 // don't blink the caret when we don't have the focus
66 if ( m_hasFocus )
67 Blink();
68 }
69
70 // ----------------------------------------------------------------------------
71 // wxCaret static functions and data
72 // ----------------------------------------------------------------------------
73
74 int wxCaretBase::GetBlinkTime()
75 {
76 return gs_blinkTime;
77 }
78
79 void wxCaretBase::SetBlinkTime(int milliseconds)
80 {
81 gs_blinkTime = milliseconds;
82 }
83
84 // ----------------------------------------------------------------------------
85 // initialization and destruction
86 // ----------------------------------------------------------------------------
87
88 void wxCaret::InitGeneric()
89 {
90 m_hasFocus = TRUE;
91 m_blinkedOut = FALSE;
92 }
93
94 wxCaret::~wxCaret()
95 {
96 if ( IsVisible() )
97 {
98 // stop blinking
99 m_timer.Stop();
100 }
101 }
102
103 // ----------------------------------------------------------------------------
104 // showing/hiding/moving the caret (base class interface)
105 // ----------------------------------------------------------------------------
106
107 void wxCaret::DoShow()
108 {
109 m_timer.Start(GetBlinkTime());
110
111 m_blinkedOut = TRUE;
112 Blink();
113 }
114
115 void wxCaret::DoHide()
116 {
117 m_timer.Stop();
118
119 if ( !m_blinkedOut )
120 {
121 Blink();
122 }
123 }
124
125 void wxCaret::DoMove()
126 {
127 if ( IsVisible() && !m_blinkedOut )
128 {
129 Blink();
130 }
131 //else: will be shown at the correct location next time it blinks
132 }
133
134 // ----------------------------------------------------------------------------
135 // handling the focus
136 // ----------------------------------------------------------------------------
137
138 void wxCaret::OnSetFocus()
139 {
140 m_hasFocus = TRUE;
141
142 Refresh();
143 }
144
145 void wxCaret::OnKillFocus()
146 {
147 m_hasFocus = FALSE;
148
149 if ( IsVisible() )
150 {
151 // the caret must be shown - otherwise, if it is hidden now, it will
152 // stay so until the focus doesn't return because it won't blink any
153 // more
154 m_blinkedOut = FALSE;
155 }
156
157 Refresh();
158 }
159
160 // ----------------------------------------------------------------------------
161 // drawing the caret
162 // ----------------------------------------------------------------------------
163
164 void wxCaret::Blink()
165 {
166 m_blinkedOut = !m_blinkedOut;
167
168 Refresh();
169 }
170
171 void wxCaret::Refresh()
172 {
173 if ( !m_blinkedOut )
174 {
175 wxClientDC dc(GetWindow());
176 DoDraw(&dc);
177 }
178 else
179 {
180 // FIXME can't be less efficient than this... we probably should use
181 // backing store for the caret instead of leaving all the burden
182 // of correct refresh logic handling to the user code
183
184 // NB: +1 is needed!
185 wxRect rect(m_x, m_y, m_width + 1, m_height + 1);
186 GetWindow()->Refresh(FALSE, &rect);
187 }
188 }
189
190 void wxCaret::DoDraw(wxDC *dc)
191 {
192 dc->SetPen( *wxBLACK_PEN );
193
194 // VZ: Robert's code for I-shaped caret - this is nice but doesn't look
195 // at all the same as the MSW version and I don't know how to indicate
196 // that the window has focus or not with such caret
197 #if 0
198 dc->DrawLine( m_x, m_y, m_x+m_width, m_y );
199 dc->DrawLine( m_x, m_y+m_height, m_x+m_width, m_y+m_height );
200 dc->DrawLine( m_x+(m_width/2), m_y, m_x+(m_width/2), m_y+m_height );
201 // dc->DrawLine( m_x+(m_width/2)+1, m_y, m_x+(m_width/2)+1, m_y+m_height );
202 #else // 1
203 if ( m_hasFocus )
204 dc->SetBrush( *wxBLACK_BRUSH );
205 dc->DrawRectangle( m_x, m_y, m_width, m_height );
206 #endif // 0/1
207 }