|
1 // ConsoleWindow.cpp |
|
2 // |
|
3 // Copyright (c) 2010 Accenture. All rights reserved. |
|
4 // This component and the accompanying materials are made available |
|
5 // under the terms of the "Eclipse Public License v1.0" |
|
6 // which accompanies this distribution, and is available |
|
7 // at the URL "http://www.eclipse.org/legal/epl-v10.html". |
|
8 // |
|
9 // Initial Contributors: |
|
10 // Accenture - Initial contribution |
|
11 // |
|
12 #include "Misc.h" |
|
13 #include <windowsx.h> |
|
14 #include "stdafx.h" |
|
15 #include "ConsoleWindow.h" |
|
16 #include "TextBuffer.h" |
|
17 #include "TextView.h" |
|
18 #include "resource.h" |
|
19 |
|
20 const int KMaxFormatBuf = 256; |
|
21 |
|
22 |
|
23 CConsoleWindow* CConsoleWindow::New(HINSTANCE aAppHandle, LPCTSTR aWindowClass, LPCTSTR aTitle, int aPosX, int aPosY, int aWidth, int aHeight, int aNumOverflowLines, MWindowObserver* aWindowObserver, MConsoleCharHandler* aCharHandler, bool aNoSelection) |
|
24 { |
|
25 std::auto_ptr<CConsoleWindow> self(new(EThrow) CConsoleWindow(aNoSelection)); |
|
26 self->Construct(aAppHandle, aWindowClass, aTitle, aPosX, aPosY, aWidth, aHeight, aNumOverflowLines, aWindowObserver, aCharHandler); |
|
27 return self.release(); |
|
28 } |
|
29 |
|
30 CConsoleWindow::~CConsoleWindow() |
|
31 { |
|
32 delete iView; |
|
33 delete iBuffer; |
|
34 } |
|
35 |
|
36 void CConsoleWindow::Write(LPCTSTR aString) |
|
37 { |
|
38 Write(aString, wcslen(aString)); |
|
39 } |
|
40 |
|
41 void CConsoleWindow::Write(LPCTSTR aString, int aLength) |
|
42 { |
|
43 iView->BeginUpdate(); |
|
44 iBuffer->Write(aString, aLength); |
|
45 iView->EndUpdate(); |
|
46 } |
|
47 |
|
48 void CConsoleWindow::WriteFormat(LPCTSTR aFormat, ...) |
|
49 { |
|
50 va_list args; |
|
51 va_start(args, aFormat); |
|
52 TCHAR buf[KMaxFormatBuf]; |
|
53 int length = _vsnwprintf(buf, KMaxFormatBuf, aFormat, args); |
|
54 Write(buf, length); |
|
55 } |
|
56 |
|
57 void CConsoleWindow::GetCursorPos(int& aX, int& aY) |
|
58 { |
|
59 iBuffer->GetCursorPos(aX, aY); |
|
60 } |
|
61 |
|
62 void CConsoleWindow::SetAbsCursorPos(int aX, int aY) |
|
63 { |
|
64 iView->BeginUpdate(); |
|
65 iBuffer->SetAbsCursorPos(aX, aY); |
|
66 iView->EndUpdate(); |
|
67 } |
|
68 |
|
69 void CConsoleWindow::SetRelCursorPos(int aX, int aY) |
|
70 { |
|
71 iView->BeginUpdate(); |
|
72 iBuffer->SetRelCursorPos(aX, aY); |
|
73 iView->EndUpdate(); |
|
74 } |
|
75 |
|
76 void CConsoleWindow::SetCursorHeight(int aHeight) |
|
77 { |
|
78 (aHeight > 0) ? iView->EnableCursor() : iView->DisableCursor(); |
|
79 } |
|
80 |
|
81 void CConsoleWindow::GetConsoleSize(int& aWidth, int& aHeight) |
|
82 { |
|
83 iBuffer->GetSize(aWidth, aHeight); |
|
84 } |
|
85 |
|
86 void CConsoleWindow::ClearScreen() |
|
87 { |
|
88 iView->BeginUpdate(); |
|
89 iBuffer->Clear(); |
|
90 iView->EndUpdate(); |
|
91 } |
|
92 |
|
93 void CConsoleWindow::ClearToEndOfLine() |
|
94 { |
|
95 iView->BeginUpdate(); |
|
96 iBuffer->ClearToEndOfLine(); |
|
97 iView->EndUpdate(); |
|
98 } |
|
99 |
|
100 void CConsoleWindow::CaptureToFile(LPCTSTR aFileName) |
|
101 { |
|
102 iBuffer->CaptureToFile(aFileName); |
|
103 } |
|
104 |
|
105 void CConsoleWindow::StopCaptureToFile() |
|
106 { |
|
107 iBuffer->StopCaptureToFile(); |
|
108 } |
|
109 |
|
110 bool CConsoleWindow::IsCapturingToFile() const |
|
111 { |
|
112 return iBuffer->IsCapturingToFile(); |
|
113 } |
|
114 |
|
115 void CConsoleWindow::PasteFromClipboard() |
|
116 { |
|
117 if (iCharHandler && OpenClipboard(Handle())) |
|
118 { |
|
119 HGLOBAL hglb = GetClipboardData(CF_TEXT); |
|
120 if (hglb) |
|
121 { |
|
122 char* narrowBuf = (char*)GlobalLock(hglb); |
|
123 if (narrowBuf) |
|
124 { |
|
125 LPTSTR wideBuf; |
|
126 int length = strlen(narrowBuf); |
|
127 ConvertNarrowToWideAlloc(narrowBuf, length, wideBuf); |
|
128 if (wideBuf) |
|
129 { |
|
130 iCharHandler->HandleConsoleString(wideBuf, length); |
|
131 delete wideBuf; |
|
132 } |
|
133 GlobalUnlock(hglb); |
|
134 } |
|
135 } |
|
136 CloseClipboard(); |
|
137 } |
|
138 } |
|
139 |
|
140 void CConsoleWindow::CopyToClipboard() const |
|
141 { |
|
142 if (OpenClipboard(Handle())) |
|
143 { |
|
144 EmptyClipboard(); |
|
145 LPTSTR wideSelection = iView->Selection(); |
|
146 if (wideSelection) |
|
147 { |
|
148 int length = wcslen(wideSelection); |
|
149 HGLOBAL hglbCopy = GlobalAlloc(GMEM_MOVEABLE, (length + 1) * sizeof(TCHAR)); |
|
150 if (hglbCopy) |
|
151 { |
|
152 char* narrowBuf = (char*)GlobalLock(hglbCopy); |
|
153 ConvertWideToNarrow(wideSelection, length, narrowBuf); |
|
154 GlobalUnlock(hglbCopy); |
|
155 SetClipboardData(CF_TEXT, hglbCopy); |
|
156 iView->ClearSelection(); |
|
157 } |
|
158 delete wideSelection; |
|
159 } |
|
160 CloseClipboard(); |
|
161 } |
|
162 } |
|
163 |
|
164 void CConsoleWindow::SetDimmed(bool aDimmed) |
|
165 { |
|
166 iView->SetDimmed(aDimmed); |
|
167 } |
|
168 |
|
169 CConsoleWindow::CConsoleWindow(bool aNoSelection) : iCharHandler(NULL), iBuffer(NULL), iView(NULL), iNoSelection(aNoSelection) |
|
170 { |
|
171 } |
|
172 |
|
173 void CConsoleWindow::Construct(HINSTANCE aAppHandle, LPCTSTR aWindowClass, LPCTSTR aTitle, int aPosX, int aPosY, int aCharWidth, int aCharHeight, int aNumOverflowLines, MWindowObserver* aWindowObserver, MConsoleCharHandler* aCharHandler) |
|
174 { |
|
175 iCharHandler = aCharHandler; |
|
176 |
|
177 int numHorizChars = (aCharWidth == -1) ? 80 : aCharWidth; |
|
178 int numVertChars = (aCharHeight == -1) ? 40 : aCharHeight; |
|
179 |
|
180 iBuffer = CTextBuffer::New(numHorizChars, numVertChars, aNumOverflowLines); |
|
181 iView = CTextView::New(*this, *iBuffer, aCharWidth, aCharHeight); |
|
182 if (!iCharHandler) |
|
183 { |
|
184 iView->DisableCursor(); |
|
185 } |
|
186 |
|
187 int pixelWidth; |
|
188 int pixelHeight; |
|
189 iView->GetSize(pixelWidth, pixelHeight); |
|
190 |
|
191 CWindow::Construct(aAppHandle, aWindowClass, aTitle, aPosX, aPosY, pixelWidth, pixelHeight, aWindowObserver); |
|
192 } |
|
193 |
|
194 void CConsoleWindow::Draw() const |
|
195 { |
|
196 iView->Draw(); |
|
197 } |
|
198 |
|
199 LRESULT CConsoleWindow::HandleChar(TCHAR aChar, UINT aModifiers) |
|
200 { |
|
201 if (iCharHandler) |
|
202 { |
|
203 iView->ScrollToEndIfNeeded(); |
|
204 iCharHandler->HandleConsoleChar(aChar, aModifiers); |
|
205 } |
|
206 return 0; |
|
207 } |
|
208 |
|
209 LRESULT CConsoleWindow::HandleFocusChange(bool aFocused) |
|
210 { |
|
211 aFocused ? iView->HandleFocusGained() : iView->HandleFocusLost(); |
|
212 return 0; |
|
213 } |
|
214 |
|
215 void CConsoleWindow::HandleScrollEvent(UINT aMessage, WPARAM aWParam) |
|
216 { |
|
217 int scrollDir = (aMessage == WM_HSCROLL) ? SB_HORZ : SB_VERT; |
|
218 SCROLLINFO scrollInfo; |
|
219 scrollInfo.cbSize = sizeof(scrollInfo); |
|
220 scrollInfo.fMask = SIF_ALL; |
|
221 GetScrollInfo(Handle(), scrollDir, &scrollInfo); |
|
222 int pos = scrollInfo.nPos; |
|
223 switch (LOWORD(aWParam)) |
|
224 { |
|
225 case SB_LINEUP: // Also SB_LINELEFT. |
|
226 scrollInfo.nPos -= (aMessage == WM_HSCROLL) ? iView->CharWidth() : iView->CharHeight(); |
|
227 break; |
|
228 case SB_LINEDOWN: // Also SB_LINERIGHT. |
|
229 scrollInfo.nPos += (aMessage == WM_HSCROLL) ? iView->CharWidth() : iView->CharHeight(); |
|
230 break; |
|
231 case SB_PAGEUP: // Also SB_PAGELEFT. |
|
232 scrollInfo.nPos -= scrollInfo.nPage; |
|
233 break; |
|
234 case SB_PAGEDOWN: // Also SB_PAGERIGHT. |
|
235 scrollInfo.nPos += scrollInfo.nPage; |
|
236 break; |
|
237 case SB_THUMBTRACK: |
|
238 scrollInfo.nPos = scrollInfo.nTrackPos; |
|
239 break; |
|
240 default: |
|
241 break; |
|
242 } |
|
243 scrollInfo.fMask = SIF_POS; |
|
244 SetScrollInfo (Handle(), scrollDir, &scrollInfo, TRUE); |
|
245 GetScrollInfo (Handle(), scrollDir, &scrollInfo); |
|
246 if (scrollInfo.nPos != pos) |
|
247 { |
|
248 if (aMessage == WM_HSCROLL) |
|
249 { |
|
250 iView->SetHorzScrollPosition(scrollInfo.nPos); |
|
251 } |
|
252 else |
|
253 { |
|
254 iView->SetVertScrollPosition(scrollInfo.nPos); |
|
255 } |
|
256 } |
|
257 } |
|
258 |
|
259 void CConsoleWindow::HandleSizeChanged(int aWidth, int aHeight) |
|
260 { |
|
261 iView->SetSize(aWidth, aHeight); |
|
262 } |
|
263 |
|
264 void CConsoleWindow::HandleMouseEvent(UINT aMessage, WPARAM aWParam, LPARAM aLParam) |
|
265 { |
|
266 if (!iNoSelection) |
|
267 { |
|
268 switch(aMessage) |
|
269 { |
|
270 case WM_LBUTTONDOWN: |
|
271 { |
|
272 SetCapture(Handle()); |
|
273 iView->StartSelection(GET_X_LPARAM(aLParam), GET_Y_LPARAM(aLParam)); |
|
274 break; |
|
275 } |
|
276 case WM_LBUTTONDBLCLK: |
|
277 { |
|
278 iView->SelectWord(GET_X_LPARAM(aLParam), GET_Y_LPARAM(aLParam)); |
|
279 break; |
|
280 } |
|
281 case WM_MOUSEMOVE: |
|
282 { |
|
283 RECT clientRect; |
|
284 GetClientRect(Handle(), &clientRect); |
|
285 POINT mousePos = { GET_X_LPARAM(aLParam), GET_Y_LPARAM(aLParam) }; |
|
286 if ((mousePos.x > clientRect.right) || (mousePos.x < clientRect.left)) |
|
287 { |
|
288 SCROLLINFO scrollInfo; |
|
289 scrollInfo.cbSize = sizeof(scrollInfo); |
|
290 scrollInfo.fMask = SIF_POS; |
|
291 GetScrollInfo(Handle(), SB_HORZ, &scrollInfo); |
|
292 if (mousePos.x > clientRect.right) |
|
293 { |
|
294 scrollInfo.nPos += iView->CharWidth(); |
|
295 } |
|
296 else |
|
297 { |
|
298 scrollInfo.nPos -= iView->CharWidth(); |
|
299 } |
|
300 SetScrollInfo (Handle(), SB_HORZ, &scrollInfo, TRUE); |
|
301 GetScrollInfo (Handle(), SB_HORZ, &scrollInfo); |
|
302 iView->SetHorzScrollPosition(scrollInfo.nPos); |
|
303 } |
|
304 if ((mousePos.y < clientRect.top) || (mousePos.y > clientRect.bottom)) |
|
305 { |
|
306 SCROLLINFO scrollInfo; |
|
307 scrollInfo.cbSize = sizeof(scrollInfo); |
|
308 scrollInfo.fMask = SIF_POS; |
|
309 GetScrollInfo(Handle(), SB_VERT, &scrollInfo); |
|
310 if (mousePos.y < clientRect.top) |
|
311 { |
|
312 scrollInfo.nPos -= iView->CharHeight(); |
|
313 } |
|
314 else |
|
315 { |
|
316 scrollInfo.nPos += iView->CharHeight(); |
|
317 } |
|
318 SetScrollInfo (Handle(), SB_VERT, &scrollInfo, TRUE); |
|
319 GetScrollInfo (Handle(), SB_VERT, &scrollInfo); |
|
320 iView->SetVertScrollPosition(scrollInfo.nPos); |
|
321 } |
|
322 |
|
323 iView->AdjustSelection(GET_X_LPARAM(aLParam), GET_Y_LPARAM(aLParam)); |
|
324 break; |
|
325 } |
|
326 case WM_LBUTTONUP: |
|
327 { |
|
328 ReleaseCapture(); |
|
329 iView->EndSelection(GET_X_LPARAM(aLParam), GET_Y_LPARAM(aLParam)); |
|
330 break; |
|
331 } |
|
332 default: |
|
333 { |
|
334 break; |
|
335 } |
|
336 } |
|
337 } |
|
338 } |
|
339 |
|
340 void CConsoleWindow::HandleMenuPopUp(HMENU aMenu) |
|
341 { |
|
342 int numMenuItems = GetMenuItemCount(aMenu); |
|
343 for (int i = 0; i < numMenuItems; ++i) |
|
344 { |
|
345 switch (GetMenuItemID(aMenu, i)) |
|
346 { |
|
347 case ID_EDIT_COPY: |
|
348 { |
|
349 EnableMenuItem(aMenu, ID_EDIT_COPY, iView->SelectionAvailable() ? MF_BYCOMMAND | MF_ENABLED : MF_BYCOMMAND | MF_GRAYED); |
|
350 break; |
|
351 } |
|
352 case ID_EDIT_PASTE: |
|
353 { |
|
354 EnableMenuItem(aMenu, ID_EDIT_PASTE, iCharHandler && IsClipboardFormatAvailable(CF_TEXT) ? MF_BYCOMMAND | MF_ENABLED : MF_BYCOMMAND | MF_GRAYED); |
|
355 break; |
|
356 } |
|
357 default: |
|
358 { |
|
359 break; |
|
360 } |
|
361 } |
|
362 } |
|
363 } |