// // XLIST-MC.VDM Ch. Ziemski 28.04.2002 // 09.06.2002 some improvements for Shft-F12 etc. // changes in documentation and help // 19.03.2003 added a html column for last modified date // 27.03.2003 colorize the most recent modification date, etc. // 29.03.2003 changed the filename from "!contents" to "contents" // 24.08.2003 fix: date format // 10.04.2004 try to fix: filenames with more than one extension (or so) // 23.05.2004 fix: Date() for 6.12 // // to do: exclude COMPDIR from last-mod-date // Tested under Win2000 only yet. // // // -- Inline documentation -- (could be displayed with Shft-F1) // // *** XLIST-MC.VDM - Xtended List Maintaining and Converting (to HTML) *** // // Creates a list of files from a directory listing (DIR) and merges it with // a (possibly) already existing definition file. // Converts the definition file into a HTML document consisting of a bunch of // tables - one table for each category. // // This definition file is like a table with one line for every file. Each line // describes one file with category, title, short description and filename. // // If there are files in the directory but not in the definition file they will // be appended there. // If there are files in the definition file but not (longer) really existing // in the directory they will be marked as "inactive" in the definition file. // // Editing the definition file by adding more descriptions or change existing // ones and restarting the macro will sort the entries again by category and // reformat it to line up the columns. // So you can maintain the definition file part for part and you will have a // table of contents this way. // // ---------------------------------------------------------------------------- // // Shft-F1 : show this help // // F11 : convert the list to HTML again // Ctrl-F11 : restart the macro (reloads, resorts, reformats, converts to HTML) // // F12 : Open the file specified by the cursor line in another VEDIT buffer // (and close it again from there) // // Shft-F12 : add the appropriate column deviders in the current line // - looks for a previous line with deviders as template: // if no one found: inserts three example deviders // - if at end-of-file: does nothing due to no existing entry in line // - if a devider would overwrite something but a space: // ignores that position (does nothing) // // Ctrl-F12 : like Shift-F12, but jump down a line then for following additions // // ------------------------------------------------------------------------------ // // Here is an example: // -------------------- // // *TITLE: Example list of files // * // *INTRO: This is an example definition file for CONV-LIST.VDM // *INTRO: // * // * filename category title short description // *--------------------|--------------------|-----------------------------------------|-------------------- // *** // COMPDIR.VDM | enhanced originals | | // Checkparen.vdm | Programming | Parenthesis checker | // chkgotos.vdm | Programming | Goto checker | checks gotos // adel2.vdm | Programming | Auto backspace | Auto backspace // book2adr.vdm | Converter | Converts Opera's (?) bookmarks to HTML | // // // This little definition file would be converted into a HTML page with the // defined title line and with a short introduction text. // Then there will follow 3 tables for the three categories. // // // I've developed this macro to maintain a part of my website, where I'm // listing many VEDIT macros. // (As side effect I'm forced to document the macros a bit more... :-) ) // // The site is still under construction but if you want to have a look // (to see this macro at work): // // http://home.t-online.de/home/Christian.Ziemski/vedit // // // // // Since it's a work in progress this documentation is to be improved.... // // //---------------------------------------------------------------------------------------- // // The macro uses the following numerical and text registers. // They are NOT restored since there is no real "exiting" this macro! // // # chars_matched // #87 buffer num for long directory list // #88 Cur_Line (for F12) // #89 Cur_Col (for F12) // #90 size of $100 (this macro itself), for restarting with F12 // #91 buffer num for DIR // #92 buffer num for definition file // #93 flag, whether a "|" was found // #94 flag for 1st run of HTML-generation (for group/category switch) // #95 ASCII value of character for inactive entries // #96 BufNum of last loaded file +1000 (for F11) // #97 longest filename + 2 // #98 flag for loaded html file // #99 temp // // #103 temp // #104 temp // #105 temp // #106 temp // // $87 last modified date // $88 #95 as text // $89 "[no category]" // $90 name of definition file // $91 HTML-Header // $92 HTML-table-header // $93 HTML-table-row // $94 HTML-table-end // $95 HTML-footer // $96 header lines of the definition file (beginning with leading *) // $97 title string (from header line of definition file beginning with *TITLE:) // $98 HTML-intro (from header lines of definition file beginning with *INTRO:) // $99 last category, used for group switch // // $103 temp // $104 temp // $105 temp // $106 temp // $107 temp // //---------------------------------------------------------------------------------------- // // ToDo: // Test with Win9x etc.; Test with US-Windows // check the file-date extraction! spaces in filenames could be problematic! // check the VM() problem at end of run // HTML-Tags aus txt-datei erzeugen, z.B. für Umlaute, <, > ... // chdir/Get_Filename bug!? => Ted // more docu // Code optimizing // Reg_Push/pop // File_Delete("|(VEDIT_TEMP)\xlist-mc.d*") ? // //======================================================================================== // //------- Some user changeable configuration options: ----------------------------------- #98=0 // 1 = let the html-file loaded after generating it // 0 = if you want to have it closed #95=247 // ASCII value of character for inactive entries Reg_Set(89, "[no category]") // title for categories without explicit name Reg_Set(90, "contents") // name of the definition file //----------------------------------------------------------- // Set the HTML-templates; used for the HTML generation later // // The key fields @HTMLTITLE@, @INTRO@, @CATEGORY@, @TITLE@, @DESCRIPTION@, @NAME@ // and @DATE@ will be replaced with the current values. // Reg_Set(91, ` @HTMLTITLE@

