home *** CD-ROM | disk | FTP | other *** search
/ OS/2 Shareware BBS: 5 Edit / 05-Edit.zip / epmmac.zip / DRAW.E < prev    next >
Text File  |  1994-12-14  |  15KB  |  460 lines

  1. /******************************************************************************
  2.  
  3. DRAW.E         revised from SLIMDRAW.E                   Bryan Lewis 3/23/88
  4.  
  5. Two small changes have made this a separately-compilable and
  6. linkable-at-runtime module.  In EOS2 it makes more sense to
  7. "connect up" the DRAW feature only when needed, rather than compile it
  8. into the always-present base.  Any stand-alone command (not called as a
  9. subroutine by others) that's used only occasionally is a good candidate for
  10. linking.
  11.  
  12. (1) The conditional compilation test (WANT_DRAW) has been removed to
  13. make this separately compilable, since WANT_DRAW is defined in
  14. STDCNF.E, not available when this is compiled alone.
  15.  
  16. (2) A DEFMAIN has been added which merely invokes the original DRAW command.
  17.  
  18. When the user issues "draw" on the command line, DRAW.EX will be linked
  19. from disk and entered at DEFMAIN.  The effect seen by the user will be the same
  20. as before, except for the slight delay of searching the DPATH for DRAW.EX.
  21. When DEFMAIN finishes, DRAW.EX will be automatically unlinked to free up
  22. memory.
  23.  
  24.  
  25. (SlimDraw was revised from Davis Foulger's DRAW.E by Bryan Lewis 10/87.)
  26. (Insert-toggle feature suggested by John McAssey.)
  27.  
  28. ******************************************************************************/
  29.  
  30. compile if not defined(SMALL)  -- If being externally compiled...
  31.  define INCLUDING_FILE = 'DRAW.E'
  32. const
  33.    tryinclude 'MYCNF.E'
  34.  compile if not defined(SITE_CONFIG)
  35.     const SITE_CONFIG = 'SITECNF.E'
  36.  compile endif
  37.  compile if SITE_CONFIG
  38.     tryinclude SITE_CONFIG
  39.  compile endif
  40. const
  41.  compile if not defined(WANT_DBCS_SUPPORT)
  42.    WANT_DBCS_SUPPORT = 0
  43.  compile endif
  44.  compile if not defined(NLS_LANGUAGE)
  45.    NLS_LANGUAGE = 'ENGLISH'
  46.  compile endif
  47.  include NLS_LANGUAGE'.e'
  48. ;include 'stdconst.e'     -- Don't waste time including just to define MAXCOL...
  49.  compile if EVERSION >= 6
  50.    EA_comment 'This defines the DRAW command; it can be linked or executed directly.'
  51.  compile endif
  52. compile endif
  53.  
  54. compile if not defined(MAXCOL)  -- Predefined constant starting in 5.60
  55.    const MAXCOL = 255           -- If it's *not* predefined, we know it's 255.
  56. compile endif
  57.  
  58. compile if EVERSION < 4       -- For EOS2, Removed to DRAWKEY.E, to make this
  59.  compile if WANT_DRAW <> 1    -- separately compilable.
  60. def F6=
  61.    cursor_command
  62.    'draw'
  63.  compile endif
  64.  
  65. compile else
  66.  
  67. defmain     --  We want to start executing as soon as we're linked.
  68.    'draw' arg(1)
  69.  
  70. compile endif  -- EVERSION < 4
  71.  
  72. defc draw
  73.    universal boxtab1,boxtab2,boxtab3,boxtab4
  74.    universal g1,g2,g3,g4,g5,g6,g7,g8,g9,ga,gb
  75. compile if WANT_DBCS_SUPPORT
  76.    universal ondbcs
  77. compile endif
  78. compile if EVERSION >= 5
  79.    universal draw_starting_keyset
  80.  compile if EVERSION >= '5.21'
  81.    universal cursor_mode
  82.  compile endif
  83.    if .keyset = 'DRAW_KEYS' then
  84.       sayerror ALREADY_DRAWING__MSG
  85.       return
  86.    endif
  87. compile endif
  88.  
  89.    style=upcase(substr(arg(1),1,1))
  90.    if not length(style) or verify(style,"123456B/") then
  91. compile if WANT_DBCS_SUPPORT
  92.    if ondbcs then
  93.       sayerror DRAW_ARGS_DBCS__MSG
  94.    else
  95. compile endif
  96.       sayerror DRAW_ARGS__MSG
  97. compile if WANT_DBCS_SUPPORT
  98.    endif
  99. compile endif
  100. compile if EVERSION < 5
  101.       setcommand 'Draw',6,1
  102. compile endif
  103.       return
  104.    endif
  105.  
  106.    /* Pick characters from a packed string rather than if's, to save space. */
  107. compile if WANT_DBCS_SUPPORT
  108.    if ondbcs then
  109.       all6=\23\5\2\4\3\1\21\22\25\6\16'+|+++++++-+'\11\11\11\11\11\11\11\11\11\11\11\14\14\14\14\14\14\14\14\14\14\14\20\20\20\20\20\20\20\20\20\20\20\26\26\26\26\26\26\26\26\26\26\26
  110.    else
  111. compile endif
  112.    all6='┤│┐┘└┌┴┬├─┼╣║╗╝╚╔╩╦╠═╬+|+++++++-+███▀▀█▀██▀█╡│╕╛╘╒╧╤╞═╪╢║╖╜╙╓╨╥╟─╫'
  113. compile if WANT_DBCS_SUPPORT
  114.    endif
  115. compile endif
  116.    if style='/' then
  117. compile if EVERSION > 5
  118.       drawchars=copies(substr(arg(1),2,1),11)
  119. compile else
  120.       drawchars=substr('',1,11,substr(arg(1),2,1)) /* 11 copies of 2nd char */
  121. compile endif
  122.    elseif style='B' then
  123.       drawchars=substr('',1,11)
  124.    else
  125.       drawchars=substr(all6,11*style-10,11)
  126.    endif
  127. ;  LAM - changed assignments to a parse statement.  Saved 140 bytes of .ex file.
  128.    parse value drawchars with g1 +1 g2 +1 g3 +1 g4 +1 g5 +1 g6 +1 g7 +1 g8 +1 g9 +1 ga +1 gb
  129.    boxtab1=g1||g2||g4||g5||g7||g9||gb
  130.    boxtab2=g1||g2||g3||g6||g8||g9||gb
  131.    boxtab3=g1||ga||g4||g3||g7||g8||gb
  132.    boxtab4=g9||ga||g5||g6||g7||g8||gb
  133.  
  134. compile if EVERSION < 5
  135.    if command_state() then cursor_data endif
  136. compile endif
  137.    istate=insert_state();
  138.    if istate then insert_toggle
  139. compile if EVERSION >= '5.50'
  140.       call fixup_cursor()
  141. compile endif
  142.    endif
  143.  
  144. compile if EVERSION < 5
  145.    sayerror DRAW_PROMPT__MSG
  146.    loop
  147.       k=getkey()
  148.       /* Insert key toggles drawing; if insert is on, simply do the key. */
  149.       if insert_state() then executekey k; iterate; endif
  150.       if k=left then
  151.          draw_left()
  152.       elseif k=right then
  153.          draw_right()
  154.       elseif k=up then
  155.          draw_up()
  156.       elseif k=down then
  157.          draw_down()
  158.       /* Allow a few other keys for minor editing. */
  159.       elseif k=backspace or k=' ' or k=home or k=end or k=del or k=ins then
  160.          executekey k
  161.       else /* All other keys simply exit draw. */
  162.          leave
  163.       endif
  164.    endloop
  165.    if istate<>insert_state() then insert_toggle
  166. compile if EVERSION >= '5.50'
  167.       call fixup_cursor()
  168. compile endif
  169.    endif
  170.    sayerror DRAW_ENDED__MSG
  171. compile else
  172.    -- EPM:  The old DRAW used a getkey() loop.  We don't have getkey() in EPM.
  173.    -- The new way:  define a clear keyset of only the active keys.
  174.    draw_starting_keyset = upcase(.keyset)
  175.    keys draw_keys
  176.  compile if EVERSION >= '5.21'
  177.    cursor_mode = querycontrol(26)
  178.    'togglecontrol 26 0'
  179.  compile endif
  180.  
  181. -- Make it a BASE CLEAR keyset so the only keys that do anything are
  182. -- the ones we explicitly define.  Without the CLEAR, the standard ASCII keys
  183. -- like 'a'-'z' would be automatically included.
  184. defkeys draw_keys base clear
  185. def left    =
  186.    if insert_state() then
  187.       left
  188.    else
  189.       draw_left()
  190.    endif
  191. def right   =
  192.    if insert_state() then
  193.       right
  194.    else
  195.       draw_right()
  196.    endif
  197. def up      =
  198.    if insert_state() then
  199.       up
  200.    else
  201.       draw_up()
  202.    endif
  203. def down    =
  204.    if insert_state() then
  205.       down
  206.    else
  207.       draw_down()
  208.    endif
  209. def backspace  =
  210.    rubout
  211. def ins        =
  212.    insert_toggle
  213. compile if EVERSION >= '5.50'
  214.     call fixup_cursor()
  215. compile endif
  216. def space      =
  217.    keyin ' '
  218. def home       =
  219.    begin_line
  220. def end        =
  221.    end_line
  222. def del        =
  223.    delete_char
  224.  
  225. -- New in EPM.  This event (pseudo-key) is triggered whenever an otherwise
  226. -- undefined key is pressed.  We let any other key exit draw mode.
  227. -- (Any other key but mouse_move, that is.  It's not considered an "other key"
  228. -- because the mouse movement is too sensitive.
  229. -- This new wrinkle isn't really required.  We could define only one or two
  230. -- keys (like Esc) as exits and simply ignore all others.
  231. def otherkeys, F3 =   -- or def Esc
  232.    universal draw_starting_keyset
  233.  compile if EVERSION >= '5.21'
  234.    universal cursor_mode
  235.  compile endif
  236.    -- Whatever other key the user pressed, remember it so we can execute it.
  237.    k = lastkey()
  238.    -- Just in case the user doesn't have a select_edit_keys(), return to
  239.    -- the standard keyset to make sure we don't get stuck in draw_keys.
  240.    keys edit_keys
  241.    .keyset = draw_starting_keyset -- Return to whatever keyset had been there.
  242.  compile if EVERSION >= '5.21'
  243.    'togglecontrol 26' cursor_mode
  244.  compile endif
  245.    -- Execute the key the user pressed when he quit drawing.
  246.    sayerror DRAW_ENDED__MSG
  247.    if k<>esc & k<>c_I & k<>F3 then executekey k; endif   -- But assume Esc was just to stop DRAW.
  248.  
  249. -- End of EPM mods. ----------------------------------------------------------
  250. compile endif
  251.  
  252. defproc get_char
  253.    universal linepos,colpos,target
  254.    colpos=.col
  255.    linepos=.line
  256.    getline target
  257.    return substr(target,.col,1)
  258.  
  259. defproc draw_up      /* draw logic for the up key */
  260.    universal last,l,r,u,d,boxtab1,linepos,colpos
  261.    universal g1,g2,g3,g4,g5,g6,g7,g8,g9,ga,gb
  262.  
  263.    if last='d' then up
  264.    else c=get_char()
  265.       if last=='u' and c==' ' then keyin g2;left;up
  266.          elseif not verify(c,boxtab1) then up
  267.          elseif c==g3 then keyin g1;left;up
  268.          elseif c==g6 then keyin g9;left;up
  269.          elseif c==g8 then keyin gb;left;up
  270.          elseif c==ga then
  271.             call left_right()
  272.             if l=1 and r=1 then keyin g7 elseif l=1 then keyin g4 else keyin g5 endif
  273.             left;up
  274.          else call left_right()
  275.               if last='r' and l=1 then keyin g4
  276.                  elseif last='l' and r=1 then keyin g5
  277.                  else keyin g2
  278.                  endif
  279.               left;up
  280.          endif
  281.       if linepos=1 then insert; .col=colpos
  282.       else
  283.          c=get_char()
  284.          if c==g4 then keyin g1;left
  285.             elseif c==g5 then keyin g9;left
  286.             elseif c==g7 then keyin gb;left
  287.             elseif c==ga then
  288.                 call left_right()
  289.                 if l=1 and r=1 then keyin g8
  290.                    elseif l=1 then keyin g3
  291.                    else keyin g6
  292.                    endif
  293.                 left
  294.             endif
  295.          endif
  296.       endif
  297.    last='u'
  298.  
  299.  
  300. defproc draw_down /* Draw logic for the Down key */
  301.    universal last,l,r,u,d,boxtab2,linepos,colpos
  302.    universal g1,g2,g3,g4,g5,g6,g7,g8,g9,ga,gb
  303.  
  304.    if last='u' then down
  305.    else c=get_char()
  306.       if last=='d' and c==' ' then keyin g2;left;down
  307.          elseif not verify(c,boxtab2) then down
  308.          elseif c==g4 then keyin g1;left;down
  309.          elseif c==g5 then keyin g9;left;down
  310.          elseif c==g7 then keyin gb;left;down
  311.          elseif c==ga then
  312.             call left_right()
  313.             if l=1 and r=1 then keyin g8 elseif l=1 then keyin g3 else keyin g6 endif
  314.             left;down
  315.          else call left_right()
  316.               if last='r' and l=1 then keyin g3
  317.                  elseif last='l' and r=1 then keyin g6
  318.                  else keyin g2
  319.                  endif
  320.               left;down
  321.          endif
  322.       if linepos=.last then insert;.col=colpos
  323.       else
  324.          c=get_char()
  325.          if c==g3 then keyin g1;left
  326.             elseif c==g6 then keyin g9;left
  327.             elseif c==g8 then keyin gb;left
  328.             elseif c==ga then
  329.                 call left_right()
  330.                 if l=1 and r=1 then keyin g7
  331.                    elseif l=1 then keyin g4
  332.                    else keyin g5
  333.                    endif
  334.                 left
  335.             endif
  336.          endif
  337.       endif
  338.    last='d'
  339.  
  340.  
  341. defproc left_right   /* Check character left and right of cursor position */
  342.    universal last,l,r,boxtab3,boxtab4,lpos,rpos,target,colpos
  343.    universal g1,g2,g3,g4,g5,g6,g7,g8,g9,ga,gb
  344.  
  345.    lpos=colpos-1
  346.    if lpos > 0 then l = substr(target,lpos,1) else l = ' ' endif
  347.    rpos=colpos+1
  348.    if rpos < MAXCOL then r = substr(target,rpos,1) else r = ' ' endif
  349.    l=not verify(l,boxtab4) /*if verify(l,boxtab4)==0 then l=1 else l=0 endif*/
  350.    r=not verify(r,boxtab3) /*if verify(r,boxtab3)==0 then r=1 else r=0 endif*/
  351.  
  352.  
  353. defproc draw_left    /* Draw logic for the Left key */
  354.    universal last,u,d,boxtab3
  355.    universal g1,g2,g3,g4,g5,g6,g7,g8,g9,ga,gb
  356.  
  357.    if last=='r' then left
  358.    else
  359.       c=get_char()
  360. compile if WANT_DBCS_SUPPORT
  361.       if last=='l' and isdbcs(c) then keyin ga;keyin ga;left;left;left
  362.          elseif last=='l' and c==' ' then keyin ga;left;left
  363. compile else
  364.       if last=='l' and c==' ' then keyin ga;left;left
  365. compile endif
  366.          elseif not verify(c,boxtab3) then left
  367.          elseif c==g5 then keyin g7;left;left
  368.          elseif c==g6 then keyin g8;left;left
  369.          elseif c==g9 then keyin gb;left;left
  370.          elseif c==g2 then
  371.             call up_down()
  372.             if u=1 and d=1 then keyin g1 elseif u=1 then keyin g4 else keyin g3 endif
  373.             left;left
  374.          else call up_down()
  375.               if last='u' and d=1 then keyin g3
  376.                  elseif last='d' and u=1 then keyin g4
  377.                  else keyin ga
  378.                  endif
  379.               left;left
  380.       endif
  381.       c=get_char()
  382. compile if WANT_DBCS_SUPPORT
  383.       if isdbcs(c) then keyin ' ';c=get_char();endif
  384. compile endif
  385.       if c==g4 then keyin g7;left
  386.          elseif c==g2 then
  387.              call up_down()
  388.              if u=1 and d=1 then keyin g9
  389.                 elseif d=1 then keyin g6
  390.                 else keyin g5
  391.                 endif
  392.              left
  393.          elseif c==g3 then keyin g8;left
  394.          elseif c==g1 then keyin gb;left
  395.       endif
  396.    endif
  397.    last='l'
  398.  
  399.  
  400. defproc draw_right   /* Draw logic for the Right key */
  401.    universal last,u,d,boxtab4,colpos
  402.    universal g1,g2,g3,g4,g5,g6,g7,g8,g9,ga,gb
  403.  
  404.    if last=='l' then right
  405.    else c=get_char()
  406.       if last=='r' and c==' ' then
  407.         keyin ga
  408.       else
  409.          if not verify(c,boxtab4) then right
  410.          elseif c==g4 then keyin g7
  411.          elseif c==g3 then keyin g8
  412.          elseif c==g1 then keyin gb
  413.          elseif c==g2 then
  414.             call up_down()
  415.             if u=1 and d=1 then keyin g9 elseif d=1 then keyin g6 else keyin g5 endif
  416.          else call up_down()
  417.               if last='u' and d=1 then keyin g6
  418.                  elseif last='d' and u=1 then keyin g5
  419.                  else keyin ga
  420.                  endif
  421.          endif
  422.          call left_right()
  423.       endif
  424.       c=get_char()
  425.       if c==g5 then keyin g7;left
  426.          elseif c==g2 then
  427.              call up_down()
  428.              if u=1 and d=1 then keyin g1
  429.                 elseif u=1 then keyin g4
  430.                 else keyin g3
  431.                 endif
  432.              left
  433.          elseif c==g6 then keyin g8;left
  434.          elseif c==g9 then keyin gb;left
  435.       endif
  436.    endif
  437.    last='r'
  438.    if colpos = MAXCOL then left endif
  439.  
  440.  
  441. defproc up_down   /* Check character above and below cursor position */
  442.    universal u,d,boxtab1,boxtab2,linepos,colpos,dpos,upos,target
  443.    universal g1,g2,g3,g4,g5,g6,g7,g8,g9,ga,gb
  444.  
  445.    if linepos=1 then u=0
  446.       else
  447.          upos=linepos-1
  448.          getline target,upos
  449.          u = substr(target,colpos,1)
  450.          u=not verify(u,boxtab2)
  451.    endif
  452.    dpos=linepos+1
  453.    if dpos > .last then d=' '
  454.      else getline target,dpos
  455.           d = substr(target,colpos,1)
  456.      endif
  457.    d=not verify(d,boxtab1)
  458.    getline target,linepos
  459.  
  460.