home *** CD-ROM | disk | FTP | other *** search
/ Amiga Format CD 5 / amigaformatcd05.iso / mui / developer / oberon / txt / class1.mod < prev    next >
Text File  |  1996-08-13  |  7KB  |  218 lines

  1. MODULE Class1;
  2.  
  3. IMPORT
  4.   m := Mui,
  5.   mb := MuiBasics,
  6.   u := Utility,
  7.   I := Intuition,
  8.   y := SYSTEM,
  9.   e := Exec,
  10.   g := Graphics,
  11.   clf := Classface, (* IF you use V40 Interface *)
  12. (*  clf := Boopsi, *)
  13.   demo;
  14.  
  15. (***************************************************************************)
  16. (* Here is the beginning of our simple new class...                        *)
  17. (***************************************************************************)
  18.  
  19. (*
  20. ** This is an example for the simplest possible MUI class. It's just some
  21. ** kind of custom image and supports only two methods: 
  22. ** MUIM_AskMinMax and MUIM_Draw.
  23. *)
  24.  
  25. (*
  26. ** This is the instance data for our custom class.
  27. ** Since it's a very simple class, it contains just a dummy entry.
  28. *)
  29.  
  30. TYPE
  31.   MyData = STRUCT;
  32.              dummy : LONGINT;
  33.            END;
  34.  
  35. (*
  36. ** AskMinMax method will be called before the window is opened
  37. ** and before layout takes place. We need to tell MUI the
  38. ** minimum, maximum and default size of our object.
  39. *)
  40.  
  41.  
  42.   PROCEDURE AskMinMax(cl: I.IClassPtr; obj: m.Object; msg: I.MsgPtr ):e.APTR;
  43.  
  44.     BEGIN
  45.       (*
  46.       ** let our superclass first fill in what it thinks about sizes.
  47.       ** this will e.g. add the size of frame and inner spacing.
  48.       *)
  49.  
  50.       IF clf.DoSuperMethodA( cl, obj, msg^ ) = NIL THEN END;
  51.  
  52.       (*
  53.       ** now add the values specific to our object. note that we
  54.       ** indeed need to *add* these values, not just set them!
  55.       *)
  56.  
  57.       INC( msg(m.pAskMinMax).minMax.minWidth, 100 );
  58.       INC( msg(m.pAskMinMax).minMax.defWidth, 120 );
  59.       INC( msg(m.pAskMinMax).minMax.maxWidth, 500 );
  60.       INC( msg(m.pAskMinMax).minMax.minHeight, 40 );
  61.       INC( msg(m.pAskMinMax).minMax.defHeight, 90 );
  62.       INC( msg(m.pAskMinMax).minMax.maxHeight,300 );
  63.  
  64.       RETURN NIL;
  65.    END AskMinMax;
  66.  
  67.  
  68. (*
  69. ** Draw method is called whenever MUI feels we should render
  70. ** our object. This usually happens after layout is finished
  71. ** or when we need to refresh in a simplerefresh window.
  72. ** Note: You may only render within the rectangle
  73. **       _mleft(obj), _mtop(obj), _mwidth(obj), _mheight(obj).
  74. *)
  75.  
  76.   PROCEDURE Draw(cl: I.IClassPtr; obj: m.Object; msg: I.MsgPtr ):e.APTR;
  77.     VAR i : INTEGER;
  78.     BEGIN
  79.  
  80.         (*
  81.         ** let our superclass draw itself first, area class would
  82.         ** e.g. draw the frame and clear the whole region. What
  83.         ** it does exactly depends on msg->flags.
  84.         *)
  85.  
  86.         IF clf.DoSuperMethodA( cl, obj, msg^ ) = NIL THEN END;
  87.  
  88.         (*
  89.         ** if MADF_DRAWOBJECT isn't set, we shouldn't draw anything.
  90.         ** MUI just wanted to update the frame or something like that.
  91.         *)
  92.  
  93.         IF ~ (m.adfDrawobject IN msg(m.pDraw).flags) THEN
  94.           RETURN 0;
  95.         END;
  96.  
  97.         (*
  98.         ** ok, everything ready to render...
  99.         *)
  100.  
  101.         g.SetAPen( m.rp(obj), m.dri(obj).pens[I.textPen] );
  102.  
  103.  
  104.         FOR i := m.mleft(obj) TO m.mright(obj) BY 5 DO
  105.           g.Move(m.rp(obj), m.mleft(obj),m.mbottom(obj));
  106.           g.Draw(m.rp(obj),i, m.mtop(obj));
  107.           g.Move(m.rp(obj),m.mright(obj),m.mbottom(obj));
  108.           g.Draw(m.rp(obj),i, m.mtop(obj));
  109.         END;
  110.         RETURN NIL;
  111.     END Draw;
  112.  
  113.  
  114. (*
  115. ** Here comes the dispatcher for our custom class. We only need to
  116. ** care about MUIM_AskMinMax and MUIM_Draw in this simple case.
  117. ** Unknown/unused methods are passed to the superclass immediately.
  118. *)
  119.  
  120.   PROCEDURE MyDispatcher (cl: I.IClassPtr; obj: m.Object; msg: I.MsgPtr):e.APTR;
  121.     BEGIN
  122.       CASE msg.methodID OF
  123.         | m.mAskMinMax : RETURN( AskMinMax(cl, obj, msg ) );
  124.         | m.mDraw      : RETURN( Draw     (cl, obj, msg ) );
  125.       ELSE;
  126.         RETURN clf.DoSuperMethodA( cl, obj, msg^ );
  127.       END;
  128.     END MyDispatcher;
  129.  
  130.  
  131.  
  132. (***************************************************************************)
  133. (* Thats all there is about it. Now lets see how things are used...        *)
  134. (***************************************************************************)
  135.  
  136.   VAR app, window, MyObj : m.Object;
  137.       MyClass, SuperClass : I.IClassPtr;
  138.       signals : LONGSET;
  139.       running : BOOLEAN;
  140.  
  141. CONST class1Id = y.VAL( LONGINT, "CLS1" );
  142.  
  143. BEGIN
  144.   running := TRUE;
  145.  
  146.         (* Get a pointer to the superclass. MUI will lock this *)
  147.         (* and prevent it from being flushed during you hold   *)
  148.         (* the pointer. When you're done, you have to call     *)
  149.         (* MUI_FreeClass() to release this lock.               *)
  150.  
  151.         SuperClass := m.GetClass( m.cArea );
  152.         IF SuperClass = NIL THEN
  153.           demo.fail( NIL, "Superclass for the new class not found." );
  154.         END;
  155.  
  156.         (* create the new class *)
  157.         MyClass := I.MakeClass( NIL, NIL, SuperClass, SIZE( MyData ), LONGSET{0} );
  158.         IF MyClass = NIL THEN
  159.           m.FreeClass( SuperClass );
  160.           demo.fail ( NIL, "Failed to create class" );
  161.         END;
  162.  
  163.         (* set the dispatcher for the new class *)
  164.         u.InitHook( MyClass, y.VAL( u.HookFunc, MyDispatcher ) );
  165.  
  166.         mb.ApplicationObject( m.aApplicationTitle      , y.ADR( "Class1" ),
  167.                               m.aApplicationVersion    , y.ADR( "$VER: Class1 1.0 (01.12.93)" ),
  168.                               m.aApplicationCopyright  , y.ADR( "©1993, Stefan Stuntz" ),
  169.                               m.aApplicationAuthor     , y.ADR( "Stefan Stuntz, Oberon: Albert Weinert" ),
  170.                               m.aApplicationDescription, y.ADR( "Demonstrate the use of custom classes. Oberon Version" ),
  171.                               m.aApplicationBase       , y.ADR( "CLASS1" ), u.end );
  172.  
  173.           mb.SubWindow; mb.WindowObject( m.aWindowTitle, y.ADR( "A Simple Custom Class") ,
  174.                                          m.aWindowID   , class1Id, u.end );
  175.                           mb.WindowContents; mb.VGroup;
  176.                                                mb.Child; mb.INewObject( MyClass, NIL );
  177.                                                             mb.TextFrame;
  178.                                                             mb.TagItem( m.aBackground, m.iBACKGROUND );
  179.                                                          MyObj := mb.IEnd();
  180.                                              mb.end;
  181.                         window := mb.End();
  182.         app := mb.EndApplication();
  183.  
  184.         IF app = NIL THEN
  185.                 demo.fail(app,"Failed to create Application.");
  186.         END;
  187.         m.DoMethod( window,m.mNotify,m.aWindowCloseRequest,e.true,
  188.                      app,2,m.mApplicationReturnID,m.vApplicationReturnIDQuit);
  189.  
  190.  
  191.  
  192. (*
  193. ** Input loop...
  194. *)
  195.  
  196.     mb.Set(window,m.aWindowOpen,e.LTRUE);
  197.  
  198.   running := TRUE;
  199.   WHILE running DO
  200.     CASE m.DOMethod( app, m.mApplicationInput, y.ADR(signals), u.end ) OF
  201.       | m.vApplicationReturnIDQuit :
  202.           running := FALSE;
  203.     ELSE END;
  204.     IF (running) & (signals # LONGSET{}) THEN y.SETREG( 0, e.Wait(signals) ) END;
  205.   END;
  206.   mb.Set(window,m.aWindowOpen,I.LFALSE);
  207.  
  208.  
  209. (*
  210. ** Shut down...
  211. *)
  212.  
  213.         m.DisposeObject(app);      (* dispose all objects. *)
  214.         IF I.FreeClass(MyClass) THEN END;          (* free our custom class. *)
  215.         m.FreeClass(SuperClass);  (* release super class pointer. *)
  216.         demo.fail( NIL, "");             (* exit, app is already disposed. *)
  217. END Class1.
  218.