home *** CD-ROM | disk | FTP | other *** search
/ Shareware Overload / ShartewareOverload.cdr / wp / bmacs.zip / DIR.M < prev    next >
Text File  |  1987-07-23  |  21KB  |  584 lines

  1. ;***
  2. ;***  Directory Handling Macro   dir.m
  3. ;***
  4. ;***  dir  produces a directory listing via DOS and allows files to be
  5. ;***  copied, deleted, edited, inserted into the current buffer, & renamed.
  6. ;***
  7. ;***  Prompts for an acceptable DOS directory command line, such as  b:
  8. ;***  or   b:\brief\macros\*.m.
  9. ;***  A second parameter (optional and not prompted) causes the display
  10. ;***  of file details such as date, time and attribute flags.
  11. ;***
  12. ;***  Written by Mark U. Edwards  11-17-84 v. 1.00  (dired.m)
  13. ;***  Rewritten by Joe R. Doupnik  12 August 1985 to version 2.0  (dir.m)
  14. ;***     Remove separate help menu; put help on window border.
  15. ;***     Show subdirectory names (files with <DIR> tag) and all file names.
  16. ;***     Get path name from DOS.
  17. ;***     Show DOS error messages whereever reasonable.
  18. ;***     Ensure that ESC does its expected thing (aborts a command).
  19. ;***     Add up/down paging of listing.
  20. ;***     Revise all external symbols (variables & macros) to d_xxx form.
  21. ;***     Clarify code and strengthen same; upgraded to BRIEF v1.2.
  22. ;***
  23. ;***     One work files, dir$.err, may be created
  24. ;***     in the default directory. Both are deleted upon macro completion.
  25. ;***     Only BRIEF intrinsic functions, and macros in this file, are used.
  26. ;***
  27. ;***     Updated by Harold Handelsman, April 12 1987 for Brief v2.0.
  28. ;***     Use the new directory searching functions in Brief.
  29. ;***     Enhanced the interface to allow multiple files to be added to the
  30. ;***     current list of edited files within the one invocation of the
  31. ;***     macro with the A (add file) macro.
  32. ;***     Added sizing of the directory display window for hardware 
  33. ;***     display size.
  34. ;***     Note: the current implementation of Brief does not allow the
  35. ;***     correct display of file size since only the lower word of
  36. ;***     the file size is returned.
  37. ;***
  38. ;***     Updated by Michael Shunfenthal
  39. ;***     Home and End cursor positioning added
  40. ;***     Window created of variable width depending upon presence of
  41. ;***     optional date, time, etc display parameter
  42. ;***     Message displays file specification.
  43.  
  44. (macro dir
  45.    (                    ; This is the only intended entry point!
  46.       (string  
  47.          d_path
  48.          temp)          
  49.  
  50.       (int
  51.          d_bottom       ; y-position of last file in directory list window
  52.          d_top
  53.          d_line
  54.          d_orig_buffer
  55.          d_dir_buf
  56.          d_misc         ; optional parameter
  57.          d_wsize)
  58.  
  59.       (global
  60.          d_bottom
  61.          d_top d_line
  62.          d_orig_buffer
  63.          d_dir_buf
  64.          d_path
  65.          d_misc
  66.          d_wsize)
  67.  
  68.       (if (get_parm 0 d_path "Directory spec: ")
  69.          (  
  70.             (message "Creating file list for %s" d_path)
  71.  
  72.             (if (! (get_parm 1 d_misc))      ; check for optional param.
  73.                (= d_misc 0)                  ; default it to false
  74.             )
  75.             (= d_orig_buffer (inq_buffer))   ; remember current buffer
  76.             (if (_dsetup)                    ; if setup failed
  77.                (
  78.                   (set_buffer d_orig_buffer) ; restore original
  79.                   (delete_buffer d_dir_buf)
  80.                )
  81.             ; else  all went ok
  82.                (
  83.                   (message "")
  84.                   (inq_screen_size d_wsize)
  85.                   (if d_misc 
  86.                      (create_window 11 (- d_wsize 4) 65 2 
  87.                      "<Esc> A=Add C=Copy D=Del E=Edit I=Ins R=Ren Home End")
  88.                      ; else
  89.                      (create_window 11 (- d_wsize 4) 45 2 
  90.                      "<Esc> Add Copy Del Ed Ins Ren ")
  91.                   )
  92.                   (attach_buffer d_dir_buf)
  93.                   (refresh)
  94.  
  95.                   (keyboard_push)            ; define active keys, save old
  96.                   (assign_to_key "<Esc>"   "d_exit")        ; ESC
  97.                   (assign_to_key "<Up>"    "d_up")          ; up arrow
  98.                   (assign_to_key "<Down>"  "d_down")        ; down arrow
  99.                   (assign_to_key "<PgUp>"  "d_pgup")        ; PgUp
  100.                   (assign_to_key "<PgDn>"  "d_pgdn")        ; PgDn
  101.                         (assign_to_key "%#71" "d_home")              ; Home
  102.                         (assign_to_key "%#79" "d_end")              ; End
  103.                   (assign_to_key "c"       "d_copy")        ; c
  104.                   (assign_to_key "C"       "d_copy")        ; C
  105.                   (assign_to_key "d"       "d_delete")      ; d
  106.                   (assign_to_key "D"       "d_delete")      ; D
  107.                   (assign_to_key "e"       "d_edit")        ; e
  108.                   (assign_to_key "E"       "d_edit")        ; E
  109.                   (assign_to_key "a"       "d_add_edit")    ; a
  110.                   (assign_to_key "A"       "d_add_edit")    ; A
  111.                   (assign_to_key "<Enter>" "d_edit")        ; <Enter>
  112.                   (assign_to_key "i"       "d_insert")      ; i
  113.                   (assign_to_key "I"       "d_insert")      ; I
  114.                   (assign_to_key "r"       "d_rename")      ; r
  115.                   (assign_to_key "R"       "d_rename")      ; R
  116.                   (process)                           
  117.                   (keyboard_pop)                ; restore old keyboard
  118.                   (message "")
  119.                )                                      ; end of ok clause
  120.             )                                         ; endif setup
  121.          )                                            ; end got a dir spec
  122.       )                                               ; endif get dir spec
  123. ;;;   (delete_macro "dir")       ; uncomment to remove ourselves when done
  124.    )
  125. )
  126.  
  127. (macro _dsetup
  128.    (                             ; validate listing, get path name from DOS.
  129.                                  ; DOS error messages are placed here & there
  130.       (string  temp)
  131.       (int fsize fdate ftime fattr)
  132.  
  133.       (= d_dir_buf (create_buffer "Directory" NULL 1))
  134.       (set_buffer d_dir_buf)
  135.       (insert "Directory for: ")                      ; insert heading
  136.       (insert d_path)
  137.       (insert "\n")
  138.       (inq_position d_top)                            ; save position of top
  139.       (++ d_top)
  140.  
  141.       (if (_d_path_fixup d_path temp)                 ; mess with the path
  142.          (return 1)
  143.       )
  144.       (file_pattern temp)                             ; set the search pattern
  145.  
  146.       (while (find_file temp fsize fdate ftime fattr) ; loop over all files
  147.          (
  148.             (= temp (+ "\n" temp))                    ; insert the name
  149.             (= temp (+ temp (substr "              " (+ (strlen temp) 1))))
  150.             (if (% (/ fattr 16) 2)                    ; is it a directory?
  151.                (+= temp "<Dir>  ")
  152.             ;else
  153.                (sprintf temp "%s%7u" temp fsize)      ; display size
  154.             )
  155.             (insert temp)
  156.             (if d_misc                                ; requested additional info?
  157.                (insert (_d_gen_misc fdate ftime fattr))
  158.             )
  159.          )
  160.       )
  161.       (inq_position d_bottom)                         ; save position of last line
  162.       (insert "\n")
  163.       (if (> d_top d_bottom)                          ; any files found ?
  164.          (
  165.             (error "No file(s).")
  166.             (return 1)
  167.          )
  168.       ;else
  169.          (
  170.             (move_abs (= d_line d_top) 1)             ; go to first line
  171.             (drop_anchor)                             ; highlight it
  172.             (end_of_line)
  173.             (return 0)                                ; return with no error
  174.          )
  175.       )
  176.    )
  177. )
  178.  
  179. ;***
  180. ;*** This macro will fix up a user specified path/filename and returns a
  181. ;*** complete path (including trailing backslash as well as a directory
  182. ;*** search string. Returns 0 if all is OK, 1 only if no file is found.
  183. ;*** Note: Currently, the routine will not generate a wildcard search string
  184. ;*** if no extension is specified.
  185. ;***
  186. ;*** e.g. Calling the macro with the first argument = "\brief\macros" will
  187. ;***      check if the path specified is a directory or a file and will
  188. ;***      return "\brief\macros\" in the first argument and in the second
  189. ;***      it will return "\brief\macros\*.*" if it was a directory. The 
  190. ;***      second string can be used to initiate a directory search.
  191. ;***
  192.  
  193. (macro _d_path_fixup
  194.    (
  195.       (int fattr)
  196.       (string str1 str2)
  197.  
  198.       (get_parm 0 str1)
  199.  
  200.       ;** Check if the specified path consists of just the driver specifier.
  201.  
  202.       (if (&& (== (substr str1 2 1) ":") (== (strlen str1) 2))
  203.          (
  204.  
  205.             ;** Just add the wildcards *.* to the directory search string.
  206.  
  207.             (put_parm 1 (+ str1 "*.*"))
  208.             (return 0)
  209.          )
  210.       )
  211.  
  212.       ;** Check if the path is null or there is a trailing backslash.
  213.  
  214.       (if (|| (== (substr str1 (strlen str1) 1) "\\") (== str1 ""))
  215.          (
  216.  
  217.             ;** Just add the wildcards *.* to the directory search string.
  218.  
  219.             (put_parm 1 (+ str1 "*.*"))
  220.             (return 0)
  221.          )
  222.       )
  223.  
  224.       ;** Check if there are NO wildcards in the path string.
  225.  
  226.       (if (! (search_string "[\\?\\*]" str1 1))
  227.          (
  228.             ;** Search for the file and check if it is a directory
  229.  
  230.             (file_pattern str1)
  231.             (if (! (find_file str2 NULL NULL NULL fattr))
  232.                (
  233.                   (error "No file(s).")
  234.                   (return 1)
  235.                )
  236.             )
  237.  
  238.             ;** Check if it is a directory
  239.  
  240.             (if (% (/ fattr 16) 2)
  241.                (
  242.  
  243.                   ;** Add the trailing backslash to the path and the
  244.                   ;** wildcards *.* to the search string.
  245.  
  246.                   (put_parm 0 (+ str1 "\\"))
  247.                   (put_parm 1 (+ str1 "\\*.*"))
  248.                   (return 0)
  249.                )
  250.             )
  251.          )
  252.       )
  253.  
  254.       ;** Check if there is a directory specified in the path string.
  255.  
  256.       (if (= fattr (rindex str1 "\\"))
  257.          (
  258.  
  259.             ;** Strip the trailing filename and return the just the directory
  260.             ;** as the path and the full path/filename as the search string.
  261.  
  262.             (put_parm 0 (substr str1 1 fattr))
  263.             (put_parm 1 str1)
  264.             (return 0)
  265.          )
  266.       ;else
  267.  
  268.          ;** No directory, check for a drive specification.
  269.  
  270.          (if (= fattr (rindex str1 ":"))
  271.             (
  272.                ;** Strip the trailing filename and return just the drive as
  273.                ;** the path and the full filename as the search string.
  274.  
  275.                (put_parm 0 (substr str1 1 fattr))
  276.                (put_parm 1 str1)
  277.                (return 0)
  278.             )
  279.          ;else
  280.             (
  281.                ;** No directory or drive specified. Return the null string for
  282.                ;** the path and the filename as the search string.
  283.  
  284.                (put_parm 0 "")
  285.                (put_parm 1 str1)
  286.                (return 0)
  287.             )
  288.          )
  289.       )
  290.    )
  291. )
  292.  
  293. (macro d_exit                          ; exit for this dir macro
  294.    (
  295.       (exit)                                       ; exit from process command
  296.       (delete_window)                              ; clean up buffers
  297.       (set_buffer d_orig_buffer)
  298.       (delete_buffer d_dir_buf)
  299.    )
  300. )
  301.  
  302. (macro d_up                            ; line up
  303.    (
  304.       (message "")
  305.       (raise_anchor)
  306.       (if (< (-- d_line) d_top)                    ; first file is on line 5
  307.          (
  308.             (= d_line d_top)
  309.             (top_of_buffer)
  310.             (refresh)
  311.          )
  312.       )                                            ; endif
  313.       (move_abs d_line 1)
  314.       (drop_anchor)                                ; display choice bar
  315.       (end_of_line)
  316.    )
  317. )
  318.  
  319. (macro d_down                          ; line down
  320.    (
  321.       (message "")
  322.       (raise_anchor)
  323.       (if (> (++ d_line) d_bottom)                 ; last file is on line d_bottom
  324.          (
  325.             (= d_line d_bottom)
  326.             (end_of_buffer)
  327.             (refresh)
  328.          )
  329.       )                                            ; endif
  330.       (move_abs d_line 1)
  331.       (drop_anchor)                                ; display choice bar
  332.       (end_of_line)
  333.    )
  334. )
  335.  
  336. (macro d_pgup                          ; page up
  337.    (
  338.       (-= d_line d_wsize)
  339.       (d_up)
  340.    )
  341. )
  342.  
  343. (macro d_pgdn                          ; page down
  344.    (
  345.       (+= d_line d_wsize)
  346.       (d_down)
  347.    )
  348. )
  349.  
  350.  
  351. (macro d_home                                                        ;go to first file
  352.     (
  353.         (= d_line d_top)                                            ;force top of buffer
  354.         (d_up)                                                        ;line up
  355.     )
  356. )
  357.  
  358. (macro d_end                                                        ;go to last file
  359.     (
  360.         (= d_line d_bottom)                                        ;force end of buffer
  361.         (d_down)                                                        ;line down
  362.     )
  363. )
  364.  
  365. (macro d_edit                          ; edit the file and exit
  366.    (
  367.       (string temp)
  368.  
  369.       (= temp (_dfilename))
  370.       (d_exit)
  371.       (edit_file temp)
  372.    )
  373. )
  374.  
  375. (macro d_add_edit                      ; edit the file, but remain
  376.    (
  377.       (string temp)
  378.  
  379.       (= temp (_dfilename))
  380.       (d_down)
  381.       (edit_file temp)
  382.       (message "Added file: %s" temp)
  383.       (set_buffer d_dir_buf)
  384.       (attach_buffer d_dir_buf)
  385.    )
  386. )
  387.  
  388. (macro d_insert                        ; insert file into current buffer
  389.    (
  390.       (string temp)
  391.  
  392.       (= temp (_dfilename))
  393.       (d_exit)
  394.       (read_file temp)
  395.    )
  396. )
  397.  
  398. (macro d_delete                        ; delete selected file
  399.    (
  400.       (int  old_line  old_col  char)
  401.  
  402.       (inq_position old_line old_col)
  403.       (keyboard_flush)
  404.       (insert " - del? (y/n)")                        ; ask for permission
  405.       (refresh)                                       ; show the tag line
  406.       (while (== (= char (read_char)) -1))            ; read a keystroke
  407.       (move_abs old_line old_col)                     ; remove the tag line
  408.       (delete_to_eol)
  409.       (%= char 256)                                   ; remove scan code
  410.       (if (|| (== char 'y') (== char 'Y'))            ; then 'y' or 'Y'
  411.          (
  412.             (if (> (del (_dfilename)) 0)
  413.                (                                      ; delete succeeded
  414.                   (delete_line)
  415.                   (if (> old_line (-- d_bottom))      ; below new bottom?
  416.                      (if (< d_bottom d_top)           ; deleted last file?
  417.                         (d_exit)                      ; yes, exit
  418.                      ; else
  419.                         (d_up)                        ; bump choice bar
  420.                      )                                ; endif no more files
  421.                   )                                   ; endif below new bottom
  422.                )
  423.                ; else
  424.                   (error "Can't delete that file.")   ; delete failed
  425.             )                                         ; endif
  426.          )
  427.       )                                               ; endif yes
  428.    )
  429. )
  430.  
  431. (macro d_rename
  432.    (                                   ; rename an existing file.
  433.                                           ; Note: trying to rename a directory
  434.                                           ; can produce unwanted side effects
  435.    (int   dot)
  436.       (string  path  new_name  new_2)
  437.  
  438.       (if (get_parm 0 new_name "Rename to: ")
  439.          (
  440.             (if (strlen new_name)                        ; new name given? 
  441.                (                                         ; yes
  442.                   (= new_name (_dupcase new_name))
  443.  
  444.                   (message "%s" (+ "REN " (+ (_dfilename) (+ " " new_name))))
  445.                   (getwd NULL path)                      ; avoid BRIEF|DOS bug
  446.                   (dos (+ "REN >&$dir$.err " (+ (_dfilename) (+ " " new_name))))
  447.                   (cd  path)                             ; bug remover #2
  448.  
  449.                   (if (! (_derror))                      ; did it work?
  450.                      (                                   ; yes
  451.                         (move_abs 0 12)
  452.                         (delete_block)                   ; clear name field
  453.                         (= new_2 (+ (upper new_name)
  454.                            (substr "            " (+ (strlen new_name) 1))))
  455.                         (drop_anchor)                    ; make choice bar
  456.                         (insert new_2)                   ; insert new name
  457.                         (end_of_line)
  458.                         (refresh)
  459.                      )                                   ; end no error clause
  460.                   )                                      ; endif no error
  461.                )
  462.             ; else
  463.                (message "Command terminated.")           ; no new name
  464.             )                                            ; endif new name given
  465.          )                                               ; end parm given clause
  466.       )                                                  ; endif get_parm
  467.    )
  468. )
  469.  
  470. (macro d_copy                          ; copy chosen file to another file
  471.    (
  472.       (string  dest_name)
  473.  
  474.       (if (get_parm 0 dest_name "Copy to: ")
  475.          (
  476.             (if  (strlen dest_name)                      ; destination given?
  477.                (
  478.                   (= dest_name (_dupcase dest_name))
  479.                   (message "%s" (+ "COPY " (+ (_dfilename)
  480.                                                    (+ " " dest_name))))
  481.                   (dos (+ "COPY >&$dir$.err "
  482.                                  (+ (_dfilename) (+ " " dest_name))))
  483.                   (_derror)                              ; show status
  484.                )
  485.                ; else
  486.                   (error "No destination - copy not done.")
  487.             )                                            ; endif file ok
  488.          )                                               ; end do a copy
  489.       )                                                  ; endif do a copy
  490.    )
  491. )
  492.  
  493. (macro _d_gen_misc
  494.    (
  495.       (int fdate ftime fattr i j)
  496.       (string temp)
  497.  
  498.       (get_parm 0 fdate)
  499.       (get_parm 1 ftime)
  500.       (get_parm 2 fattr)
  501.  
  502.       (= i (/ fdate 32))
  503.       (= j (+ 80 (/ i 16)))
  504.       (%= i 16)
  505.       (sprintf temp "  %2d/%02d/%2d " i (% fdate 32) j)
  506.       (= j (/ ftime 32))
  507.       (if (< j 0)
  508.          (+= j 2048)
  509.       )
  510.       (= i (/ j 64))
  511.       (%= j 64)
  512.       (sprintf temp "%s%2d:%02d " temp i j)
  513.       (if (% (/ fattr 32) 2)
  514.          (+= temp "A")
  515.       ;else
  516.          (+= temp " ")
  517.       )
  518.       (if (% fattr 2)
  519.          (+= temp "R")
  520.       ;else
  521.          (+= temp " ")
  522.       )
  523.       (if (% (/ fattr 2) 2)
  524.          (+= temp "H")
  525.       ;else
  526.          (+= temp " ")
  527.       )
  528.       (if (% (/ fattr 4) 2)
  529.          (+= temp "S")
  530.       ;else
  531.          (+= temp " ")
  532.       )
  533.    )
  534. )
  535.  
  536. (macro _dfilename
  537.    (                                   ; get filename from display list
  538.       (string temp)
  539.       
  540.       (beginning_of_line)
  541.       (= temp (read 12))                              ; read filename + tag
  542.       (end_of_line)                                   ; restore cursor position
  543.       (returns (trim (+ d_path temp)))                ; prepend path name
  544.    )
  545. )
  546.  
  547. (macro _derror
  548.    (                          ; get and display dos command's message line. 
  549.                               ; Note: DOS error messages begin with ascii
  550.                               ; text in column 1, informational messages
  551.                               ; start with spaces or are completely null.
  552.    (int  _derror_buf)
  553.       (string temp)
  554.  
  555.       (= _derror_buf (create_buffer "error" "$dir$.err" 1)) ; make a buffer
  556.       (set_buffer _derror_buf)                           ; look in it
  557.       (end_of_buffer)                                    ; add two blank lines
  558.       (insert " \n \n")                                  ; in case file is empty
  559.       (move_abs 2 1)                                     ; message coordinates
  560.       (= temp (read))
  561.       (= temp (substr temp 1 (- (strlen temp) 1)))       ; trim trailing c/r
  562.       (set_buffer d_dir_buf)                             ; restore popup
  563.       (delete_buffer _derror_buf)                        ; remove temp buf
  564.       (del "$dir$.err")                                  ; delete work file
  565.       (message "%s" temp)                                ; show DOS message
  566.       (if (> (substr temp 1 1) " ")                      ; text means error
  567.          (returns 1)                                     ; say DOS error
  568.       ; else
  569.          (returns 0)                                     ; DOS success msg
  570.       )                                                  ; endif
  571.    )
  572. )
  573.  
  574. (macro _dupcase
  575.    (                             ; convert string old to upper case string new
  576.       (string  old)
  577.  
  578.       (get_parm 0 old)
  579.       (return (upper old))
  580.    )
  581. )
  582.  
  583.                                                                                                   
  584.