Last modified: @DATE@

@INTRO@ `) Reg_Set(92, ' ') Reg_Set(93, ' ') Reg_Set(94, '
  @CATEGORY@ Description Macro name Last mod.
@TITLE@ @DESCRIPTION@ @NAME@
@FILEDATE@

') Reg_Set(95, 'Last modified: @DATE@

') //======================================================================================== Key_Add(`Shft-F1`, `[VISUAL EXIT] if((Reg_Size(100)==#90)&&(Buf_Num==#92)){ CALL(100, "HELP") } `, OK) Key_Add('F11', '[VISUAL EXIT] if((Reg_Size(100)==#90)&&(Buf_Num==#92)){ #88=Cur_Line #89=Cur_Col CALL(100, "CONV2HTML") Goto_Line(#88) Goto_Col(#89) }', OK) Key_Add('Ctrl-F11', '[VISUAL EXIT] if((Reg_Size(100)==#90)&&(Buf_Num==#92)){ #88=Cur_Line #89=Cur_Col CALL(100) Goto_Line(#88) Goto_Col(#89) }', OK) Key_Add(`F12`, `[VISUAL EXIT] if( Reg_Size(100)==#90) { CALL(100, "LOADFILE") }`, OK) Key_Add(`Shft-F12`, `[VISUAL EXIT] if((Reg_Size(100)==#90)&&(Buf_Num==#92)){ CALL(100, "FILLPIPES") }`, OK) Key_Add(`Ctrl-F12`, `[VISUAL EXIT] if((Reg_Size(100)==#90)&&(Buf_Num==#92)){ CALL(100, "FILLPIPES") Line(1, NOERR) }`, OK) //--------------------------------------------------------------------------------------- Out_Reg(88) // put ASCII value of character for inactive entries as string into $88 Type_Char(#95) Out_Reg(CLEAR) #90=Reg_Size(100) // for checking if $100 is unchanged (for F-keys) Reg_Empty(87) // holds the last modified date (youngest macro) // if no definition file found in the current dir: let the user choose a directory Chdir(PATH_ONLY) if(! File_Exist("|@(90).txt")){ #103=Dialog_Input_1(104,"`CONV-LIST.VDM: Info`, `There is no definition file in the current directory. \nPlease choose a directory in the following dialog box \nby 'opening' a file in the desired directory; \nor [Cancel].`,`[&Ok]`,`[&Cancel]`", APP+CENTER,0,0) if((#103==0) || (#103==2)){ return } #103=Buf_Num if(Get_Filename(103,"|(CUR_DIR)\*.*")==0){ // bug? pfad wird nicht immer beachtet!?!?! return // o.k.??? } Buf_Switch(Buf_Free(EXTRA)) Reg_Ins(103) Search("\",REVERSE+NOERR) Reg_Copy_Block(104, 0, Cur_Pos) Buf_Quit(OK) Chdir(@104) } // ----- // get the list of files in the directory inclusive date/time System("DIR *.* > |(VEDIT_TEMP)\xlist-mc.dir",DOS+SIMPLE) Buf_Switch(#87=Buf_Free) File_Open("|(VEDIT_TEMP)\xlist-mc.dir") // get the list of files in the directory Buf_Switch(#91=Buf_Free) Out_Ins() Dir("*.*",NOMSG) Out_Ins(CLEAR) Replace("|W|>","",BEGIN+ALL+NOERR) // delete trailing whitespace Replace("|<..|N","",BEGIN+ALL+NOERR) // delete entry of parent directory Replace("|<|*\|N","",BEGIN+ALL+NOERR) // delete entry of subdirectories Replace("|<|@(90)|Y|N", "", BEGIN+ALL+NOERR) // delete entries of definition file itself Replace("|<|*.bak|N","",BEGIN+ALL+NOERR) // delete entries of *.bak files File_Save_As("|(VEDIT_TEMP)\xlist-mc.tmp", OK+NOMSG) // ----- // open the definition file #99=File_Check("|@(90).txt") if (#99 == -1){ Buf_Switch(#92=Buf_Free) File_Open("|@(90).txt") }else{ Buf_Switch(#99) #92=Buf_Num } // remove (and save) the header lines, some formatting BoF Reg_Empty(96) while(Match("|<*")==0){ if(Match("|<**")==0){ // to find the end of the header if the first entry is commented out Reg_Copy(96, 1, APPEND) Del_Line(1) break } Reg_Copy(96, 1, APPEND) Del_Line(1) } Replace("|W|>","",BEGIN+ALL+NOERR) // delete trailing whitespace Replace("|<|X","",BEGIN+ALL+NOERR) // delete empty lines Replace("|<|@(90)|Y|N", "", BEGIN+ALL+NOERR) // delete entries of definition file itself BoF // ----- // check all files in the directory if they are in the definition file too Buf_Switch(#91) BoF while(! At_EoF){ Reg_Copy_Block(103, Cur_Pos, EoL_Pos) // current filename Buf_Switch(#92) Search("|<|@(103)|X", BEGIN+NOERR) // is the file as active entry in definition file? if(!EM){ // if yes Char(Chars_Matched) if(Search("|<|@(103)|X", BEGIN+ALL+NOERR) > 1){ // search for active doublettes Win_Clear() Message("\nAttention: There are some files with more than one active entry!\n") Message("----------------------------------------------------------------\n\n") } while(Search("|<|@(103)|X", BEGIN+ALL+NOERR) > 1){ // search for active doublettes Message(">> ") Reg_Type(103) Message(` << has more than one active entry. Double is set to inactive.\n`) BoL Ins_Char(#95) Ins_Text(" [2x] ") } }else{ // if not found as active entry Search("|<|@(88)|[|W]|@(103)|X", BEGIN+NOERR) // check if it's an inactive entry if(!EM){ // if yes Del_Char(1) // switch from inactive to active state Replace("|<|W", "", NOERR) }else{ // if no Search("|<*|*|@(103)|X", BEGIN+NOERR) // check if it's an commented out entry if(EM){ // if no Search("|<|@(88)|[|W]*|*|@(103)|X", BEGIN+NOERR) // check if it's an inactive commented out entry if(EM){ // if absolutely not there => append it there EoF Reg_Ins(103) Ins_Newline(1) } } } } Buf_Switch(#91) Line(1, NOERR) } BoF // ----- // check all files in the definition file if they are existing in file list; if not mark the entry as inaktive Buf_Switch(#92) BoF while(! At_EoF){ #103=Cur_Pos if(Cur_Char != #95){ // if not an inactive entry line Search("|{||,|N}", NOERR) Search("|!|W", REVERSE+ADVANCE+NOERR) if(EM || At_BoL){ // if no filename in that line (maybe a faulty leading "|") BoL Ins_Char(#95) // mark line as inactive Ins_Text(" ") }else{ Reg_Copy_Block(103, #103, Cur_Pos) // current filename Buf_Switch(#91) Search("|@(103)|X", BEGIN+NOERR) // search this one in directory list Buf_Switch(#92) if(EM){ // if file not existing in directory list BoL Ins_Char(#95) // mark it as inactive Ins_Text(" ") } } } Line(1, NOERR) } BoF // ----- // reformat and sort the definition file Buf_Switch(#92) BoF // delete all leading and trailing spaces in every column Replace("\s+\|\s*", " \| ", BEGIN+ALL+NOERR+REGEXP) // insert a space around the pipes where necessary (should be optimzed!) Replace("{[^\s]}\|", "\1 \|", BEGIN+ALL+NOERR+REGEXP) Replace("\|{[^\s]}", "\| \1", BEGIN+ALL+NOERR+REGEXP) // search the longest filename => in #97 (+ 2) BoF #97=0 // longest name #93=0 // flag if at least one "|" found while(! At_EoF){ Search_Block("|", Cur_Pos, EoL_Pos, NOERR) if(!EM){ Search("|!|W", REVERSE+ADVANCE) #93=1 // at least one | found }else{ EoL } if((Cur_Col + 2) > #97){ #97=Cur_Col + 2 } Line(1, NOERR) } // line up the trailing infos (if any) BoF while(! At_EoF){ Search_Block("|", Cur_Pos, EoL_Pos, NOERR) if(!EM){ if(Cur_Col < #97){ Ins_Indent(#97) }else{ Del_Char(#97-Cur_Col) } } Line(1, NOERR) } BoF if(#93){ // if at least one "|" existing // move all line containing a | to top Sort_Merge("#97,#97+2",0,File_Size, REVERSE) EoF Search("||", REVERSE) Line(1) // and sort them by category and name Sort_Merge("#97,#97+20;1,#97",0,Cur_Pos) // (it would be nice to be able to sort entries without category to the end, but // unfortunately that's not so easy since SPACE < ABC ... // And using another collate table seems to be to complicated here.) } // sort the rest by name if(! At_EoF){ // to avoid crash Sort_Merge("1,#97",Cur_Pos, File_Size) } // more beautifying (the 3rd and 4th column) for(#105=2; #105<4; #105++){ #104=0 BoF while(! At_EoF){ #103=Search_Block("|", Cur_Pos, EoL_Pos, ALL+NOERR+ERRBREAK) if(#103 >= #105){ BoL Search_Block("|", Cur_Pos, EoL_Pos, COUNT, #105) // jump to the 2nd resp. 3rd "|" if(Cur_Col > #104){ #104=Cur_Col } }else{ EoL if(Cur_Col > #104){ #104=Cur_Col + 1 } } Line(1, NOERR) } BoF while(! At_EoF){ #103=Search_Block("|", Cur_Pos, EoL_Pos, ALL+NOERR+ERRBREAK) if(#103 >= #105){ BoL Search_Block("|", Cur_Pos, EoL_Pos, COUNT, #105) // jump to the 2nd resp. 3rd "|" if(Cur_Col < #104){ Ins_Char(32, COUNT, #104-Cur_Col) } } Line(1, NOERR) } } // get all inactive enties and put them to the end of file BoF Reg_Empty(104) while(! At_EoF){ Search("|<|@(88) ", NOERR) // search inactive entries if(EM){ break }else{ Reg_Copy(104, 1, APPEND) Del_Line(1) } } EoF Reg_Ins(104) // insert header again BoF Reg_Ins(96) File_Save(NOMSG) // --------------------------------------------------------- :CONV2HTML: // generating the HTML code Buf_Switch(#91) Buf_Quit(OK) #99=File_Check("|@(90).htm") // is the html-file already loaded (from a previous run or so)? if (#99 == -1){ // if not: Buf_Switch(#91) // use the used buffer #91 for that File_Save_As("|@(90).htm",OK+NOMSG) // #98=0 }else{ Buf_Switch(#99) // if yes: #98=1 #91=Buf_Num // use it, but clear all lines BoF Del_Line(ALL) } // check header of definition file Buf_Switch(#92) Replace("|<|X","",BEGIN+ALL+NOERR) // delete empty lines BoF Reg_Empty(97) // HTML-title Reg_Empty(98) // introduction lines while(Match("|<*")==0){ if(Match("|<*TITLE:")==0){ Char(Chars_Matched) Reg_Copy_Block(97, Cur_Pos, EoL_Pos) } if(Match("|<*INTRO:")==0){ Char(Chars_Matched) Reg_Copy(98,1, APPEND) Reg_Set(98, "
", APPEND) } Line(1, NOERR) } if(Reg_Size(97)==0){ Reg_Set(97, "no title") } // build HTML Buf_Switch(#91) BoF Reg_Ins(91, BEGIN) // HTML-header Replace("@HTMLTITLE@", @97, CASE+NOERR) Replace("@INTRO@", "", CASE+NOERR) if(!EM){ Reg_Ins(98) } EoF Reg_Empty(99) // last category Buf_Switch(#92) #94=1 // flag for 1st run while(! At_EoF){ // Format der Datei: // // * header or comments // name | category | title | short description // ÷ inactive entries BoL if((Cur_Char == #95) || (Cur_Char == '*')){ // if comment or inactive entry Line(1, NOERR) Continue } Reg_Empty(103) // filename Reg_Empty(104) // category Reg_Empty(105) // title Reg_Empty(106) // descr #103=Cur_Pos Search_Block("|", Cur_Pos, EoL_Pos, NOERR+ADVANCE) if(! EM){ // if fields with | found #103=Cur_Pos Char(-1) Search("|!|W", REVERSE+ADVANCE) Reg_Copy_Block(103, BoL_Pos, Cur_Pos) // name Goto_Pos(#103) Search_Block("|", Cur_Pos, EoL_Pos, NOERR+ADVANCE) if(!EM){ // after the category there is more... Reg_Copy_Block(104, #103, Cur_Pos-2) // save category #103=Cur_Pos Search_Block("|", Cur_Pos, EoL_Pos, NOERR+ADVANCE) if(!EM){ // after the title there is more... Reg_Copy_Block(105, #103, Cur_Pos-2) // save title Reg_Copy_Block(106, Cur_Pos, EoL_Pos) }else{ // only title left Reg_Copy_Block(105, #103, EoL_Pos) } }else{ // only category found Reg_Copy_Block(104, #103, EoL_Pos) } }else{ // only name found Reg_Copy_Block(103, #103, EoL_Pos) } // remove leading and trailing spaces from category, title and description Buf_Switch(Buf_Free(EXTRA)) Reg_Ins(104) Replace("|<|W","",BEGIN+ALL+NOERR) Replace("|W|>","",BEGIN+ALL+NOERR) Reg_Copy_Block(104, 0, File_Size, DELETE) Reg_Ins(105) Replace("|<|W","",BEGIN+ALL+NOERR) Replace("|W|>","",BEGIN+ALL+NOERR) Reg_Copy_Block(105, 0, File_Size, DELETE) Reg_Ins(106) Replace("|<|W","",BEGIN+ALL+NOERR) Replace("|W|>","",BEGIN+ALL+NOERR) Reg_Copy_Block(106, 0, File_Size, DELETE) Buf_Quit(OK) Buf_Switch(#92) // switch back if(Reg_Size(104)==0){ Reg_Set(104, @89) // category = "[no category]" } if(Reg_Size(105)==0){ Reg_Set(105, "...") // title } if(Reg_Size(106)==0){ Reg_Set(106, "...") // description } // insert the results in the other buffer Buf_Switch(#91) if(Reg_Compare(99, @(104)) != 0){ // if category has changed if(#94==1){ // not on the very first run #94++ }else{ Reg_Ins(94) // insert HTML-table-end } Reg_Set(99, @104) // remember this, the last used category // create new table with header Reg_Ins(92, BEGIN) // HTML table header template Replace("@CATEGORY@", @99, CASE) EoF } Reg_Ins(93, BEGIN) // HTML table row template Replace("@TITLE@", @105, CASE) Replace("@DESCRIPTION@", "", CASE) if(!EM){ Reg_Ins(106) } Replace("@NAME@", @103, ALL+CASE) // get date of last modification of this file and add it here Buf_Switch(#87) // long dir list Reg_Empty(107) Search("|{ ,|<}|@(103)|X", BEGIN+NOERR) // fix/pay attention!: longer filenames // restrict to real filenames!! // spaces in filenames!! NT/W9x differences?! if (!EM) { BoL // (date in US and European format: 10/13/2002 or 13.10.2002) // To do: test with international! and in Win9x/XP // more testing here! Search_Block("|D|D|{.,/}|D|D|{.,/}|D|D|[|D|D]", Cur_Pos, EoL_Pos, NOERR) #86=Chars_Matched // if (! EM) { if (Match("|D|D/")==0) { Replace_Block("{[0-9]+}/{[0-9]+}/{[0-9]+}{[^0-9]}", "\3-\1-\2\4", Cur_Pos, EoL_Pos, REGEXP) } if (Match("|D|D.")==0) { Replace_Block("{[0-9]+}\.{[0-9]+}\.{[0-9]+}{[^0-9]}", "\3-\2-\1\4", Cur_Pos, EoL_Pos, REGEXP) } // } Reg_Copy_Block(107, Cur_Pos-#86-1, Cur_Pos-1) if (Reg_Compare(107, @(87)) == 1) { // if this date is greater(younger) than $87 Reg_Set(87, @107) // => save the current one } } Buf_Switch(#91) Replace("@FILEDATE@", "|@(107)", ALL+CASE) EoF Buf_Switch(#92) Line(1, NOERR) } Buf_Switch(#91) EoF if(#94 <= 2){ // Reg_Ins(94) // insert HTML-table-end } Reg_Ins(95, BEGIN) // HTML-footer // Buf_Switch(Buf_Free(EXTRA)) // Out_Ins() // get the current date // Date(NOMSG+NOCR) // bug: mm-dd-yyyy is wrong format! must be yyyy-mm-dd // Out_Ins(CLEAR) // Reg_Copy_Block(103, 6, 10) // Reg_Set(103, "-", APPEND) // Reg_Copy_Block(103, 0, 5, APPEND) // Buf_Quit(OK) // new with 6.12 Out_Reg(103) Date(REVERSE+NOMSG+NOCR) Out_Reg(CLEAR) Replace("@DATE@", @103, BEGIN+CASE+ALL+NOERR) // with "last modification" note // mark the youngest ones with another color Replace("@LASTMODCOLOR@{.*\@(87)}", "BGCOLOR=#00FF00\1", BEGIN+CASE+ALL+REGEXP) Replace("@LASTMODCOLOR@", "", BEGIN+CASE+ALL+NOERR) // and delete the unused color variables File_Save(NOMSG) BoF if(#98==0){ // if html-file wasn't loaded before the run (and not set to remain loaded) Buf_Quit(OK) // close it now } Buf_Switch(#87) // long dir list Buf_Quit(OK) Buf_Switch(#92) BoF // Visual_Macro(NOMSG) // Doesn't work: Due to the output of CHDIR above there // // is always a prompt: "Return to visal mode" :-( Win_Clear // Workaround for that problem Update() // return //========================================================================================= // Show some help instructions (the inline doco from top of the macro) :HELP: Key_Purge() Win_Clear #103=Buf_Num Buf_Switch(XBUF1) Reg_Ins(Macro_Num) BoF Search("|H3CDOC>", NOERR) // the leading "<" is masked out intentionally! if(EM){ Message("\n\n No inline help found.") }else{ Line(1) Del_Block(0,Cur_Pos) Search("|H3C/DOC>", NOERR) if(!EM){ BoL Del_Block(Cur_Pos, File_Size) } Replace("^/+", BEGIN+ALL+REGEXP+NOERR) // remove leading comment characters BoF while(! At_EoF){ // shorten lines longer than window width (not perfect, but ...) Goto_Col(Win_Cols) Del_Block(Cur_Pos, EoL_Pos) Line(1, NOERR+ERRBREAK) } EoF #106=Cur_Line - 1 // number of lines to display #105=Win_Lines - 1 // number of lines displayable in the window BoF repeat(ALL){ Win_Clear Type(#105, NORESTORE) if(Cur_Line >= #106){ break } #104=Get_Key("\nPress any key to continue or to quit ...", STATLINE+RAW) if(#104==27){ break } } } Update Buf_Quit(OK) Buf_Switch(#103) Visual_Macro(NOMSG) if(#104 != 27){ Get_Key("\nPress any key to close help...", STATLINE+RAW) } return //========================================================================================= // Key-Assignment: If in definition file: Load the file where the cursor is on :LOADFILE: if(Buf_Num==#92){ Save_Pos() BoL if((Cur_Char == #95) || (Cur_Char == '*') || At_EoL){ return } Search("|{||,|N}", NOERR) if(EM){ Restore_Pos() return } Search("|! ", REVERSE+ADVANCE) Reg_Copy_Block(103, BoL_Pos, Cur_Pos) Restore_Pos() File_Open("|@(103)") #96=Buf_Num+1000 }else{ if(Buf_Num == (#96-1000)){ File_Close(CONFIRM+NOMSG) Buf_Quit() Buf_Switch(#92) } } return //--------------------------- // Key-Assignment: Fill line with appropriate |'s :FILLPIPES: BoL if(At_EoF){return} // do nothing if at end-of-file #103=Cur_Pos Search("|", REVERSE+NOERR) if(EM){ // if no previous dividers found: insert dummy ones EoL Ins_Text(" | | | ") return } Goto_Pos(#103) Replace_Block("|" ," ", Cur_Pos, EoL_Pos, ALL+NOERR) // remove the existing dividers in the line (if any) BoL Search("|", REVERSE+NOERR) BoL // for every divider in a previous line with deviders // get it's position and create a new divider in the current line repeat(ALL){ Search_Block("|", Cur_Pos, EoL_Pos, NOERR+ERRBREAK) #104=Cur_Pos #105=Cur_Col Goto_Pos(#103) EoL Ins_Indent(#105) // fill up the line with spaces if neccessary Goto_Col(#105) if(At_EoL){ Ins_Text("|") }else{ if(Cur_Char == 32){ // only if on a space: insert a divider by overwriting Ins_Text("|", OVERWRITE) } } Goto_Pos(#104+1) } Goto_Pos(#103) EoL if(Cur_Char(-1)=='|'){Ins_Text(" ")} BoL Search("|", ADVANCE) Char(1) return //=======================================================================================