grub2: bring back build of aros-side grub2 tools
[AROS.git] / workbench / libs / gadtools / paletteclass.c
blob65a7b59ad15c1d327ec734c7989da1d8f8f9d7f8
1 /*
2 Copyright © 1995-2005, The AROS Development Team. All rights reserved.
3 $Id$
5 Desc: Internal GadTools palette class.
6 Lang: English
7 */
10 #include <proto/exec.h>
11 #include <exec/libraries.h>
12 #include <exec/memory.h>
13 #include <proto/dos.h>
14 #include <intuition/classes.h>
15 #include <intuition/classusr.h>
16 #include <intuition/gadgetclass.h>
17 #include <intuition/imageclass.h>
18 #include <intuition/intuition.h>
19 #include <intuition/cghooks.h>
20 #include <graphics/rastport.h>
21 #include <graphics/text.h>
22 #include <utility/tagitem.h>
23 #include <devices/inputevent.h>
24 #include <proto/alib.h>
25 #include <proto/utility.h>
27 #include <string.h> /* memset() */
28 #include <stdlib.h>
30 #define SDEBUG 0
31 #define DEBUG 0
32 #include <aros/debug.h>
34 #include "gadtools_intern.h"
36 /**********************************************************************************************/
38 #define HSPACING 2
39 #define VSPACING 2
41 #define HBORDER HSPACING
42 #define VBORDER VSPACING
45 #define HSELBORDER 1
46 #define VSELBORDER 1
48 #define GadToolsBase ((struct GadToolsBase_intern *)cl->cl_UserData)
50 /**********************************************************************************************/
52 STATIC VOID RenderFrame(struct PaletteData *data, struct RastPort *rp, struct IBox *gadbox,
53 struct DrawInfo *dri, BOOL recessed, BOOL edgesonly, Class *cl);
55 /**********************************************************************************************/
57 STATIC VOID GetGadgetIBox(struct Gadget *g, struct GadgetInfo *gi, struct IBox *ibox)
59 ibox->Left = g->LeftEdge;
60 ibox->Top = g->TopEdge;
61 ibox->Width = g->Width;
62 ibox->Height = g->Height;
64 if (gi)
66 if (g->Flags & GFLG_RELRIGHT)
67 ibox->Left += gi->gi_Domain.Width - 1;
69 if (g->Flags & GFLG_RELBOTTOM)
70 ibox->Top += gi->gi_Domain.Height - 1;
72 if (g->Flags & GFLG_RELWIDTH)
73 ibox->Width += gi->gi_Domain.Width;
75 if (g->Flags & GFLG_RELHEIGHT)
76 ibox->Height += gi->gi_Domain.Height;
80 /**********************************************************************************************/
82 STATIC UWORD GetPalettePen(struct PaletteData *data, UWORD idx)
84 UWORD pen;
86 if (data->pd_ColorTable)
87 pen = data->pd_ColorTable[idx];
88 else
89 pen = idx + data->pd_ColorOffset;
91 return (pen);
94 /**********************************************************************************************/
96 STATIC BOOL InsidePalette(struct PaletteData *data, WORD x, WORD y)
98 (void)data;
99 (void)x;
100 (void)y;
102 return TRUE;
105 /**********************************************************************************************/
107 STATIC UWORD ComputeColor(struct PaletteData *data, WORD x, WORD y)
109 UWORD row, col;
111 WORD color;
113 col = (x - data->pd_PaletteBox.Left) / data->pd_ColWidth;
114 row = (y - data->pd_PaletteBox.Top) / data->pd_RowHeight;
116 color = data->pd_NumCols *row + col;
118 if (color < 0)
120 color = 0;
122 else if (color >= data->pd_NumColors)
124 color = data->pd_NumColors - 1;
127 return (UWORD)color;
130 /**********************************************************************************************/
132 #define MIN(a, b) (( a < b) ? a : b)
134 STATIC VOID RenderPalette(struct PaletteData *data, struct RastPort *rp, Class *cl)
136 UWORD currentcolor = data->pd_ColorOffset, colors_left;
137 WORD left, top;
138 register UWORD col, row;
139 struct IBox *pbox = &(data->pd_PaletteBox);
141 EnterFunc(bug("RenderPalette(data=%p, rp=%p)\n", data, rp));
143 top = pbox->Top;
145 colors_left = data->pd_NumColors;
146 SetDrMd(rp, JAM1);
148 for (row = data->pd_NumRows; row; row --)
150 left = pbox->Left;
151 for (col = MIN(data->pd_NumCols, colors_left); col; col --)
154 SetAPen(rp, GetPalettePen(data, currentcolor));
156 RectFill( rp, left, top,
157 left + data->pd_ColWidth - VSPACING - 1,
158 top + data->pd_RowHeight - HSPACING - 1 );
160 D(bug( "Rectfilling area (%d, %d, %d, %d)\n with color %d", left, top,
161 left + data->pd_ColWidth - VSPACING - 1, top + data->pd_RowHeight - HSPACING,
162 currentcolor));
164 currentcolor ++;
166 left += data->pd_ColWidth;
168 } /* for (each row) */
169 top += data->pd_RowHeight;
171 colors_left -= data->pd_NumCols;
173 } /* for (each column) */
175 ReturnVoid("RenderPalette");
178 /**********************************************************************************************/
180 VOID UpdateActiveColor( struct PaletteData *data,
181 struct DrawInfo *dri,
182 struct RastPort *rp,
183 Class *cl)
185 struct IBox framebox;
186 WORD left, top, right, bottom;
188 EnterFunc(bug("UpdateActiveColor(data=%p, dri=%p, rp=%p)\n",
189 data, dri, rp));
191 SetAPen(rp, dri->dri_Pens[BACKGROUNDPEN]);
192 SetDrMd(rp, JAM1);
194 if (data->pd_OldColor != data->pd_Color)
197 left = data->pd_PaletteBox.Left + (data->pd_OldColor % data->pd_NumCols) *data->pd_ColWidth;
198 top = data->pd_PaletteBox.Top + (data->pd_OldColor / data->pd_NumCols) *data->pd_RowHeight;
200 D(bug( "clearing old selected: (%d, %d, %d, %d) oldcolor=%d\n",
201 left, top, left + data->pd_ColWidth, top + data->pd_RowHeight, data->pd_OldColor));
203 /* Clear area with BACKGROUNDPEN */
204 RectFill( rp,
205 left - VBORDER,
206 top - HBORDER,
207 left + data->pd_ColWidth - 1,
208 top + data->pd_RowHeight - 1);
210 /* Rerender in original color */
211 SetAPen(rp, GetPalettePen(data, data->pd_OldColor + data->pd_ColorOffset));
213 RectFill( rp, left, top,
214 left + data->pd_ColWidth - VSPACING - 1,
215 top + data->pd_RowHeight - HSPACING - 1);
219 left = data->pd_PaletteBox.Left + (data->pd_Color % data->pd_NumCols) *data->pd_ColWidth;
220 top = data->pd_PaletteBox.Top + (data->pd_Color / data->pd_NumCols) *data->pd_RowHeight;
222 /* Right & bottom of *colored* area */
223 right = left + data->pd_ColWidth - VSPACING - 1;
224 bottom = top + data->pd_RowHeight - HSPACING - 1;
226 /* Render new active entry */
227 D(bug( "rendering new selected: (%d, %d, %d, %d), color=%d\n",
228 left, top, right, bottom, data->pd_Color));
231 if ((right - left >= 6) && (bottom - top >= 6))
233 /* Draw some borders */
235 SetAPen(rp, dri->dri_Pens[BACKGROUNDPEN]);
237 /* We draw left & right from top to bottom, but draw top & bottom
238 ** so they don't overlap with what's allready drawn
241 /* left */
242 RectFill( rp, left, top,
243 left + 1, bottom);
245 /* right */
246 RectFill( rp, right - 1, top,
247 right, bottom);
249 /* top */
250 RectFill( rp, left + 2, top,
251 right - 2, top + 1);
253 /* bottom */
254 RectFill( rp, left + 2, bottom - 1,
255 right - 2, bottom);
258 /* Draw recessed frame around selected color */
259 framebox.Left = left - VBORDER;
260 framebox.Top = top - HBORDER;
261 framebox.Width = data->pd_ColWidth + VBORDER;
262 framebox.Height = data->pd_RowHeight + HBORDER;
264 RenderFrame(data, rp, &framebox, dri, TRUE, TRUE, cl);
266 /* The newly update color becomes the new OldColor */
267 data->pd_OldColor = data->pd_Color;
269 ReturnVoid("UpdateActiveColor");
272 /**********************************************************************************************/
274 STATIC VOID RenderFrame(struct PaletteData *data, struct RastPort *rp, struct IBox *gadbox,
275 struct DrawInfo *dri, BOOL recessed, BOOL edgesonly, Class *cl)
277 WORD left, top;
279 EnterFunc(bug( "RenderFrame(rp=%p, gadbox=%p, dri=%p)\n",
280 rp, gadbox, dri));
282 left = gadbox->Left; top = gadbox->Top;
284 if (!data->pd_Frame)
286 struct TagItem frame_tags[] =
288 {IA_Resolution , (dri->dri_Resolution.X << 16) + dri->dri_Resolution.Y},
289 {IA_FrameType , FRAME_BUTTON},
290 {IA_EdgesOnly , edgesonly},
291 {TAG_DONE}
294 data->pd_Frame = NewObjectA(NULL, FRAMEICLASS, frame_tags);
297 if (data->pd_Frame)
299 struct TagItem frameset_tags[] =
301 {IA_Width , gadbox->Width},
302 {IA_Height , gadbox->Height},
303 {IA_Recessed , recessed},
304 {IA_EdgesOnly , edgesonly},
305 {TAG_DONE}
308 SetAttrsA(data->pd_Frame, frameset_tags);
310 DrawImageState(rp,
311 (struct Image *)data->pd_Frame,
312 left,
313 top,
314 IDS_NORMAL,
315 dri);
319 ReturnVoid("RenderFrame");
322 /**********************************************************************************************/
324 STATIC IPTR palette_set(Class *cl, Object *o, struct opSet *msg)
326 struct TagItem *tag, *tstate = msg->ops_AttrList;
327 struct PaletteData *data = INST_DATA(cl, o);
328 BOOL labelplace_set = FALSE, relayout = FALSE;
329 BOOL colortag_found = FALSE, numcolorstag_found = FALSE;
330 IPTR retval = 0UL;
333 EnterFunc(bug("Palette::Set()\n"));
335 while ((tag = NextTagItem(&tstate)))
337 IPTR tidata = tag->ti_Data;
340 switch (tag->ti_Tag)
342 case GTPA_Depth: /* [ISU] */
343 /* NumColors tag overrides Depth tag! */
344 if (!numcolorstag_found)
346 data->pd_NumColors = (1 << ((UBYTE)tidata));
348 D(bug("Depth initialized to %d\n", tidata));
349 relayout = TRUE;
350 retval = 1UL;
352 break;
354 case GTPA_Color: /* [IS] */
355 colortag_found = TRUE;
357 data->pd_OldColor = data->pd_Color;
358 data->pd_Color = (UBYTE)tidata;
359 D(bug("Color set to %d\n", tidata));
360 retval = 1UL;
361 break;
363 case GTPA_ColorOffset: /* [I] */
364 data->pd_ColorOffset = (UBYTE)tidata;
365 D(bug("ColorOffset initialized to %d\n", tidata));
366 retval = 1UL;
367 break;
369 case GTPA_IndicatorWidth: /* [I] */
370 data->pd_IndWidth = (UWORD)tidata;
371 D(bug("Indicatorwidth set to %d\n", tidata));
373 /* If palette has an indictor on left, GA_LabelPlace
374 ** defaults to GV_LabelPlace_Left
376 if (!labelplace_set)
377 data->pd_LabelPlace = GV_LabelPlace_Left;
378 break;
380 case GTPA_IndicatorHeight: /* [I] */
381 data->pd_IndHeight = (UWORD)tidata;
382 D(bug("Indicatorheight set to %d\n", tidata));
383 break;
385 case GA_LabelPlace: /* [I] */
386 data->pd_LabelPlace = (LONG)tidata;
387 D(bug("Labelplace set to %d\n", tidata));
389 labelplace_set = TRUE;
390 break;
392 case GA_TextAttr: /* [I] */
393 data->pd_TAttr = (struct TextAttr *)tidata;
394 D(bug("TextAttr set to %s %d\n",
395 data->pd_TAttr->ta_Name, data->pd_TAttr->ta_YSize));
396 break;
398 case GTPA_ColorTable:
399 data->pd_ColorTable = (UBYTE *)tidata;
400 break;
402 case GTPA_NumColors:
403 numcolorstag_found = TRUE;
405 data->pd_NumColors = (UWORD)tidata;
406 relayout = TRUE;
407 break;
409 } /* switch (tag->ti_Tag) */
411 } /* for (each attr in attrlist) */
413 if (colortag_found)
415 /* convert pen number to index */
417 if (data->pd_ColorTable)
419 WORD i;
421 /* convert pen number to index number */
422 for(i = 0; i < data->pd_NumColors; i++)
424 if (data->pd_ColorTable[i] == data->pd_Color)
426 data->pd_Color = i;
427 break;
432 else
434 data->pd_Color -= data->pd_ColorOffset;
436 } /* if (colortag_found) */
438 if (relayout)
440 /* Check if the old selected fits into the new depth */
441 if (data->pd_Color > data->pd_NumColors - 1)
443 data->pd_Color = 0;
444 data->pd_OldColor = 0; /* So that UpdateActiveColor() don't get confused */
447 /* Relayout the gadget */
448 DoMethod(o, GM_LAYOUT, (IPTR) msg->ops_GInfo, FALSE);
451 ReturnPtr ("Palette::Set", IPTR, retval);
454 /**********************************************************************************************/
456 IPTR GTPalette__OM_GET(Class *cl, Object *o, struct opGet *msg)
458 struct PaletteData *data = INST_DATA(cl, o);
459 IPTR retval = 0;
461 switch (msg->opg_AttrID)
463 case GTA_GadgetKind:
464 case GTA_ChildGadgetKind:
465 *(msg->opg_Storage) = PALETTE_KIND;
466 retval = 1UL;
467 break;
469 case GTPA_Color:
470 *msg->opg_Storage = (IPTR)GetPalettePen(data, data->pd_Color);
471 break;
473 case GTPA_ColorOffset:
474 *msg->opg_Storage = (IPTR)data->pd_ColorOffset;
475 break;
477 case GTPA_ColorTable:
478 *msg->opg_Storage = (IPTR)data->pd_ColorTable;
479 break;
481 default:
482 retval = DoSuperMethodA(cl, o, (Msg)msg);
483 break;
486 return retval;
489 /**********************************************************************************************/
491 IPTR GTPalette__OM_NEW(Class *cl, Object *o, struct opSet *msg)
493 struct opSet ops;
494 struct TagItem tags[] =
496 {GA_RelSpecial , TRUE},
497 {TAG_MORE , (IPTR)NULL}
500 EnterFunc(bug("Palette::New()\n"));
502 tags[1].ti_Data = (IPTR)msg->ops_AttrList;
504 ops.MethodID = OM_NEW;
505 ops.ops_GInfo = NULL;
506 ops.ops_AttrList = &tags[0];
508 o = (Object *)DoSuperMethodA(cl, o, (Msg)&ops);
509 if (o)
511 struct PaletteData *data = INST_DATA(cl, o);
513 /* Set some defaults */
514 data->pd_NumColors = 2;
515 data->pd_ColorTable = NULL;
516 data->pd_Color = 0;
517 data->pd_OldColor = 0 ; /* = data->pd_OldColor */
518 data->pd_ColorOffset = 0;
519 data->pd_IndWidth = 0;
520 data->pd_IndHeight = 0;
521 data->pd_LabelPlace = GV_LabelPlace_Above;
523 palette_set(cl, o, msg);
526 ReturnPtr ("Palette::New", IPTR, (IPTR)o);
529 /**********************************************************************************************/
531 IPTR GTPalette__OM_DISPOSE(Class *cl, Object *o, Msg msg)
533 struct PaletteData *data = INST_DATA(cl, o);
535 if (data->pd_Frame)
536 DisposeObject(data->pd_Frame);
538 return DoSuperMethodA(cl, o, msg);
541 /**********************************************************************************************/
543 IPTR GTPalette__GM_LAYOUT(Class *cl, struct Gadget *g, struct gpLayout *msg)
546 /* The palette gadget has been resized and we need to update our layout */
548 struct PaletteData *data = INST_DATA(cl, g);
549 struct IBox *gbox = &(data->pd_GadgetBox),
550 *pbox = &(data->pd_PaletteBox),
551 *indbox = &(data->pd_IndicatorBox);
552 UWORD cols, rows, cols_p2;
553 WORD leftover_width, leftover_height;
555 EnterFunc(bug("Palette::Layout()\n"));
557 if (!msg->gpl_GInfo)
558 ReturnInt("Palette::Layout", IPTR, 0); /* We MUST have a GInfo to get screen aspect ratio */
560 /* Delete the old gadget box */
561 if (!msg->gpl_Initial)
564 struct RastPort *rp;
566 if ((rp = ObtainGIRPort(msg->gpl_GInfo)))
568 SetAPen(rp, msg->gpl_GInfo->gi_DrInfo->dri_Pens[BACKGROUNDPEN]);
569 D(bug( "Clearing area (%d, %d, %d, %d)\n",
570 gbox->Left, gbox->Top, gbox->Left + gbox->Width, gbox->Top + gbox->Height));
571 RectFill( rp, gbox->Left, gbox->Top,
572 gbox->Left + gbox->Width - 1, gbox->Top + gbox->Height - 1);
574 ReleaseGIRPort(rp);
578 /* get the IBox surrounding the whole palette */
579 GetGadgetIBox(g, msg->gpl_GInfo, gbox);
581 D(bug( "Got palette ibox: (%d, %d, %d, %d)\n",
582 gbox->Left, gbox->Top, gbox->Width, gbox->Height));
584 /* Get the palette box */
585 pbox->Left = gbox->Left + VBORDER + VSPACING;
586 pbox->Top = gbox->Top + HBORDER + HSPACING;
587 pbox->Width = gbox->Width - VBORDER *2 - VSPACING *2;
588 pbox->Height = gbox->Height - HBORDER *2 - HSPACING *2;
591 /* If we have an indicator box then account for this */
592 if (data->pd_IndHeight)
594 indbox->Top = pbox->Top;
595 indbox->Left = pbox->Left;
596 indbox->Width = pbox->Width;
597 indbox->Height = data->pd_IndHeight;
599 pbox->Height -= (indbox->Height + HSPACING *2);
600 pbox->Top += (data->pd_IndHeight + HSPACING *2);
602 else if (data->pd_IndWidth)
604 indbox->Left = pbox->Left;
605 indbox->Top = pbox->Top;
606 indbox->Width = data->pd_IndWidth;
607 indbox->Height = pbox->Height;
609 pbox->Width -= (indbox->Width + VSPACING *2);
610 pbox->Left += (data->pd_IndWidth + VSPACING *2);
614 /* Compute initial aspect ratio */
615 cols = 1;
616 cols_p2 = data->pd_NumColors * pbox->Width / pbox->Height;
617 while ((cols*cols) <= cols_p2)
619 cols++;
621 if ((cols * cols) > cols_p2)
623 cols--;
625 rows = (data->pd_NumColors + cols - 1) / cols;
627 data->pd_NumCols = (UBYTE)cols;
628 data->pd_NumRows = (UBYTE)rows;
630 data->pd_ColWidth = pbox->Width / data->pd_NumCols;
631 data->pd_RowHeight = pbox->Height / data->pd_NumRows;
633 D(bug("cols=%d, rows=%d\n", data->pd_NumCols, data->pd_NumRows));
634 D(bug("colwidth=%d, rowheight=%d\n", data->pd_ColWidth, data->pd_RowHeight));
636 /* Adjust the pbox's and indbox's height according to leftovers */
638 leftover_width = pbox->Width % data->pd_NumCols;
639 leftover_height = pbox->Height % data->pd_NumRows;
641 pbox->Width -= leftover_width;
642 pbox->Height -= leftover_height;
644 if (data->pd_IndHeight)
645 indbox->Width -= leftover_width;
646 else if (data->pd_IndWidth)
647 indbox->Height -= leftover_height;
649 ReturnInt ("Palette::Layout", IPTR, 0);
653 /**********************************************************************************************/
655 IPTR GTPalette__GM_RENDER(Class *cl, struct Gadget *g, struct gpRender *msg)
657 struct PaletteData *data = INST_DATA(cl, g);
659 struct DrawInfo *dri = msg->gpr_GInfo->gi_DrInfo;
660 struct RastPort *rp;
661 struct IBox *gbox = &(data->pd_GadgetBox);
663 EnterFunc(bug("Palette::Render()\n"));
665 rp = msg->gpr_RPort;
667 switch (msg->gpr_Redraw)
669 case GREDRAW_REDRAW:
670 D(bug("Doing total redraw\n"));
672 /* Render gadget label in correct position */
673 renderlabel(GadToolsBase, g, rp, data->pd_LabelPlace);
675 RenderFrame(data, rp, gbox, dri, FALSE, FALSE, cl);
677 RenderPalette(data, rp, cl);
679 /* Render frame aroun ibox */
680 if (data->pd_IndWidth || data->pd_IndHeight)
682 RenderFrame(data, rp, &(data->pd_IndicatorBox), dri, TRUE, TRUE, cl);
685 case GREDRAW_UPDATE:
686 D(bug("Doing redraw update\n"));
688 UpdateActiveColor(data, dri, rp, cl);
690 if (data->pd_IndWidth || data->pd_IndHeight)
692 struct IBox *ibox = &(data->pd_IndicatorBox);
694 SetAPen(rp, GetPalettePen(data, data->pd_Color));
696 D(bug( "Drawing indocator at: (%d, %d, %d, %d)\n",
697 ibox->Left, ibox->Top,
698 ibox->Left + ibox->Width, ibox->Top + ibox->Height));
700 RectFill( msg->gpr_RPort,
701 ibox->Left + VBORDER + VSPACING,
702 ibox->Top + HBORDER + HSPACING,
703 ibox->Left + ibox->Width - 1 - VBORDER - VSPACING,
704 ibox->Top + ibox->Height - 1 - HBORDER - HSPACING);
707 break;
709 } /* switch (redraw method) */
711 if (g->Flags & GFLG_DISABLED)
713 DoDisabledPattern( rp,
714 gbox->Left,
715 gbox->Top,
716 gbox->Left + gbox->Width - 1,
717 gbox->Top + gbox->Height - 1,
718 dri->dri_Pens[SHADOWPEN],
719 GadToolsBase);
722 ReturnInt ("Palette::Render", IPTR, 0);
725 /**********************************************************************************************/
727 IPTR GTPalette__GM_HITTEST(Class *cl, Object *o, struct gpHitTest *msg)
729 struct PaletteData *data = INST_DATA(cl, o);
730 WORD x, y;
732 IPTR retval = 0UL;
734 EnterFunc(bug("Palette::HitTest()\n"));
736 /* One might think that this method is not necessary to implement,
737 ** but here is an example to show the opposite:
738 ** Consider a 16 color palette with 8 rows and 2 cols.
739 ** Gadget is 87 pix. heigh. Each row will then be 10 pix hight + 7 pix
740 ** of "nowhere". To prevent anything from happening when this area is
741 ** clicked, we rule it out here.
744 x = msg->gpht_Mouse.X + data->pd_GadgetBox.Left;
745 y = msg->gpht_Mouse.Y + data->pd_GadgetBox.Top;
747 if( (x > data->pd_PaletteBox.Left)
748 && (x < data->pd_PaletteBox.Left + data->pd_PaletteBox.Width - 1)
749 && (y > data->pd_PaletteBox.Top)
750 && (y < data->pd_PaletteBox.Top + data->pd_PaletteBox.Height - 1) )
752 retval = GMR_GADGETHIT;
755 ReturnInt ("Palette::HitTest", IPTR, retval);
758 /**********************************************************************************************/
760 IPTR GTPalette__GM_GOACTIVE(Class *cl, struct Gadget *g, struct gpInput *msg)
762 struct PaletteData *data = INST_DATA(cl, g);
763 IPTR retval = 0UL;
765 EnterFunc(bug("Palette::GoActive()\n"));
766 if (g->Flags & GFLG_DISABLED)
768 retval = GMR_NOREUSE;
770 else
772 if (msg->gpi_IEvent)
774 UBYTE clicked_color;
776 /* Set temporary active to the old active */
777 data->pd_ColorBackup = data->pd_Color;
779 clicked_color = ComputeColor( data,
780 msg->gpi_Mouse.X + data->pd_GadgetBox.Left,
781 msg->gpi_Mouse.Y + data->pd_GadgetBox.Top);
783 if (clicked_color != data->pd_Color)
785 struct RastPort *rp;
787 data->pd_Color = clicked_color;
789 if ((rp = ObtainGIRPort(msg->gpi_GInfo)))
791 DoMethod((Object *)g, GM_RENDER, (IPTR) msg->gpi_GInfo, (IPTR) rp, GREDRAW_UPDATE);
793 ReleaseGIRPort(rp);
797 retval = GMR_MEACTIVE;
799 } /* if (gadget activated is a result of user input) */
800 else
802 retval = GMR_NOREUSE;
805 } /* if (gadget isn't disabled) */
807 ReturnInt("Palette::GoActive", IPTR, retval);
810 /**********************************************************************************************/
812 IPTR GTPalette__GM_HANDLEINPUT(Class *cl, Object *o, struct gpInput *msg)
814 struct PaletteData *data = INST_DATA(cl, o);
815 struct InputEvent *ie = msg->gpi_IEvent;
816 IPTR retval = 0UL;
818 EnterFunc(bug("Palette::HandleInput\n"));
820 retval = GMR_MEACTIVE;
822 if (ie->ie_Class == IECLASS_RAWMOUSE)
824 WORD x = msg->gpi_Mouse.X + data->pd_GadgetBox.Left;
825 WORD y = msg->gpi_Mouse.Y + data->pd_GadgetBox.Top;
827 if (x <= data->pd_PaletteBox.Left)
828 x = data->pd_PaletteBox.Left + 1;
830 if (y <= data->pd_PaletteBox.Top)
831 y = data->pd_PaletteBox.Top + 1;
833 if (x >= data->pd_PaletteBox.Left + data->pd_PaletteBox.Width - 1)
834 x = data->pd_PaletteBox.Left + data->pd_PaletteBox.Width - 2;
836 if (y >= data->pd_PaletteBox.Top + data->pd_PaletteBox.Height - 1)
837 y = data->pd_PaletteBox.Top + data->pd_PaletteBox.Height - 2;
839 switch (ie->ie_Code)
841 case SELECTUP:
843 /* If the button was released outside the gadget, then
844 ** go back to old state --> no longer: stegerg
847 D(bug("IECLASS_RAWMOUSE: SELECTUP\n"));
848 #if 0
849 if (!InsidePalette(data, x, y))
851 struct RastPort *rp;
853 /* Left released outside of gadget area, go back
854 ** to old state
856 data->pd_Color = data->pd_ColorBackup;
857 D(bug("Left released outside gadget\n"));
859 if ((rp = ObtainGIRPort(msg->gpi_GInfo)))
861 DoMethod(o, GM_RENDER, msg->gpi_GInfo, rp, GREDRAW_UPDATE);
863 ReleaseGIRPort(rp);
866 else
868 #endif
869 D(bug( "Left released inside gadget, color=%d\n", GetPalettePen(data, data->pd_Color)));
870 *(msg->gpi_Termination) = GetPalettePen(data, data->pd_Color);
871 retval = GMR_VERIFY;
872 #if 0
874 #endif
876 retval |= GMR_NOREUSE;
877 break;
880 case IECODE_NOBUTTON:
883 UBYTE over_color;
885 D(bug("IECLASS_POINTERPOS\n"));
887 if (InsidePalette(data, x, y))
890 over_color = ComputeColor(data, x, y);
892 if (over_color != data->pd_Color)
894 struct RastPort *rp;
896 data->pd_Color = over_color;
897 if ((rp = ObtainGIRPort(msg->gpi_GInfo)))
899 DoMethod(o, GM_RENDER, (IPTR) msg->gpi_GInfo, (IPTR) rp, GREDRAW_UPDATE);
901 ReleaseGIRPort(rp);
904 } /* if (mouse is over a different color) */
906 } /* if (mouse is over gadget) */
908 retval = GMR_MEACTIVE;
911 break;
914 case MENUUP:
916 /* Right released on gadget, go back to old state */
918 struct RastPort *rp;
920 data->pd_Color = data->pd_ColorBackup;
921 D(bug("Right mouse pushed \n"));
923 if ((rp = ObtainGIRPort(msg->gpi_GInfo)))
925 DoMethod(o, GM_RENDER, (IPTR) msg->gpi_GInfo, (IPTR) rp, GREDRAW_UPDATE);
927 ReleaseGIRPort(rp);
930 retval = GMR_NOREUSE;
931 break;
934 } /* switch (ie->ie_Code) */
936 } /* if (mouse event) */
938 ReturnInt("Palette::HandleInput", IPTR, retval);
941 /**********************************************************************************************/
943 IPTR GTPalette__OM_SET(Class *cl, Object *o, struct opSet *msg)
945 IPTR retval = DoSuperMethodA(cl, o, (Msg)msg);
946 retval += (IPTR)palette_set(cl, o, msg);
947 /* If we have been subclassed, OM_UPDATE should not cause a GM_RENDER
948 *because it would circumvent the subclass from fully overriding it.
949 *The check of cl == OCLASS(o) should fail if we have been
950 *subclassed, and we have gotten here via DoSuperMethodA().
952 if ( retval && ((msg->MethodID != OM_UPDATE) || (cl == OCLASS(o))) )
954 struct GadgetInfo *gi = msg->ops_GInfo;
956 if (gi)
958 struct RastPort *rp = ObtainGIRPort(gi);
960 if (rp)
962 DoMethod( o,
963 GM_RENDER,
964 (IPTR) gi,
965 (IPTR) rp,
966 FindTagItem(GA_Disabled, msg->ops_AttrList) ? GREDRAW_REDRAW : GREDRAW_UPDATE);
968 ReleaseGIRPort(rp);
970 } /* if */
972 } /* if */
974 } /* if */
976 return retval;
979 /**********************************************************************************************/