home *** CD-ROM | disk | FTP | other *** search
/ AmigActive 26 / AACD 26.iso / AACD / Programming / ace_gpl_release / src / ace / c / event.c < prev    next >
Encoding:
C/C++ Source or Header  |  1998-10-04  |  15.8 KB  |  630 lines

  1. /* << ACE >>
  2.  
  3.    -- Amiga BASIC Compiler --
  4.  
  5.    ** Parser: event trapping code **
  6.    ** Copyright (C) 1998 David Benn
  7.    ** 
  8.    ** This program is free software; you can redistribute it and/or
  9.    ** modify it under the terms of the GNU General Public License
  10.    ** as published by the Free Software Foundation; either version 2
  11.    ** of the License, or (at your option) any later version.
  12.    **
  13.    ** This program is distributed in the hope that it will be useful,
  14.    ** but WITHOUT ANY WARRANTY; without even the implied warranty of
  15.    ** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  16.    ** GNU General Public License for more details.
  17.    **
  18.    ** You should have received a copy of the GNU General Public License
  19.    ** along with this program; if not, write to the Free Software
  20.    ** Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.
  21.  
  22.    Author: David J Benn
  23.      Date: 26th October-30th November, 1st-13th December 1991,
  24.        14th,20th-27th January 1992, 
  25.            2nd-17th, 21st-29th February 1992, 
  26.        1st,13th,14th,22nd,23rd March 1992,
  27.        21st,22nd April 1992,
  28.        2nd,3rd,11th,15th,16th May 1992,
  29.        7th,8th,9th,11th,13th,14th,28th,29th,30th June 1992,
  30.        2nd-8th,14th-19th,26th-29th July 1992,
  31.        1st-3rd,7th,8th,9th August 1992,
  32.        6th,7th,21st December 1992,
  33.        13th,28th February 1993,
  34.        1st March 1993,
  35.        25th September 1993,
  36.        24th,25th,26th October 1993,
  37.        2nd,8th-10th November 1993,
  38.        24th July 1994,
  39.        7th,8th August 1995
  40. */
  41.  
  42. #include "acedef.h"
  43.  
  44. /* externals */
  45. extern    int    sym;
  46. extern    int    lastsym;
  47. extern    SYM    *curr_item;
  48.  
  49. extern    char       id[MAXIDSIZE]; 
  50. extern    SHORT      shortval;
  51. extern    LONG       longval; 
  52. extern    float      singleval;
  53.  
  54. extern    BOOL     break_event;
  55. extern    BOOL     menu_event;
  56. extern    BOOL     mouse_event;
  57. extern    BOOL     timer_event;
  58. extern    BOOL     error_event;
  59. extern    BOOL     wdw_event;
  60. extern    BOOL     gad_event;
  61.  
  62. extern    BOOL     break_event_label_exists;
  63. extern    BOOL     menu_event_label_exists;
  64. extern    BOOL     mouse_event_label_exists;
  65. extern    BOOL     timer_event_label_exists;
  66. extern    BOOL     error_event_label_exists;
  67. extern    BOOL     wdw_event_label_exists;
  68. extern    BOOL     gad_event_label_exists;
  69.  
  70. extern    BOOL      ontimerused;
  71.  
  72. extern    BOOL     break_opt;
  73. extern    BOOL     wdw_close_opt;
  74.  
  75. extern    int    break_event_branch;
  76. extern    int    menu_event_branch;
  77. extern    int    mouse_event_branch;
  78. extern    int    timer_event_branch;
  79. extern    int    error_event_branch;
  80. extern    int    wdw_event_branch;
  81. extern    int    gad_event_branch;
  82.  
  83. extern    char     break_event_label[80];
  84. extern    char     menu_event_label[80];
  85. extern    char     mouse_event_label[80];
  86. extern    char     timer_event_label[80];
  87. extern    char     error_event_label[80];
  88. extern    char     wdw_event_label[80];
  89. extern    char     gad_event_label[80];
  90.  
  91. extern    float     timer_event_seconds;
  92. extern    char      ontimer_seconds[40];
  93.  
  94. /* functions */
  95. void get_event_trap_label()
  96. {
  97. /* ON <event>|[TIMER(n)] GOSUB <label> | GOTO <label> | CALL <SUBname> */
  98. int   event;
  99. int   branchsym;
  100. char  theLabel[80];
  101.  
  102.  if ((sym != breaksym) && (sym != menusym) &&
  103.      (sym != mousesym) && (sym != timersym) && 
  104.      (sym != errorsym) && (sym != windowsym) &&
  105.      (sym != gadgetsym))
  106.     _error(55);
  107.  else
  108.  {
  109.   event=sym; /* remember event specifier */
  110.  
  111.   /* if TIMER, get single-precision seconds */
  112.   if (event == timersym)
  113.   {
  114.    insymbol();
  115.    if (sym != lparen) _error(14);
  116.    else
  117.    {
  118.     insymbol();
  119.     if ((sym != shortconst) && (sym != longconst) &&
  120.         (sym != singleconst)) _error(27); /* numeric constant expected */
  121.     else
  122.     {
  123.      switch(sym)
  124.      {
  125.       case shortconst  : timer_event_seconds=SPFlt((ULONG)shortval); break;
  126.       case longconst   : timer_event_seconds=SPFlt((ULONG)longval);  break;
  127.       case singleconst : timer_event_seconds=singleval; break;
  128.      }
  129.      sprintf(ontimer_seconds,"#$%lx",timer_event_seconds);
  130.      insymbol();
  131.      if (sym != rparen) _error(9);       
  132.     }
  133.    }
  134.   }
  135.   insymbol();
  136.   if (sym != gosubsym && sym != gotosym && sym != callsym) 
  137.      _error(56);
  138.   else
  139.   {
  140.    branchsym=sym; /* GOSUB, GOTO or CALL? */
  141.  
  142.    insymbol();
  143.    if (sym != ident && sym != shortconst && sym != longconst)
  144.        _error(57);  /* label or SUB name expected */
  145.    else
  146.    {
  147.      /* Make a label from a line number? */
  148.      if (sym != ident) make_label_from_linenum(sym,id);
  149.  
  150.      /* 
  151.      ** Convert to a SUB label, check for existence 
  152.      ** (defined or declared) of SUB and number of 
  153.      ** parameters (must be zero to be valid).
  154.      */    
  155.      if (branchsym == callsym) 
  156.      {
  157.     sprintf(theLabel,"_SUB_%s",id);
  158.     if (!exist(theLabel,subprogram))
  159.     {
  160.         _error(59);
  161.         return;
  162.     }
  163.     else
  164.     if (curr_item->no_of_params != 0)
  165.     {
  166.         _error(78);
  167.         return;
  168.     }
  169.      }
  170.      else
  171.     strcpy(theLabel,id);
  172.  
  173.      switch(event)
  174.      {
  175.       case breaksym : strcpy(break_event_label,theLabel);
  176.               break_event_label_exists=TRUE; 
  177.               break_event_branch=branchsym;
  178.               break;
  179.  
  180.       case menusym  : strcpy(menu_event_label,theLabel);
  181.                menu_event_label_exists=TRUE;
  182.               menu_event_branch=branchsym;
  183.               break;
  184.  
  185.       case mousesym : strcpy(mouse_event_label,theLabel); 
  186.               mouse_event_label_exists=TRUE;
  187.               mouse_event_branch=branchsym;
  188.               break;
  189.  
  190.       case timersym : strcpy(timer_event_label,theLabel); 
  191.               timer_event_label_exists=TRUE;
  192.               timer_event_branch=branchsym;
  193.               break;
  194.  
  195.       case errorsym : strcpy(error_event_label,theLabel); 
  196.               error_event_label_exists=TRUE;
  197.               error_event_branch=branchsym;
  198.               break;
  199.  
  200.       case windowsym : strcpy(wdw_event_label,theLabel); 
  201.               wdw_event_label_exists=TRUE;
  202.               wdw_event_branch=branchsym;
  203.               break;
  204.  
  205.       case gadgetsym : strcpy(gad_event_label,theLabel); 
  206.               gad_event_label_exists=TRUE;
  207.               gad_event_branch=branchsym;
  208.               break;
  209.      }
  210.     insymbol();
  211.    }
  212.   }
  213.  }
  214. }
  215.  
  216. void change_event_trapping_status(event)
  217. int event;
  218. {
  219. /* <event> ON|OFF|STOP */
  220. int action;
  221.  
  222.  if (lastsym != windowsym && lastsym != gadgetsym &&
  223.      lastsym != menusym) insymbol();
  224.  
  225.  if ((sym != onsym) && (sym != offsym) && (sym != stopsym))
  226.     _error(58); /* ON, OFF or STOP expected */
  227.  else
  228.  {
  229.   action=sym; /* remember action symbol */
  230.   insymbol();
  231.   /* enable event trapping for <event>. */
  232.   if (action == onsym)
  233.      switch(event)
  234.      {
  235.       case breaksym : if (break_event_label_exists) 
  236.                  break_event=TRUE;
  237.                       else _error(59);
  238.               break;
  239.  
  240.       case menusym  : if (menu_event_label_exists) 
  241.                  menu_event=TRUE;
  242.                       else _error(59);
  243.               break;
  244.  
  245.       case mousesym : if (mouse_event_label_exists) 
  246.                  mouse_event=TRUE;
  247.                       else _error(59);
  248.               break;
  249.  
  250.       case timersym : if (timer_event_label_exists) 
  251.                  { timer_event=TRUE; ontimerused=TRUE; }
  252.                       else _error(59);
  253.               break;
  254.  
  255.       case errorsym : if (error_event_label_exists) 
  256.                  error_event=TRUE;
  257.                       else _error(59);
  258.               break;
  259.  
  260.       case windowsym : if (wdw_event_label_exists) 
  261.                  wdw_event=TRUE;
  262.                       else _error(59);
  263.               break;
  264.  
  265.       case gadgetsym : if (gad_event_label_exists) 
  266.                  gad_event=TRUE;
  267.                       else _error(59);
  268.               break;
  269.      }
  270.   else
  271.   /* disable event trapping for <event>. */
  272.   if (action == offsym)
  273.      switch(event)
  274.      {
  275.       case breaksym : if (break_event_label_exists) 
  276.                  { break_event=FALSE; break_event_label_exists=FALSE; }
  277.                       else _error(59);
  278.               break;
  279.  
  280.       case menusym  :  if (menu_event_label_exists) 
  281.                   { menu_event=FALSE; menu_event_label_exists=FALSE; }
  282.                        else _error(59);
  283.                break;
  284.  
  285.       case mousesym : if (mouse_event_label_exists) 
  286.                  { mouse_event=FALSE; mouse_event_label_exists=FALSE; }
  287.                       else _error(59);
  288.               break;
  289.  
  290.       case timersym : if (timer_event_label_exists) 
  291.                  { timer_event=FALSE; timer_event_label_exists=FALSE; }
  292.                       else _error(59);
  293.               break;
  294.  
  295.       case errorsym : if (error_event_label_exists) 
  296.                  { error_event=FALSE; error_event_label_exists=FALSE; }
  297.                       else _error(59);
  298.               break;
  299.  
  300.       case windowsym : if (wdw_event_label_exists) 
  301.                  { wdw_event=FALSE; wdw_event_label_exists=FALSE; }
  302.                       else _error(59);
  303.               break;
  304.  
  305.       case gadgetsym : if (gad_event_label_exists) 
  306.                  { gad_event=FALSE; gad_event_label_exists=FALSE; }
  307.                       else _error(59);
  308.               break;
  309.      }
  310.   else
  311.   /* disable event trapping for <event> but remember trapping routine. */ 
  312.   if (action == stopsym)
  313.      switch(event)
  314.      {
  315.       case breaksym : if (break_event_label_exists) 
  316.                  break_event=FALSE;
  317.                       else _error(59);
  318.               break;
  319.  
  320.       case menusym  : if (menu_event_label_exists) 
  321.                  menu_event=FALSE;
  322.                       else _error(59);
  323.               break;
  324.  
  325.       case mousesym : if (mouse_event_label_exists) 
  326.                  mouse_event=FALSE;
  327.                       else _error(59);
  328.               break;
  329.  
  330.       case timersym : if (timer_event_label_exists) 
  331.                  timer_event=FALSE;
  332.                       else _error(59);
  333.               break;
  334.  
  335.       case errorsym : if (error_event_label_exists) 
  336.                  error_event=FALSE;
  337.                       else _error(59);
  338.               break;
  339.  
  340.       case windowsym : if (wdw_event_label_exists) 
  341.                  wdw_event=FALSE;
  342.                       else _error(59);
  343.               break;
  344.  
  345.       case gadgetsym : if (gad_event_label_exists) 
  346.                  gad_event=FALSE;
  347.                       else _error(59);
  348.               break;
  349.      }
  350.  
  351.   insymbol();
  352.  } 
  353. }
  354.  
  355. void turn_event_off(eventHandler)
  356. char *eventHandler;
  357. {
  358. /* 
  359. ** Turn event trapping off if this 
  360. ** subroutine/subprogram belongs to 
  361. ** an event.
  362. */
  363.      if ((strcmp(eventHandler,break_event_label) == 0) && (break_event))
  364.         { break_event=FALSE; break_event_label_exists=FALSE; }
  365.      else
  366.      if ((strcmp(eventHandler,menu_event_label) == 0) && (menu_event))
  367.         { menu_event=FALSE; menu_event_label_exists=FALSE; }
  368.      else
  369.      if ((strcmp(eventHandler,mouse_event_label) == 0) && (mouse_event))
  370.         { mouse_event=FALSE; mouse_event_label_exists=FALSE; }
  371.      else
  372.      if ((strcmp(eventHandler,timer_event_label) == 0) && (timer_event))
  373.         { timer_event=FALSE; timer_event_label_exists=FALSE; }
  374.      else
  375.      if ((strcmp(eventHandler,error_event_label) == 0) && (error_event))
  376.         { error_event=FALSE; error_event_label_exists=FALSE; }
  377.      else
  378.      if ((strcmp(eventHandler,wdw_event_label) == 0) && (wdw_event))
  379.         { wdw_event=FALSE; wdw_event_label_exists=FALSE; }
  380.      else
  381.      if ((strcmp(eventHandler,gad_event_label) == 0) && (gad_event))
  382.         { gad_event=FALSE; gad_event_label_exists=FALSE; }
  383. }
  384.  
  385. void check_for_event()
  386. {
  387. /* produce code for event trapping */
  388.  if (break_opt)       ctrl_c_test();
  389.  if (break_event)     break_event_test();
  390.  if (menu_event)      menu_event_test();
  391.  if (wdw_close_opt)    wdw_close_test(); 
  392.  if (wdw_event)     wdw_event_test();
  393.  if (gad_event)     gad_event_test();
  394.  if (mouse_event)     mouse_event_test();
  395.  if (timer_event)     timer_event_test();
  396.  if (error_event)     error_event_test();
  397. }
  398.  
  399. void ctrl_c_test()
  400. {
  401. char lab[80],lablabel[80];
  402.  
  403. /* test for ctrl-c signal 
  404.    and exit program if a 
  405.    break signal is pending. */
  406.  
  407.    make_label(lab,lablabel);
  408.  
  409.    gen("jsr","_ctrl_c_test","  ");
  410.    gen("tst.l","d0","  ");
  411.    gen("beq.s",lab,"  ");
  412.    gen("jmp","_EXIT_PROG","  ");
  413.    gen(lablabel,"  ","  ");
  414.  
  415.    enter_XREF("_ctrl_c_test");
  416. }
  417.  
  418. void break_event_test()
  419. {
  420. char lab[80],lablabel[80];
  421.  
  422. /* test for ctrl-c signal 
  423.    and pass control to the
  424.    BREAK trapping subroutine. */
  425.  
  426.    make_label(lab,lablabel);
  427.  
  428.    gen("jsr","_ctrl_c_test","  ");
  429.    gen("tst.l","d0","  ");
  430.    gen("beq.s",lab,"  ");
  431.  
  432.    if (break_event_branch == callsym)
  433.       gen("jsr",break_event_label,"  ");
  434.    else
  435.    if (break_event_branch == gosubsym) 
  436.       gen_branch("jsr",break_event_label);
  437.    else
  438.       gen_branch("jmp",break_event_label);
  439.  
  440.    gen(lablabel,"  ","  ");
  441.  
  442.    enter_XREF("_ctrl_c_test");
  443. }
  444.  
  445. void menu_event_test()
  446. {
  447. char lab[80],lablabel[80];
  448.  
  449. /* test for menu button press 
  450.    and pass control to the
  451.    MENU trapping subroutine. */
  452.  
  453.  gen("jsr","_menu_test","  ");
  454.  gen("tst.l","d0","  ");
  455.  make_label(lab,lablabel);
  456.  gen("beq.s",lab,"  ");
  457.  
  458.  if (menu_event_branch == callsym)
  459.    gen("jsr",menu_event_label,"  ");
  460.  else
  461.  if (menu_event_branch == gosubsym) 
  462.     gen_branch("jsr",menu_event_label);
  463.  else
  464.     gen_branch("jmp",menu_event_label);
  465.  gen(lablabel,"  ","  ");
  466.  enter_XREF("_menu_test");
  467. }
  468.  
  469. void mouse_event_test()
  470. {
  471. char lab[80],lablabel[80];
  472.  
  473. /* test for left mouse button 
  474.    press and pass control to the
  475.    MOUSE trapping subroutine. */
  476.  
  477.  gen("moveq","#0","d0");
  478.  gen("jsr","_mouse","  ");
  479.  gen("tst.l","d0","  ");
  480.  make_label(lab,lablabel);
  481.  gen("beq.s",lab,"  ");
  482.  
  483.  if (mouse_event_branch == callsym)
  484.     gen("jsr",mouse_event_label,"  ");
  485.  else
  486.  if (mouse_event_branch == gosubsym) 
  487.     gen_branch("jsr",mouse_event_label);
  488.  else
  489.     gen_branch("jmp",mouse_event_label);
  490.  gen(lablabel,"  ","  ");
  491.  enter_XREF("_mouse");
  492. }
  493.  
  494. void timer_event_test()
  495. {
  496. char lab[80],lablabel[80];
  497.  
  498. /* test for timer event 
  499.    and pass control to the
  500.    TIMER trapping subroutine. */
  501.  
  502.  gen("move.l",ontimer_seconds,"d0");
  503.  gen("jsr","_ontimer","  ");
  504.  gen("tst.l","d0","  ");
  505.  make_label(lab,lablabel);
  506.  gen("beq.s",lab,"  ");
  507.  
  508.  if (timer_event_branch == callsym)
  509.    gen("jsr",timer_event_label,"  ");
  510.  else
  511.  if (timer_event_branch == gosubsym) 
  512.    gen_branch("jsr",timer_event_label);
  513.  else
  514.    gen_branch("jmp",timer_event_label);
  515.  gen(lablabel,"  ","  ");
  516.  enter_XREF("_ontimer");
  517.  enter_XREF("_MathBase");  /* timer routines need mathffp.library */
  518. }
  519.  
  520. void error_event_test()
  521. {
  522. char lab[80],lablabel[80];
  523.  
  524. /* Test for I/O error condition 
  525.    and pass control to the ERROR
  526.    trapping subroutine.
  527. */
  528.  
  529.  gen("jsr","_testerror","  ");
  530.  gen("tst.l","d0","  ");
  531.  make_label(lab,lablabel);
  532.  gen("beq.s",lab,"  ");
  533.  
  534.  if (error_event_branch == callsym)
  535.     gen("jsr",error_event_label,"  ");
  536.  else
  537.  if (error_event_branch == gosubsym) 
  538.     gen_branch("jsr",error_event_label);
  539.  else
  540.     gen_branch("jmp",error_event_label);
  541.  gen(lablabel,"  ","  ");
  542.  enter_XREF("_testerror");
  543. }
  544.  
  545. void wdw_close_test()
  546. {
  547. char lab[80],lablabel[80];
  548.  
  549. /* Test for close-gadget selection 
  550.    in any window and exit program 
  551.    if close-gadget click detected.
  552.  
  553.    The clicked window will be closed
  554.    before the program exits.
  555. */
  556.    make_label(lab,lablabel);
  557.  
  558.    gen("move.l","#1","-(sp)");
  559.    gen("jsr","_wdw_close_test","  ");
  560.    gen("addq","#4","sp");
  561.    gen("tst.l","d0","  ");
  562.    gen("beq.s",lab,"  ");
  563.    gen("jmp","_EXIT_PROG","  ");
  564.    gen(lablabel,"  ","  ");
  565.  
  566.    enter_XREF("_wdw_close_test");
  567. }
  568.  
  569. void wdw_event_test()
  570. {
  571. char lab[80],lablabel[80];
  572.  
  573. /* Test for close-gadget selection 
  574.    in any window and transfer control
  575.    to a user-defined subroutine if 
  576.    close-gadget click detected.
  577.    
  578.    This may be extended in the future
  579.    to accomodate other window events
  580.    (eg: resizing).   
  581. */
  582.    make_label(lab,lablabel);
  583.  
  584.    gen("move.l","#0","-(sp)");
  585.    gen("jsr","_wdw_close_test","  ");
  586.    gen("addq","#4","sp");
  587.    gen("tst.l","d0","  ");
  588.    gen("beq.s",lab,"  ");
  589.  
  590.   if (wdw_event_branch == callsym)
  591.     gen("jsr",wdw_event_label,"  ");
  592.    else
  593.    if (wdw_event_branch == gosubsym) 
  594.           gen_branch("jsr",wdw_event_label);
  595.    else
  596.         gen_branch("jmp",wdw_event_label);
  597.    gen(lablabel,"  ","  ");
  598.  
  599.    enter_XREF("_wdw_close_test");
  600. }
  601.  
  602. void gad_event_test()
  603. {
  604. char lab[80],lablabel[80];
  605.  
  606. /* Test for user-defined gadget selection 
  607.    in current output window and transfer 
  608.    control to a user-defined subroutine 
  609.    if a gadget click is detected.
  610. */
  611.    make_label(lab,lablabel);
  612.  
  613.    gen("move.l","#0","-(sp)");
  614.    gen("jsr","_gadget_event_test","  ");
  615.    gen("addq","#4","sp");
  616.    gen("tst.l","d0","  ");
  617.    gen("beq.s",lab,"  ");
  618.  
  619.    if (gad_event_branch == callsym)
  620.     gen("jsr",gad_event_label,"  ");
  621.    else
  622.    if (gad_event_branch == gosubsym) 
  623.           gen_branch("jsr",gad_event_label);
  624.    else
  625.         gen_branch("jmp",gad_event_label);
  626.    gen(lablabel,"  ","  ");
  627.  
  628.    enter_XREF("_gadget_event_test");
  629. }
  630.