Tabs to spaces, more consistent formatting.
[AROS.git] / workbench / libs / muimaster / classes / register.c
blob004caa46526b9f9700c1641e0c4d43d4774fad90
1 /*
2 Copyright © 2002-2011, The AROS Development Team. All rights reserved.
3 $Id$
4 */
6 #include <string.h>
7 #include <exec/memory.h>
8 #include <intuition/icclass.h>
9 #include <intuition/gadgetclass.h>
10 #include <intuition/imageclass.h>
11 #include <clib/alib_protos.h>
12 #include <proto/exec.h>
13 #include <proto/intuition.h>
14 #include <proto/utility.h>
15 #include <proto/graphics.h>
16 #include <proto/muimaster.h>
18 #include "mui.h"
19 #include "muimaster_intern.h"
20 #include "support.h"
21 #include "prefs.h"
22 #include "font.h"
24 /* #define MYDEBUG 1 */
25 #include "debug.h"
27 extern struct Library *MUIMasterBase;
29 #define INTERTAB 4
30 #define TEXTSPACING 4
31 #define REGISTERTAB_EXTRA_HEIGHT 7
32 #define REGISTER_FRAMEX 7
33 #define REGISTER_FRAMEBOTTOM 5
34 #define REGISTER_FRAMETOP 4
36 struct RegisterTabItem
38 STRPTR text; /* strlen(text) - valide between new/delete */
39 WORD textlen; /* strlen(text) - valide between setup/cleanup */
40 WORD x1, x2; /* tab x input sensitive interval, relative to
41 * object's origin - valid between show/hide */
42 WORD y1, y2; /* tab y input sensitive interval -
43 * valid between setup/cleanup */
46 struct Register_DATA
48 struct MUI_EventHandlerNode ehn;
49 struct RegisterTabItem *items;
50 char **labels;
51 BOOL frame;
52 WORD active;
53 WORD numitems;
54 WORD oldactive;
55 WORD left;
56 WORD top;
57 WORD min_width; /* object min width required */
58 WORD def_width; /* object def width required */
59 WORD tab_height; /* title height */
60 WORD framewidth;
61 WORD frameheight;
62 WORD fontw;
63 WORD fonth;
64 WORD fontb;
65 WORD total_hspacing;
66 WORD ty; /* text y origin - valid between setup/cleanup */
67 WORD columns; /* Number of register columns */
68 WORD rows; /* Number of register rows */
72 /**************************************************************************
73 Layout Tab Items
74 **************************************************************************/
75 static void LayoutTabItems(Object *obj, struct Register_DATA *data)
77 WORD extra_space;
78 WORD fitwidth;
79 WORD x = 0;
80 WORD y = -data->tab_height;
81 WORD item_width; /* from vertical line left to v l right */
82 int i;
83 int tabs_on_bottom = 0;
85 item_width = (_width(obj) - data->total_hspacing) / data->columns;
86 //data->numitems;
87 extra_space = (_width(obj) - data->total_hspacing) % data->columns;
88 //data->numitems;
90 D(bug("LayoutTabItems(%lx) : width = %d, mwidth = %d, "
91 "max item width = %d, remainder = %d\n",
92 obj, _width(obj), _mwidth(obj), item_width, extra_space));
94 for (i = 0; i < data->numitems; i++)
96 struct RegisterTabItem *ri = &data->items[i];
98 if (i % data->columns == 0)
100 x = INTERTAB - 1;
101 if (i > data->active && !tabs_on_bottom)
103 y = _height(obj) - muiAreaData(obj)->mad_InnerBottom;
104 tabs_on_bottom = 1;
106 else
107 y += data->tab_height;
110 ri->x1 = x;
111 ri->x2 = ri->x1 + item_width - 1;
112 if (extra_space > 0)
114 ri->x2++;
115 extra_space--;
117 fitwidth = ri->x2 - ri->x1 + 1 - TEXTSPACING;
118 x += fitwidth + TEXTSPACING + INTERTAB;
120 ri->y1 = y;
121 ri->y2 = y + data->tab_height - 1;
125 /**************************************************************************
126 Render one item
127 **************************************************************************/
128 static void RenderRegisterTabItem(struct IClass *cl, Object *obj,
129 WORD item)
131 struct Register_DATA *data = INST_DATA(cl, obj);
132 struct RegisterTabItem *ri = &data->items[item];
133 struct TextExtent extent;
134 WORD fitlen; /* text len fitting in alloted space */
135 WORD fitpix; /* text pixels fitting in alloted space */
136 WORD x, y;
137 WORD top_item_bar_y;
138 WORD bottom_item_bar_y;
139 WORD left_item_bar_x;
140 WORD right_item_bar_x;
141 WORD item_bar_width;
142 WORD text_y;
143 WORD item_bg_height;
144 WORD fitwidth;
146 if ((item < 0) || (item >= data->numitems))
147 return;
149 y = data->top + ri->y1;
151 if (data->active == item)
153 top_item_bar_y = _top(obj) + ri->y1;
154 bottom_item_bar_y = _top(obj) + ri->y2 - 2;
155 left_item_bar_x = _left(obj) + ri->x1 - 1;
156 right_item_bar_x = _left(obj) + ri->x2 + 1;
157 item_bg_height = data->tab_height;
158 text_y = y + data->ty;
159 item_bar_width = right_item_bar_x - left_item_bar_x + 1;
160 /* fill tab with register background */
161 DoMethod(obj, MUIM_DrawBackground, left_item_bar_x,
162 top_item_bar_y + 4, item_bar_width, item_bg_height - 4,
163 left_item_bar_x, top_item_bar_y + 4, 0);
164 DoMethod(obj, MUIM_DrawBackground, left_item_bar_x + 2,
165 top_item_bar_y + 2, item_bar_width - (2 * 2), 2,
166 left_item_bar_x + 2, top_item_bar_y + 2, 0);
167 DoMethod(obj, MUIM_DrawBackground, left_item_bar_x + 4,
168 top_item_bar_y + 1, item_bar_width - (2 * 4), 1,
169 left_item_bar_x + 4, top_item_bar_y + 1, 0);
171 else
173 top_item_bar_y = _top(obj) + ri->y1 + 2;
174 bottom_item_bar_y = _top(obj) + ri->y2 - 1;
175 left_item_bar_x = _left(obj) + ri->x1;
176 right_item_bar_x = _left(obj) + ri->x2;
177 item_bg_height = data->tab_height - 3;
178 text_y = y + data->ty + 1;
179 item_bar_width = right_item_bar_x - left_item_bar_x + 1;
180 SetAPen(_rp(obj), _pens(obj)[MPEN_BACKGROUND]);
181 RectFill(_rp(obj), left_item_bar_x, top_item_bar_y + 4,
182 right_item_bar_x, bottom_item_bar_y);
183 RectFill(_rp(obj), left_item_bar_x + 2, top_item_bar_y + 2,
184 right_item_bar_x - 2, top_item_bar_y + 3);
185 RectFill(_rp(obj), left_item_bar_x + 4, top_item_bar_y + 1,
186 right_item_bar_x - 4, top_item_bar_y + 1);
189 /* top horiz bar */
190 SetAPen(_rp(obj), _pens(obj)[MPEN_SHINE]);
191 RectFill(_rp(obj), left_item_bar_x + 4, top_item_bar_y,
192 right_item_bar_x - 4, top_item_bar_y);
193 /* left vert bar */
194 RectFill(_rp(obj), left_item_bar_x, top_item_bar_y + 4, left_item_bar_x,
195 bottom_item_bar_y);
196 WritePixel(_rp(obj), left_item_bar_x + 1, top_item_bar_y + 3);
197 WritePixel(_rp(obj), left_item_bar_x + 1, top_item_bar_y + 2);
198 WritePixel(_rp(obj), left_item_bar_x + 2, top_item_bar_y + 1);
199 WritePixel(_rp(obj), left_item_bar_x + 3, top_item_bar_y + 1);
200 SetAPen(_rp(obj), _pens(obj)[MPEN_HALFSHINE]);
201 WritePixel(_rp(obj), left_item_bar_x + 3, top_item_bar_y);
202 WritePixel(_rp(obj), left_item_bar_x + 4, top_item_bar_y + 1);
203 WritePixel(_rp(obj), left_item_bar_x + 2, top_item_bar_y + 2);
204 WritePixel(_rp(obj), left_item_bar_x + 3, top_item_bar_y + 2);
205 WritePixel(_rp(obj), left_item_bar_x + 2, top_item_bar_y + 3);
206 WritePixel(_rp(obj), left_item_bar_x, top_item_bar_y + 3);
207 WritePixel(_rp(obj), left_item_bar_x + 1, top_item_bar_y + 4);
209 if (data->active == item)
211 /* bottom horiz bar */
212 SetAPen(_rp(obj), _pens(obj)[MPEN_SHINE]);
213 WritePixel(_rp(obj), left_item_bar_x - 1, bottom_item_bar_y + 1);
214 SetAPen(_rp(obj), _pens(obj)[MPEN_SHADOW]);
215 WritePixel(_rp(obj), right_item_bar_x + 1, bottom_item_bar_y + 1);
216 DoMethod(obj, MUIM_DrawBackground, left_item_bar_x - 1,
217 bottom_item_bar_y + 2, item_bar_width + (2 * 1), 1,
218 left_item_bar_x - 1, bottom_item_bar_y + 2, 0);
221 /* right vert bar */
222 SetAPen(_rp(obj), _pens(obj)[MPEN_SHADOW]);
223 WritePixel(_rp(obj), right_item_bar_x - 1, top_item_bar_y + 2);
224 RectFill(_rp(obj), right_item_bar_x, top_item_bar_y + 4,
225 right_item_bar_x, bottom_item_bar_y);
226 SetAPen(_rp(obj), _pens(obj)[MPEN_HALFSHADOW]);
227 WritePixel(_rp(obj), right_item_bar_x - 2, top_item_bar_y + 1);
228 WritePixel(_rp(obj), right_item_bar_x - 1, top_item_bar_y + 3);
229 WritePixel(_rp(obj), right_item_bar_x, top_item_bar_y + 3);
230 SetAPen(_rp(obj), _pens(obj)[MPEN_BACKGROUND]);
231 WritePixel(_rp(obj), right_item_bar_x - 3, top_item_bar_y + 1);
233 /* text */
234 fitwidth = item_bar_width - TEXTSPACING;
235 fitlen =
236 TextFit(_rp(obj), ri->text, ri->textlen, &extent, NULL, 1, fitwidth,
237 data->tab_height);
238 fitpix = extent.te_Width;
239 // D(bug("extent for %s (len=%d) in %d pix = %d chars, %d pix [%x,%x,%x]\n",
240 // ri->text, ri->textlen, fitwidth, fitlen, fitpix, _rp(obj),
241 // _rp(obj)->Font, _font(obj)));
242 x = left_item_bar_x + (item_bar_width - fitpix) / 2;
243 SetDrMd(_rp(obj), JAM1);
244 SetAPen(_rp(obj), _pens(obj)[MPEN_TEXT]);
245 Move(_rp(obj), x, text_y);
246 Text(_rp(obj), ri->text, fitlen);
249 /**************************************************************************
250 Render tab bar
251 **************************************************************************/
252 static void RenderRegisterTab(struct IClass *cl, Object *obj, ULONG flags)
254 struct Register_DATA *data = INST_DATA(cl, obj);
257 * Erase / prepare for drawing
259 if (flags & MADF_DRAWOBJECT)
261 DoMethod(obj, MUIM_DrawParentBackground, data->left, data->top,
262 data->framewidth, data->tab_height - 1, data->left, data->top,
265 else
267 /* draw parent bg over oldactive */
268 IPTR method;
269 WORD old_left, old_top, old_width, old_height;
270 struct RegisterTabItem *ri = &data->items[data->oldactive];
271 if (data->oldactive >= data->columns)
272 method = MUIM_DrawBackground;
273 else
274 method = MUIM_DrawParentBackground;
276 old_left = _left(obj) + ri->x1 - 2;
277 old_top = _top(obj) + ri->y1;
278 old_width = ri->x2 - ri->x1 + 5;
279 old_height = data->tab_height - 1;
280 DoMethod(obj, method, old_left, old_top,
281 old_width, old_height, old_left, old_top, 0);
282 SetDrMd(_rp(obj), JAM1);
283 SetAPen(_rp(obj), _pens(obj)[MPEN_SHINE]);
284 RectFill(_rp(obj), old_left, old_top + old_height,
285 old_left + old_width, old_top + old_height);
288 SetDrMd(_rp(obj), JAM1);
289 SetAPen(_rp(obj), _pens(obj)[MPEN_SHINE]);
290 SetFont(_rp(obj), _font(obj));
291 SetSoftStyle(_rp(obj), FS_NORMAL, AskSoftStyle(_rp(obj)));
295 * Draw new graphics
297 /* register frame */
298 if (flags & MADF_DRAWOBJECT
299 || (data->active / data->columns !=
300 data->oldactive / data->columns))
302 int i, y, tabs_on_bottom = 0;
304 SetAPen(_rp(obj), _pens(obj)[MPEN_SHINE]);
306 RectFill(_rp(obj), data->left,
307 data->top + data->tab_height - 1,
308 data->left,
309 data->top + data->tab_height + data->frameheight - 1);
311 y = data->top + data->tab_height - 1;
313 for (i = 0; i < data->rows; i++)
315 if (!tabs_on_bottom && (i > data->active / data->columns))
317 y = _bottom(obj) - muiAreaData(obj)->mad_InnerBottom +
318 data->tab_height;
319 tabs_on_bottom = 1;
322 RectFill(_rp(obj), data->left + 1, y,
323 data->left + data->framewidth - 2, y);
324 y += data->tab_height;
327 SetAPen(_rp(obj), _pens(obj)[MPEN_SHADOW]);
329 RectFill(_rp(obj), data->left + data->framewidth - 1,
330 data->top + data->tab_height - 1,
331 data->left + data->framewidth - 1,
332 data->top + data->tab_height + data->frameheight - 1);
334 RectFill(_rp(obj), data->left + 1,
335 data->top + data->tab_height + data->frameheight - 1,
336 data->left + data->framewidth - 2,
337 data->top + data->tab_height + data->frameheight - 1);
338 for (i = 0; i < data->numitems; i++)
340 RenderRegisterTabItem(cl, obj, i);
343 else
345 /* If active register has been changed and is on same row we simply draw both registers only */
346 RenderRegisterTabItem(cl, obj, data->active);
347 RenderRegisterTabItem(cl, obj, data->oldactive);
352 /**************************************************************************
353 Set the coordinates
354 **************************************************************************/
355 static void SetHardCoord(Object *obj, struct Register_DATA *data)
357 struct MUI_AreaData *adata = muiAreaData(obj);
358 const struct MUI_FrameSpec_intern *frame;
360 //adata->mad_InnerLeft = REGISTER_FRAMEX;
361 //adata->mad_InnerTop = data->tab_height
362 // * (1 + data->active/data->columns) + REGISTER_FRAMETOP;
363 //adata->mad_InnerRight = REGISTER_FRAMEX;
364 //adata->mad_InnerBottom = data->tab_height
365 // * (data->rows - 1 - data->active/data->columns)
366 // + REGISTER_FRAMEBOTTOM;
368 frame = &muiGlobalInfo(obj)->mgi_Prefs->frames[MUIV_Frame_Group];
370 adata->mad_InnerLeft = frame->innerLeft + 1;
371 adata->mad_InnerTop =
372 data->tab_height * (1 + data->active / data->columns) +
373 frame->innerTop;
374 adata->mad_InnerRight = frame->innerRight + 1;
375 adata->mad_InnerBottom =
376 data->tab_height * (data->rows - 1 - data->active / data->columns)
377 + frame->innerBottom + 1;
378 /* D(bug("Hardcoord %p top=%ld bottom=%ld\n",
379 obj, adata->mad_HardITop, adata->mad_HardIBottom)); */
382 IPTR Register__OM_NEW(struct IClass *cl, Object *obj, struct opSet *msg)
384 struct Register_DATA *data;
385 int i;
386 IPTR tmp = 0;
388 obj =
389 (Object *) DoSuperNewTags(cl, obj, NULL, MUIA_Group_PageMode, TRUE,
390 MUIA_Background, MUII_RegisterBack, TAG_MORE,
391 (IPTR) msg->ops_AttrList);
392 if (!obj)
393 return (IPTR) NULL;
395 data = INST_DATA(cl, obj);
397 data->frame = GetTagData(MUIA_Register_Frame, 0, msg->ops_AttrList);
399 data->labels =
400 (char **)GetTagData(MUIA_Register_Titles, 0, msg->ops_AttrList);
402 if (!data->labels)
404 CoerceMethod(cl, obj, OM_DISPOSE);
405 return (IPTR) NULL;
408 for (data->numitems = 0; data->labels[data->numitems]; data->numitems++)
411 if (data->numitems <= 0)
413 CoerceMethod(cl, obj, OM_DISPOSE);
414 return (IPTR) NULL;
417 data->columns =
418 (WORD) GetTagData(MUIA_Register_Columns, data->numitems,
419 msg->ops_AttrList);
420 if (data->columns <= 0)
421 data->columns = 1;
422 data->rows = (data->numitems + data->columns - 1) / data->columns;
424 get(obj, MUIA_Group_ActivePage, &tmp);
425 data->active = (WORD) tmp;
427 if (data->active < 0 || data->active >= data->numitems)
429 data->active = 0;
431 data->oldactive = data->active;
433 data->items =
434 (struct RegisterTabItem *)AllocVec(data->numitems *
435 sizeof(struct RegisterTabItem), MEMF_PUBLIC | MEMF_CLEAR);
437 if (!data->items)
439 CoerceMethod(cl, obj, OM_DISPOSE);
440 return (IPTR) NULL;
443 for (i = 0; i < data->numitems; i++)
445 data->items[i].text = data->labels[i];
448 data->ehn.ehn_Events = IDCMP_MOUSEBUTTONS | IDCMP_RAWKEY;
449 data->ehn.ehn_Priority = 0;
450 data->ehn.ehn_Flags = 0;
451 data->ehn.ehn_Object = obj;
452 data->ehn.ehn_Class = cl;
454 return (IPTR) obj;
458 IPTR Register__OM_GET(struct IClass *cl, Object *obj, struct opGet *msg)
460 struct Register_DATA *data = INST_DATA(cl, obj);
462 #define STORE *(msg->opg_Storage)
464 switch (msg->opg_AttrID)
466 case MUIA_Register_Frame:
467 STORE = (IPTR) data->frame;
468 return 1;
470 case MUIA_Register_Titles:
471 STORE = (IPTR) data->labels;
472 return 1;
475 return DoSuperMethodA(cl, obj, (Msg) msg);
479 IPTR Register__OM_DISPOSE(struct IClass *cl, Object *obj, Msg msg)
481 struct Register_DATA *data = INST_DATA(cl, obj);
483 if (data->items)
484 FreeVec(data->items);
486 return DoSuperMethodA(cl, obj, msg);
489 IPTR Register__MUIM_Setup(struct IClass *cl, Object *obj,
490 struct MUIP_Setup *msg)
492 struct Register_DATA *data = INST_DATA(cl, obj);
493 WORD i, h = 0;
495 if (!DoSuperMethodA(cl, obj, (Msg) msg))
497 return FALSE;
500 _font(obj) = zune_font_get(obj, MUIV_Font_Title);
501 data->fonth = _font(obj)->tf_YSize;
502 data->fontb = _font(obj)->tf_Baseline;
504 h = 0;
506 i = data->fonth + REGISTERTAB_EXTRA_HEIGHT;
507 h = (i > h) ? i : h;
509 data->tab_height = h;
510 data->ty = data->fontb + 1 + (data->tab_height - data->fonth) / 2;
512 /* D(bug("Register_Setup : data->height=%d\n", data->tab_height)); */
514 for (i = 0; i < data->numitems; i++)
516 data->items[i].textlen = strlen(data->items[i].text);
519 data->total_hspacing = (data->columns + 1) * INTERTAB - 2;
520 /* D(bug("Register_AskMinMax : data->total_hspacing = %d\n",
521 data->total_hspacing)); */
523 data->min_width = data->total_hspacing * 3;
524 data->def_width = data->total_hspacing;
526 if (!(muiGlobalInfo(obj)->mgi_Prefs->register_truncate_titles))
528 struct RastPort temprp;
529 int i;
530 WORD textpixmax;
532 InitRastPort(&temprp);
533 SetFont(&temprp, _font(obj));
535 textpixmax = 0;
536 for (i = 0; i < data->numitems; i++)
538 WORD textpix =
539 TextLength(&temprp, data->items[i].text,
540 data->items[i].textlen);
541 textpixmax = MAX(textpix, textpixmax);
543 data->def_width += (textpixmax + TEXTSPACING + 1) * data->numitems;
544 data->def_width = MAX(data->min_width, data->def_width);
547 SetHardCoord(obj, data);
548 muiAreaData(obj)->mad_Flags |=
549 (MADF_INNERLEFT | MADF_INNERTOP | MADF_INNERRIGHT |
550 MADF_INNERBOTTOM);
552 DoMethod(_win(obj), MUIM_Window_AddEventHandler, (IPTR) & data->ehn);
554 return TRUE;
557 IPTR Register__MUIM_Cleanup(struct IClass *cl, Object *obj,
558 struct MUIP_Cleanup *msg)
560 struct Register_DATA *data = INST_DATA(cl, obj);
562 DoMethod(_win(obj), MUIM_Window_RemEventHandler, (IPTR) & data->ehn);
564 return DoSuperMethodA(cl, obj, (Msg) msg);
567 IPTR Register__MUIM_AskMinMax(struct IClass *cl, Object *obj,
568 struct MUIP_AskMinMax *msg)
570 struct Register_DATA *data = INST_DATA(cl, obj);
572 DoSuperMethodA(cl, obj, (Msg) msg);
573 /* D(bug("Register_AskMinMax1 : %ld, %ld, %ld\n", */
574 /* msg->MinMaxInfo->MinWidth, msg->MinMaxInfo->DefWidth, */
575 /* msg->MinMaxInfo->MaxWidth)); */
578 /* D(bug("Register_AskMinMax : spacings = %d, minw=%d, defw=%d, " */
579 /* "mymin=%d, mydef=%d\n", */
580 /* data->total_hspacing, msg->MinMaxInfo->MinWidth, */
581 /* msg->MinMaxInfo->DefWidth, */
582 /* data->min_width, data->def_width)); */
584 msg->MinMaxInfo->MinWidth =
585 MAX(msg->MinMaxInfo->MinWidth, data->min_width);
586 msg->MinMaxInfo->MaxWidth =
587 MAX(msg->MinMaxInfo->MaxWidth, data->def_width);
588 msg->MinMaxInfo->DefWidth =
589 MAX(msg->MinMaxInfo->DefWidth, data->def_width);
591 /* msg->MinMaxInfo->MinHeight += data->tab_height; */
592 /* msg->MinMaxInfo->DefHeight += data->tab_height; */
593 msg->MinMaxInfo->MaxHeight = MUI_MAXMAX;
595 /* D(bug("Register_AskMinMax %p : tabheight=%d, minh=%d\n", obj, */
596 /* data->tab_height, */
597 /* msg->MinMaxInfo->MinHeight)); */
599 /* D(bug("Register_AskMinMax2 : %ld, %ld, %ld\n", */
600 /* msg->MinMaxInfo->MinWidth, msg->MinMaxInfo->DefWidth, */
601 /* msg->MinMaxInfo->MaxWidth)); */
602 return TRUE;
605 IPTR Register__MUIM_Layout(struct IClass *cl, Object *obj,
606 struct MUIP_Layout *msg)
608 struct Register_DATA *data = INST_DATA(cl, obj);
609 ULONG retval = 1;
610 IPTR active = 0;
612 get(obj, MUIA_Group_ActivePage, &active);
614 if (active != data->active)
616 data->oldactive = data->active;
617 data->active = active;
619 SetHardCoord(obj, data);
620 DoMethod(obj, MUIM_UpdateInnerSizes);
622 DoSuperMethodA(cl, obj, (Msg) msg);
624 data->left = _left(obj);
625 data->top = _top(obj);
626 data->framewidth = _width(obj);
627 data->frameheight = _height(obj) - data->tab_height;
629 LayoutTabItems(obj, data);
631 /* D(bug( */
632 /* "Register_Layout : left=%d, top=%d / framewidth=%d, frameheight=%d\n", */
633 /* data->left, data->top, data->framewidth, data->frameheight)); */
635 return retval;
638 IPTR Register__MUIM_Show(struct IClass *cl, Object *obj,
639 struct MUIP_Show *msg)
641 /* struct Register_DATA *data = INST_DATA(cl, obj);*/
643 DoSuperMethodA(cl, obj, (Msg) msg);
645 /* D(bug("Register_Show : left = %d, _left = %d, mleft = %d, \n", */
646 /* data->left, _left(obj), _mleft(obj))) */
648 return TRUE;
651 IPTR Register__MUIM_Draw(struct IClass *cl, Object *obj,
652 struct MUIP_Draw *msg)
654 struct Register_DATA *data = INST_DATA(cl, obj);
656 /* Before all the current page is drawn erase the part of the area covered
657 * by tabs which is not erased (between _left(obj) and _mleft(obj) and
658 * so on */
659 if (data->oldactive != data->active && (msg->flags & MADF_DRAWUPDATE)
660 && (data->active / data->columns !=
661 data->oldactive / data->columns))
663 int left, top, width, height;
665 left = _mright(obj) + 1;
666 top = _mtop(obj);
667 width = _right(obj) - left; /* +1 - 1 */
668 height = _mheight(obj);
670 DoMethod(obj, MUIM_DrawBackground, left, top, width, height, left,
671 top, 0);
673 left = _left(obj) + 1;
674 /* +1 because the register frame shouldn't be ereased */
675 width = _mleft(obj) - left; /* + 1 - 1 */
677 DoMethod(obj, MUIM_DrawBackground, left, top, width, height, left,
678 top, 0);
680 top = _top(obj) + data->tab_height;
681 height = _mtop(obj) - top; /* + 1 - 1 */
682 width = _width(obj) - 2;
684 if (height > 0 && width > 0)
685 DoMethod(obj, MUIM_DrawBackground, left, top, width, height,
686 left, top, 0);
688 top = _mbottom(obj);
689 height = _bottom(obj) - top; /* + 1 - 1 */
691 if (height > 0 && width > 0)
692 DoMethod(obj, MUIM_DrawBackground, left, top, width, height,
693 left, top, 0);
696 DoSuperMethodA(cl, obj, (Msg) msg);
698 /* D(bug("Register_Draw : flags = %d\n", msg->flags)); */
699 if (!(msg->flags & (MADF_DRAWOBJECT | MADF_DRAWUPDATE)))
700 return (0);
702 RenderRegisterTab(cl, obj, msg->flags);
704 data->oldactive = data->active;
705 return TRUE;
708 IPTR Register__MUIM_HandleEvent(struct IClass *cl, Object *obj,
709 struct MUIP_HandleEvent *msg)
711 struct Register_DATA *data = INST_DATA(cl, obj);
712 WORD i, x, y;
714 if (msg->muikey != MUIKEY_NONE)
716 switch (msg->muikey)
718 case MUIKEY_PRESS:
719 case MUIKEY_RIGHT:
720 case MUIKEY_TOGGLE:
721 nfset(obj, MUIA_Group_ActivePage, MUIV_Group_ActivePage_Next);
722 return MUI_EventHandlerRC_Eat;
724 case MUIKEY_LEFT:
725 nfset(obj, MUIA_Group_ActivePage, MUIV_Group_ActivePage_Prev);
726 return MUI_EventHandlerRC_Eat;
728 case MUIKEY_WORDLEFT:
729 case MUIKEY_LINESTART:
730 nfset(obj, MUIA_Group_ActivePage, MUIV_Group_ActivePage_First);
731 return MUI_EventHandlerRC_Eat;
733 case MUIKEY_WORDRIGHT:
734 case MUIKEY_LINEEND:
735 nfset(obj, MUIA_Group_ActivePage, MUIV_Group_ActivePage_Last);
736 return MUI_EventHandlerRC_Eat;
741 if (msg->imsg)
743 if ((msg->imsg->Class == IDCMP_MOUSEBUTTONS) &&
744 (msg->imsg->Code == SELECTDOWN))
746 x = msg->imsg->MouseX - data->left;
747 y = msg->imsg->MouseY - data->top;
749 /* D(bug("Register_HandleEvent : %d,%d,%d -- %d,%d,%d\n", */
750 /* 0, x, _width(obj), 0, y, data->tab_height)); */
751 if (_between(0, x, _width(obj)))
753 /* D(bug("Register_HandleEvent : in tab, %d,%d\n", x, y)); */
754 for (i = 0; i < data->numitems; i++)
756 if (_between(data->items[i].x1, x, data->items[i].x2) &&
757 _between(data->items[i].y1, y, data->items[i].y2))
759 if (data->active != i)
761 nfset(obj, MUIA_Group_ActivePage, i);
762 return MUI_EventHandlerRC_Eat;
764 break;
771 return 0;
775 BOOPSI_DISPATCHER(IPTR, Register_Dispatcher, cl, obj, msg)
777 switch (msg->MethodID)
779 case OM_NEW:
780 return Register__OM_NEW(cl, obj, (struct opSet *)msg);
781 case OM_GET:
782 return Register__OM_GET(cl, obj, (struct opGet *)msg);
783 case OM_DISPOSE:
784 return Register__OM_DISPOSE(cl, obj, msg);
785 case MUIM_Setup:
786 return Register__MUIM_Setup(cl, obj, (struct MUIP_Setup *)msg);
787 case MUIM_Cleanup:
788 return Register__MUIM_Cleanup(cl, obj, (struct MUIP_Cleanup *)msg);
789 case MUIM_AskMinMax:
790 return Register__MUIM_AskMinMax(cl, obj,
791 (struct MUIP_AskMinMax *)msg);
792 case MUIM_Layout:
793 return Register__MUIM_Layout(cl, obj, (struct MUIP_Layout *)msg);
794 case MUIM_Show:
795 return Register__MUIM_Show(cl, obj, (struct MUIP_Show *)msg);
796 case MUIM_Draw:
797 return Register__MUIM_Draw(cl, obj, (struct MUIP_Draw *)msg);
798 case MUIM_HandleEvent:
799 return Register__MUIM_HandleEvent(cl, obj,
800 (struct MUIP_HandleEvent *)msg);
801 default:
802 return DoSuperMethodA(cl, obj, msg);
805 BOOPSI_DISPATCHER_END
807 const struct __MUIBuiltinClass _MUI_Register_desc =
809 MUIC_Register,
810 MUIC_Group,
811 sizeof(struct Register_DATA),
812 (void *) Register_Dispatcher