]> asedeno.scripts.mit.edu Git - PuTTY_svn.git/blob - mac/macevlog.c
Scroll the event log to the end after adding a line if it was looking at the
[PuTTY_svn.git] / mac / macevlog.c
1 /* $Id: macevlog.c,v 1.4 2003/02/23 12:41:44 ben Exp $ */
2 /*
3  * Copyright (c) 2003 Ben Harris
4  * All rights reserved.
5  *
6  * Permission is hereby granted, free of charge, to any person
7  * obtaining a copy of this software and associated documentation
8  * files (the "Software"), to deal in the Software without
9  * restriction, including without limitation the rights to use,
10  * copy, modify, merge, publish, distribute, sublicense, and/or
11  * sell copies of the Software, and to permit persons to whom the
12  * Software is furnished to do so, subject to the following
13  * conditions:
14  * 
15  * The above copyright notice and this permission notice shall be
16  * included in all copies or substantial portions of the Software.
17  * 
18  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
19  * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
20  * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
21  * NONINFRINGEMENT.  IN NO EVENT SHALL THE AUTHORS BE LIABLE FOR
22  * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF
23  * CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN
24  * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
25  * SOFTWARE.
26  */
27
28 #include <MacTypes.h>
29 #include <Lists.h>
30 #include <MacWindows.h>
31 #include <Quickdraw.h>
32 #include <Script.h>
33 #include <ToolUtils.h>
34
35 #include <limits.h>
36 #include <string.h>
37
38 #include "putty.h"
39 #include "mac.h"
40 #include "macresid.h"
41 #include "terminal.h"
42
43 static void mac_draweventloggrowicon(Session *s);
44 static void mac_adjusteventlogscrollbar(Session *s);
45 static void mac_clickeventlog(WindowPtr, EventRecord *);
46 static void mac_activateeventlog(WindowPtr, EventRecord *);
47 static void mac_groweventlog(WindowPtr, EventRecord *);
48 static void mac_updateeventlog(WindowPtr);
49
50 static void mac_createeventlog(Session *s)
51 {
52     Rect view;
53     ListBounds bounds = { 0, 0, 0, 1 }; /* 1 column, 0 rows */
54     Point csize = { 0, 0 };
55     GrafPtr saveport;
56     long fondsize;
57     WinInfo *wi;
58
59     s->eventlog_window = GetNewWindow(wEventLog, NULL, (WindowPtr)-1);
60     wi = smalloc(sizeof(*wi));
61     memset(wi, 0, sizeof(*wi));
62     wi->s = s;
63     wi->wtype = wEventLog;
64     wi->click = &mac_clickeventlog;
65     wi->activate = &mac_activateeventlog;
66     wi->grow = &mac_groweventlog;
67     wi->update = &mac_updateeventlog;
68     SetWRefCon(s->eventlog_window, (long)wi);
69     GetPort(&saveport);
70     SetPort((GrafPtr)GetWindowPort(s->eventlog_window));
71     fondsize = GetScriptVariable(smRoman, smScriptSmallFondSize);
72     TextFont(HiWord(fondsize));
73     TextSize(LoWord(fondsize));
74     SetPort(saveport);
75 #if TARGET_API_MAC_CARBON
76     GetPortBounds(GetWindowPort(s->eventlog_window), &view);
77 #else
78     view = s->eventlog_window->portRect;
79 #endif
80     view.right -= 15; /* Scrollbar */
81     s->eventlog = LNew(&view, &bounds, csize, 0, s->eventlog_window,
82                        TRUE, TRUE, FALSE, TRUE);
83     mac_adjusteventlogscrollbar(s);
84 #if TARGET_API_MAC_CARBON
85     SetListSelectionFlags(s->eventlog, lExtendDrag | lNoDisjoint | lNoExtend);
86 #else
87     (*s->eventlog)->selFlags = lExtendDrag | lNoDisjoint | lNoExtend;
88 #endif
89     ShowWindow(s->eventlog_window);
90 }
91
92 void mac_freeeventlog(Session *s)
93 {
94
95     if (s->eventlog != NULL)
96         LDispose(s->eventlog);
97     if (s->eventlog_window != NULL) {
98         sfree((WinInfo *)GetWRefCon(s->eventlog_window));
99         DisposeWindow(s->eventlog_window);
100     }
101 }
102
103 /*
104  * FIXME: logevent() should be passed a frontend handle, but backends have to
105  * have a terminal handle instead, because they pass it to from_backend(),
106  * so we accept a terminal handle here as well, and hope no-one tries to call
107  * us with sensible arguments.
108  */
109 void logevent(void *frontend, char *str)
110 {
111     Terminal *term = frontend;
112     Session *s = term->frontend;
113     ListBounds bounds, visible;
114     Cell cell = { 0, 0 };
115
116     if (s->eventlog == NULL)
117         mac_createeventlog(s);
118     if (s->eventlog == NULL)
119         return;
120
121 #if TARGET_API_MAC_CARBON
122     GetListDataBounds(s->eventlog, &bounds);
123     GetListVisibleCells(s->eventlog, &visible);
124 #else
125     bounds = (*s->eventlog)->dataBounds;
126     visible = (*s->eventlog)->visible;
127 #endif
128
129     cell.v = bounds.bottom;
130     LAddRow(1, cell.v, s->eventlog);
131     LSetCell(str, strlen(str), cell, s->eventlog);
132     /* ">=" and "2" because there can be a blank cell below the last one. */
133     if (visible.bottom >= bounds.bottom)
134         LScroll(0, 2, s->eventlog);
135 }
136
137 static void mac_draweventloggrowicon(Session *s)
138 {
139     Rect clip;
140     RgnHandle savergn;
141
142     SetPort((GrafPtr)GetWindowPort(s->eventlog_window));
143     /*
144      * Stop DrawGrowIcon giving us space for a horizontal scrollbar
145      * See Tech Note TB575 for details.
146      */
147 #if TARGET_API_MAC_CARBON
148     GetPortBounds(GetWindowPort(s->eventlog_window), &clip);
149 #else
150     clip = s->eventlog_window->portRect;
151 #endif
152     clip.left = clip.right - 15;
153     savergn = NewRgn();
154     GetClip(savergn);
155     ClipRect(&clip);
156     DrawGrowIcon(s->eventlog_window);
157     SetClip(savergn);
158     DisposeRgn(savergn);
159 }
160
161 /*
162  * For some reason, LNew doesn't seem to respect the hasGrow
163  * parameter, so we hammer the scrollbar into shape ourselves.
164  */
165 static void mac_adjusteventlogscrollbar(Session *s)
166 {
167 #if TARGET_API_MAC_CARBON
168     Rect winrect;
169
170     GetPortBounds(GetWindowPort(s->eventlog_window), &winrect);
171     SizeControl(GetListVerticalScrollBar(s->eventlog),
172                 16, winrect.bottom - 13);
173 #else
174     SizeControl((*s->eventlog)->vScroll,
175                 16, s->eventlog_window->portRect.bottom - 13);
176 #endif
177 }
178
179 void mac_clickeventlog(WindowPtr window, EventRecord *event)
180 {
181     Session *s = mac_windowsession(window);
182     Point mouse;
183     GrafPtr saveport;
184
185     GetPort(&saveport);
186     SetPort((GrafPtr)GetWindowPort(window));
187     mouse = event->where;
188     GlobalToLocal(&mouse);
189     LClick(mouse, event->modifiers, s->eventlog);
190     SetPort(saveport);
191 }
192
193 static void mac_groweventlog(WindowPtr window, EventRecord *event)
194 {
195     Session *s = mac_windowsession(window);
196     Rect limits;
197     long grow_result;
198 #if TARGET_API_MAC_CARBON
199     Rect rect;
200     Point cellsize;
201 #else
202     GrafPtr saveport;
203 #endif
204
205     SetRect(&limits, 15, 0, SHRT_MAX, SHRT_MAX);
206     grow_result = GrowWindow(window, event->where, &limits);
207     if (grow_result == 0) return;
208     SizeWindow(window, LoWord(grow_result), HiWord(grow_result), TRUE);
209     LSize(LoWord(grow_result) - 15, HiWord(grow_result), s->eventlog);
210     mac_adjusteventlogscrollbar(s);
211     /* We would use SetListCellSize in Carbon, but it's missing. */
212     (*s->eventlog)->cellSize.h = LoWord(grow_result) - 15;
213 #if TARGET_API_MAC_CARBON
214     cellsize.h = LoWord(grow_result) - 15;
215     GetListViewBounds(s->eventlog, &rect);
216     InvalWindowRect(window, &rect);
217 #else
218     GetPort(&saveport);
219     SetPort(window);
220     InvalRect(&(*s->eventlog)->rView);
221     SetPort(saveport);
222 #endif
223 }
224
225 static void mac_activateeventlog(WindowPtr window, EventRecord *event)
226 {
227     Session *s = mac_windowsession(window);
228     int active = (event->modifiers & activeFlag) != 0;
229
230     LActivate(active, s->eventlog);
231     mac_draweventloggrowicon(s);
232 }
233
234 static void mac_updateeventlog(WindowPtr window)
235 {
236     Session *s = mac_windowsession(window);
237 #if TARGET_API_MAC_CARBON
238     RgnHandle visrgn;
239 #endif
240
241     SetPort((GrafPtr)GetWindowPort(window));
242     BeginUpdate(window);
243 #if TARGET_API_MAC_CARBON
244     visrgn = NewRgn();
245     GetPortVisibleRegion(GetWindowPort(window), visrgn);
246     LUpdate(visrgn, s->eventlog);
247     DisposeRgn(visrgn);
248 #else
249     LUpdate(window->visRgn, s->eventlog);
250 #endif
251     mac_draweventloggrowicon(s);
252     EndUpdate(window);
253 }
254
255 void mac_showeventlog(Session *s)
256 {
257
258     ShowWindow(s->eventlog_window);
259 }
260
261 /*
262  * Local Variables:
263  * c-file-style: "simon"
264  * End:
265  */