Minor fixes to comments.
[AROS.git] / rom / intuition / gadgetclass.c
blobc4783ad438957e7224cf59e7048427967c74f9ea
1 /*
2 Copyright 1995-2011, The AROS Development Team. All rights reserved.
3 Copyright 2001-2003, The MorphOS Development Team. All Rights Reserved.
4 $Id$
5 */
7 #include <exec/types.h>
9 #include <dos/dos.h>
10 #include <dos/dosextens.h>
12 #include <intuition/intuition.h>
13 #include <intuition/intuitionbase.h>
14 #include <intuition/classes.h>
15 #include <intuition/classusr.h>
16 #include <intuition/gadgetclass.h>
17 #include <intuition/cghooks.h>
18 #include <intuition/icclass.h>
20 #include <graphics/gfxbase.h>
21 #include <graphics/gfxmacros.h>
23 #include <utility/tagitem.h>
24 #include <utility/hooks.h>
26 #include <clib/macros.h>
28 #include <string.h>
30 #include <proto/exec.h>
31 #include <proto/intuition.h>
32 #include <proto/graphics.h>
33 #include <proto/utility.h>
35 #ifndef __MORPHOS__
37 struct ICData;
38 #include "intuition_intern.h"
39 #include <aros/asmcall.h>
40 #include <proto/alib.h>
41 #include "gadgets.h"
43 #endif /* !__MORPHOS__ */
45 #define DEBUG_GADGET(x) ;
47 /****************************************************************************/
49 /* set gadget attributes
51 static ULONG set_gadgetclass(Class *cl, struct ExtGadget *eg, struct opSet *msg)
53 struct IntuitionBase *IntuitionBase = (struct IntuitionBase *)cl->cl_UserData;
54 struct Library *UtilityBase = GetPrivIBase(IntuitionBase)->UtilityBase;
55 struct TagItem *tag, *tstate = msg->ops_AttrList;
56 IPTR tidata;
57 ULONG retval = 0UL; /* set to non-zero to signal visual changes */
59 while ( (tag = NextTagItem(&tstate)) )
61 tidata = tag->ti_Data;
63 switch(tag->ti_Tag)
65 case GA_Left:
66 eg->LeftEdge = (WORD)tidata;
67 //eg->Flags &= ~GFLG_RELRIGHT;
68 retval = 1UL;
69 break;
71 case GA_Top:
72 eg->TopEdge = (WORD)tidata;
73 //eg->Flags &= ~GFLG_RELBOTTOM;
74 retval = 1UL;
75 break;
77 case GA_Width:
78 eg->Width = (WORD)tidata;
79 eg->Flags &= ~GFLG_RELWIDTH;
80 retval = 1UL;
81 break;
83 case GA_Height:
84 eg->Height = (WORD)tidata;
85 eg->Flags &= ~GFLG_RELHEIGHT;
86 retval = 1UL;
87 break;
89 case GA_RelRight:
90 eg->LeftEdge = (WORD)tidata;
91 eg->Flags |= GFLG_RELRIGHT;
92 retval = 1UL;
93 break;
95 case GA_RelBottom:
96 eg->TopEdge = (WORD)tidata;
97 eg->Flags |= GFLG_RELBOTTOM;
98 retval = 1UL;
99 break;
101 case GA_RelWidth:
102 eg->Width = (WORD)tidata;
103 eg->Flags |= GFLG_RELWIDTH;
104 retval = 1UL;
105 break;
107 case GA_RelHeight:
108 eg->Height = (WORD)tidata;
109 eg->Flags |= GFLG_RELHEIGHT;
110 retval = 1UL;
111 break;
113 case GA_RelSpecial:
114 if (tidata)
116 eg->Flags |= GFLG_RELSPECIAL;
118 else
120 eg->Flags &= ~GFLG_RELSPECIAL;
122 retval = 1UL;
123 break;
125 case GA_Bounds:
126 if (tidata)
128 eg->BoundsLeftEdge = ((struct IBox *)tidata)->Left;
129 eg->BoundsTopEdge = ((struct IBox *)tidata)->Top;
130 eg->BoundsWidth = ((struct IBox *)tidata)->Width;
131 eg->BoundsHeight = ((struct IBox *)tidata)->Height;
132 eg->MoreFlags |= GMORE_BOUNDS;
134 retval = 1UL;
135 break;
137 case GA_GadgetHelp:
138 if (tidata)
140 eg->MoreFlags |= GMORE_GADGETHELP;
142 else
144 eg->MoreFlags &= ~GMORE_GADGETHELP;
146 retval = 1UL;
147 break;
149 case GA_Next:
150 eg->NextGadget = (struct ExtGadget *)tidata;
151 break;
153 case GA_Previous:
154 if( (tidata != 0L) && (msg->MethodID == OM_NEW) )
156 eg->NextGadget = ((struct ExtGadget *)tidata)->NextGadget;
157 ((struct ExtGadget *)tidata)->NextGadget = eg;
159 break;
161 case GA_IntuiText:
162 eg->GadgetText = (struct IntuiText *)tidata;
163 if (tidata)
165 eg->Flags &= ~GFLG_LABELMASK;
166 eg->Flags |= GFLG_LABELITEXT;
168 retval = 1UL;
169 break;
171 case GA_Text:
172 eg->GadgetText = (struct IntuiText *)tidata;
173 if (tidata)
175 eg->Flags &= ~GFLG_LABELMASK;
176 eg->Flags |= GFLG_LABELSTRING;
178 retval = 1UL;
179 break;
181 case GA_LabelImage:
182 eg->GadgetText = (struct IntuiText *)tidata;
183 if (tidata)
185 eg->Flags &= ~GFLG_LABELMASK;
186 eg->Flags |= GFLG_LABELIMAGE;
188 retval = 1UL;
189 break;
191 case GA_Image:
192 eg->GadgetRender = (APTR)tidata;
193 if (tidata)
195 eg->Flags |= GFLG_GADGIMAGE;
197 retval = 1UL;
198 break;
200 case GA_Border:
201 eg->GadgetRender = (APTR)tidata;
202 if (tidata)
204 eg->Flags &= ~GFLG_GADGIMAGE;
206 retval = 1UL;
207 break;
209 case GA_SelectRender:
210 eg->SelectRender = (APTR)tidata;
212 eg->Flags |= (GFLG_GADGIMAGE & GFLG_GADGHIMAGE);
214 retval = 1UL;
215 break;
217 case GA_SpecialInfo:
218 eg->SpecialInfo = (APTR)tidata;
219 break;
221 case GA_GZZGadget:
222 if ( tidata != FALSE )
224 eg->GadgetType |= GTYP_GZZGADGET;
226 else
228 eg->GadgetType &= ~GTYP_GZZGADGET;
230 break;
232 case GA_SysGadget:
233 if ( tidata != FALSE )
235 eg->GadgetType |= GTYP_SYSGADGET;
237 else
239 eg->GadgetType &= ~GTYP_SYSGADGET;
241 break;
243 case GA_Selected:
244 if ( tidata != FALSE )
246 eg->Flags |= GFLG_SELECTED;
248 else
250 eg->Flags &= ~GFLG_SELECTED;
252 retval = 1UL;
253 break;
255 case GA_Disabled:
256 if ( tidata != FALSE )
258 eg->Flags |= GFLG_DISABLED;
260 else
262 eg->Flags &= ~GFLG_DISABLED;
264 retval = 1UL;
265 break;
267 case GA_EndGadget:
268 if ( tidata != FALSE )
270 eg->Activation |= GACT_ENDGADGET;
272 else
274 eg->Activation &= ~GACT_ENDGADGET;
276 break;
278 case GA_Immediate:
279 if ( tidata != FALSE )
281 eg->Activation |= GACT_IMMEDIATE;
283 else
285 eg->Activation &= ~GACT_IMMEDIATE;
287 break;
289 case GA_RelVerify:
290 if ( tidata != FALSE )
292 eg->Activation |= GACT_RELVERIFY;
294 else
296 eg->Activation &= ~GACT_RELVERIFY;
298 break;
300 case GA_FollowMouse:
301 if ( tidata != FALSE )
303 eg->Activation |= GACT_FOLLOWMOUSE;
305 else
307 eg->Activation &= ~GACT_FOLLOWMOUSE;
309 break;
311 case GA_RightBorder:
312 if ( tidata != FALSE )
314 eg->Activation |= GACT_RIGHTBORDER;
316 else
318 eg->Activation &= ~GACT_RIGHTBORDER;
320 break;
322 case GA_LeftBorder:
323 if ( tidata != FALSE )
325 eg->Activation |= GACT_LEFTBORDER;
327 else
329 eg->Activation &= ~GACT_LEFTBORDER;
331 break;
333 case GA_TopBorder:
334 if ( tidata != FALSE )
336 eg->Activation |= GACT_TOPBORDER;
338 else
340 eg->Activation &= ~GACT_TOPBORDER;
342 break;
344 case GA_BottomBorder:
345 if ( tidata != FALSE )
347 eg->Activation |= GACT_BOTTOMBORDER;
349 else
351 eg->Activation &= ~GACT_BOTTOMBORDER;
353 break;
355 case GA_ToggleSelect:
356 if (tidata)
358 eg->Activation |= GACT_TOGGLESELECT;
360 else
362 eg->Activation &= ~GACT_TOGGLESELECT;
364 break;
366 case GA_TabCycle:
367 if (tidata)
369 eg->Flags |= GFLG_TABCYCLE;
371 else
373 eg->Flags &= ~GFLG_TABCYCLE;
375 break;
377 case GA_Highlight:
378 eg->Flags &= ~GFLG_GADGHIGHBITS;
379 eg->Flags |= tidata & GFLG_GADGHIGHBITS;
380 break;
382 case GA_SysGType:
383 eg->GadgetType &= ~GTYP_SYSTYPEMASK;
384 eg->GadgetType |= tidata & GTYP_SYSTYPEMASK;
385 break;
387 case GA_ID:
388 /* GA_ID should NOT be set if this is a OM_UPDATE.
389 ** This is because gadgets should send their GA_ID
390 ** when doing a OM_NOTIFY, so that the receiver
391 ** might see who sent the message.
392 ** But we surely don't want to change the GA_ID
393 ** of the reciver to that of the sender.
395 if (msg->MethodID != OM_UPDATE)
397 eg->GadgetID = tidata;
399 break;
401 case GA_UserData:
402 eg->UserData = (APTR)tidata;
403 DEBUG_GADGET(dprintf("set_gadgetclass: UserData 0x%lx\n",tidata));
404 break;
406 case ICA_TARGET:
407 ((struct GadgetData *)eg)->IC.ic_Target = (Object *)tidata;
408 break;
410 case ICA_MAP:
411 ((struct GadgetData *)eg)->IC.ic_Mapping = (struct TagItem *)tidata;
412 break;
414 } /* switch tag */
416 } /* while NextTagItem */
418 #if 0
419 /* This seems to be wrong here. Instead buttongclass is where
420 something like this happens, so look there (stegerg) */
422 if ((msg->MethodID == OM_NEW) &&
423 (eg->Flags & GFLG_GADGIMAGE) &&
424 (eg->GadgetRender != NULL))
426 if (eg->Width == 0) eg->Width = ((struct Image *)eg->GadgetRender)->Width;
427 if (eg->Height == 0) eg->Height = ((struct Image *)eg->GadgetRender)->Height;
429 #endif
431 return retval;
435 IPTR GadgetClass__OM_NEW(Class *cl, Object *o, struct opSet *msg)
437 struct ExtGadget *eg = (struct ExtGadget *)DoSuperMethodA(cl, o, (Msg)msg);
439 if (eg)
441 /* set some defaults */
443 * The instance object is cleared memory!
444 * memset (eg, 0, sizeof(struct GadgetData));
446 eg->Flags = GFLG_EXTENDED;
447 eg->GadgetType = GTYP_CUSTOMGADGET;
448 eg->MoreFlags = GMORE_BOOPSIGADGET;
449 eg->MutualExclude = (IPTR)&((Class *)o)->cl_Dispatcher;
451 /* Handle our special tags - overrides defaults */
452 set_gadgetclass(cl, eg, msg);
455 return (IPTR)eg;
458 IPTR GadgetClass__OM_SET(Class *cl, struct ExtGadget *eg, struct opSet *msg)
460 return DoSuperMethodA(cl, (Object *)eg, (Msg)msg) + set_gadgetclass(cl, eg, (struct opSet *)msg);
463 IPTR GadgetClass__OM_NOTIFY(Class *cl, struct GadgetData *gd, struct opUpdate *msg)
465 struct IntuitionBase *IntuitionBase = (struct IntuitionBase *)cl->cl_UserData;
466 DEBUG_GADGET(dprintf("dispatch_gadgetclass: OM_NOTIFY\n"));
467 DoNotify(cl, (Object *)gd, &(gd->IC), msg);
468 DEBUG_GADGET(dprintf("dispatch_gadgetclass: OM_NOTIFY done\n"));
470 return (IPTR)0;
473 IPTR GadgetClass__OM_DISPOSE(Class *cl, struct GadgetData *gd, Msg msg)
475 struct IntuitionBase *IntuitionBase = (struct IntuitionBase *)cl->cl_UserData;
476 FreeICData((struct ICData *)&gd->IC);
477 return DoSuperMethodA(cl, (Object *)gd, (Msg)msg);
480 /* get gadget attributes - gadgetclass really has no gettable
481 * attributes, but we will implement some useful ones anyway. ;0
483 IPTR GadgetClass__OM_GET(Class *cl, struct ExtGadget *eg, struct opGet *msg)
485 ULONG retval = 1UL;
487 switch (msg->opg_AttrID)
489 case GA_Left:
490 case GA_RelRight:
491 *msg->opg_Storage = (IPTR) eg->LeftEdge;
492 break;
494 case GA_Top:
495 case GA_RelBottom:
496 *msg->opg_Storage = (IPTR) eg->TopEdge;
497 break;
499 case GA_Width:
500 case GA_RelWidth:
501 *msg->opg_Storage = (IPTR) eg->Width;
502 break;
504 case GA_Height:
505 case GA_RelHeight:
506 *msg->opg_Storage = (IPTR) eg->Height;
507 break;
509 case GA_Selected:
510 *msg->opg_Storage = (IPTR)((eg->Flags & GFLG_SELECTED) != 0);
511 break;
513 case GA_Disabled:
514 *msg->opg_Storage = (IPTR)((eg->Flags & GFLG_DISABLED) != 0);
515 break;
517 case GA_ID:
518 *msg->opg_Storage = (IPTR)eg->GadgetID;
519 break;
521 case GA_UserData:
522 *msg->opg_Storage = (IPTR)eg->UserData;
523 break;
525 case GA_RelSpecial:
526 *msg->opg_Storage = (IPTR)(eg->Flags & GFLG_RELSPECIAL) ? TRUE : FALSE;
527 break;
529 case GA_GadgetHelp:
530 *msg->opg_Storage = (IPTR)(eg->MoreFlags & GMORE_GADGETHELP) ? TRUE : FALSE;
531 break;
533 case GA_Next:
534 *msg->opg_Storage = (IPTR)eg->NextGadget;
535 break;
537 case GA_IntuiText:
538 *msg->opg_Storage = (IPTR)((eg->Flags & GFLG_LABELITEXT) ? eg->GadgetText : 0);
539 break;
541 case GA_Text:
542 *msg->opg_Storage = (IPTR)((eg->Flags & GFLG_LABELSTRING) ? eg->GadgetText : 0);
543 break;
545 case GA_LabelImage:
546 *msg->opg_Storage = (IPTR)((eg->Flags & GFLG_LABELIMAGE) ? eg->GadgetText : 0);
547 break;
549 case GA_Image:
550 *msg->opg_Storage = (IPTR)((eg->Flags & GFLG_GADGIMAGE) ? eg->GadgetRender : 0);
551 break;
553 case GA_Border:
554 *msg->opg_Storage = (IPTR)((eg->Flags & GFLG_GADGIMAGE) ? 0 : eg->GadgetRender);
555 break;
557 case GA_SelectRender:
558 *msg->opg_Storage = (IPTR)((eg->Flags & GFLG_GADGHIMAGE) ? eg->SelectRender : 0);
559 break;
561 case GA_SpecialInfo:
562 *msg->opg_Storage = (IPTR)eg->SpecialInfo;
563 break;
565 case GA_GZZGadget:
566 *msg->opg_Storage = (IPTR)((eg->GadgetType & GTYP_GZZGADGET) ? TRUE : FALSE);
567 break;
569 case GA_SysGadget:
570 *msg->opg_Storage = (IPTR)((eg->GadgetType & GTYP_SYSGADGET) ? TRUE : FALSE);
571 break;
573 case GA_EndGadget:
574 *msg->opg_Storage = (IPTR)((eg->Activation & GACT_ENDGADGET) ? TRUE : FALSE);
575 break;
577 case GA_Immediate:
578 *msg->opg_Storage = (IPTR)((eg->Activation & GACT_IMMEDIATE) ? TRUE : FALSE);
579 break;
581 case GA_RelVerify:
582 *msg->opg_Storage = (IPTR)((eg->Activation & GACT_RELVERIFY) ? TRUE : FALSE);
583 break;
585 case GA_FollowMouse:
586 *msg->opg_Storage = (IPTR)((eg->Activation & GACT_FOLLOWMOUSE) ? TRUE : FALSE);
587 break;
589 case GA_RightBorder:
590 *msg->opg_Storage = (IPTR)((eg->Activation & GACT_RIGHTBORDER) ? TRUE : FALSE);
591 break;
593 case GA_LeftBorder:
594 *msg->opg_Storage = (IPTR)((eg->Activation & GACT_LEFTBORDER) ? TRUE : FALSE);
595 break;
597 case GA_TopBorder:
598 *msg->opg_Storage = (IPTR)((eg->Activation & GACT_TOPBORDER) ? TRUE : FALSE);
599 break;
601 case GA_BottomBorder:
602 *msg->opg_Storage = (IPTR)((eg->Activation & GACT_BOTTOMBORDER) ? TRUE : FALSE);
603 break;
605 case GA_ToggleSelect:
606 *msg->opg_Storage = (IPTR)((eg->Activation & GACT_TOGGLESELECT) ? TRUE : FALSE);
607 break;
609 case GA_TabCycle:
610 *msg->opg_Storage = (IPTR)((eg->Flags & GFLG_TABCYCLE) ? TRUE : FALSE);
611 break;
613 case GA_Highlight:
614 *msg->opg_Storage = (IPTR)((eg->Flags & GFLG_GADGHIGHBITS) ? TRUE : FALSE);
615 break;
617 case GA_SysGType:
618 *msg->opg_Storage = (IPTR)(eg->GadgetType & GTYP_SYSTYPEMASK);
619 break;
621 case ICA_TARGET:
622 *msg->opg_Storage = (IPTR)((struct GadgetData *)eg)->IC.ic_Target;
623 break;
625 case ICA_MAP:
626 *msg->opg_Storage = (IPTR)((struct GadgetData *)eg)->IC.ic_Mapping;
627 break;
629 case GA_Bounds:
630 if (msg->opg_Storage)
632 struct IBox *ibox = (struct IBox *)msg->opg_Storage;
634 ibox->Left = eg->BoundsLeftEdge;
635 ibox->Top = eg->BoundsTopEdge;
636 ibox->Width = eg->BoundsWidth;
637 ibox->Height = eg->BoundsHeight;
639 break;
642 default:
643 #if 0
644 /* DONT DO THIS!! For example BGUI propclass relies on this not happening!! */
646 *msg->opg_Storage = (IPTR)NULL;
648 #endif
649 retval = 0UL;
650 break;
652 } /* switch attrid) */
654 return(retval);
657 /* test if we should try to activate this gadget...
659 IPTR GadgetClass__GM_HITTEST(Class *cl, Object *o, struct gpHitTest *gpht)
661 return (IPTR)GMR_GADGETHIT;
664 /* Methods follows that only need to return a value because they should be handled by
665 * the subclasses
667 IPTR GadgetClass__One(Class *cl, Object *o, Msg msg)
669 return (IPTR)1;
672 IPTR GadgetClass__Zero(Class *cl, Object *o, Msg msg)
674 return (IPTR)0;
677 IPTR GadgetClass_NoReuse(Class *cl, Object *o, Msg msg)
679 return (IPTR)GMR_NOREUSE;
682 IPTR GadgetClass__GM_HELPTEST(Class *cl, Object *o, Msg msg)
684 DEBUG_GADGET(dprintf("dispatch_gadgetclass: GM_HELPTEST\n"));
685 return (IPTR)GMR_HELPHIT;
688 IPTR GadgetClass__ICM_SETLOOP(Class *cl, struct GadgetData *gd, Msg msg)
690 DEBUG_GADGET(dprintf("dispatch_gadgetclass: ICM_SETLOOP\n"));
691 gd->IC.ic_LoopCounter += 1UL;
693 return (IPTR)0;
696 IPTR GadgetClass__ICM_CLEARLOOP(Class *cl, struct GadgetData *gd, Msg msg)
698 DEBUG_GADGET(dprintf("dispatch_gadgetclass: ICM_CLEARLOOP\n"));
699 gd->IC.ic_LoopCounter -= 1UL;
701 return (IPTR)0;
704 IPTR GadgetClass__ICM_CHECKLOOP(Class *cl, struct GadgetData *gd, Msg msg)
706 DEBUG_GADGET(dprintf("dispatch_gadgetclass: ICM_CHECKLOOP\n"));
707 return (IPTR)gd->IC.ic_LoopCounter;