1. Source Code Beautifier for WEE (and other editors)
- Posted by K_D_R Dec 12, 2015
- 1326 views
After fiddling around with another source code beautifier, I gave up and went back to my version of Jiri Babor's "tidy.ex". Works like a charm. The original file is backed-up to file_name&"~", a "tidied" version of the file is written to file_name&".tidy" which is then copied over the original file. If you don't want to risk your original file you can comment out the code that do that overwrites the input file.
include tidy.e -- add to ui_gtk.e -- -- append the following lines to the end of the add(runmenu, { ~~ createmenuitem("Test Run after Bind/Shroud/Translate", "RunTestRun", 0, run_testrun), -- add comma create(GtkSeparatorMenuItem), -- add line createmenuitem("Tidy Source Code", "RunStart") -- add line }) -- insert the following lines at the end -- of the RunStart function: elsif equal(lbl, "Run Terminal Emulator") then Run("$SHELL") -- insert elsif equal(lbl, "Tidy Source Code") then printf(1, "\n\n\t%s\n\n", {tidy(file_name)}) ------------------------------------------------- else crash("Unable to get menu label")
Here is the file, "tidy.e"
-- -- tidy.e 1.2 -- -- 2013-04-07 edit by Kenneth Rhodes -- wolfmanjacques@gmail.com -- -- tidy.e 1.2, derived from Jiri Babor's tidy.ex 1.0, -- is an include file, intended to be used -- with an editor written in euphoria such as ed.ex. -- It can also be called from the command_line by -- tidy.ex 1.2 -- -- usage: -- include tidy.e -- tidy(sequence filename) -- -- -- Changes from Jiri Babor's tidy.ex 1.0: -- -- Added support for "loop", "switch", "type", "ifdef" -- -- Dropped command_line code and wrapped the input/output -- code in the public function, "tidy(filename)". -- -- Added routine to automatically backup input/source file -- file with a DESTRUCTIVE copy of the input filename to: -- file & "~". If the backup file cannot be written, then -- the integer flag "TIDY" will be set to FALSE and the -- program will abort. -- -- tidy.e returns a message indicating success, or type -- of failure. -- -- Added command_line interface for tidy.e, tidy.ex 1.2: -- tidy.ex usage: eui tidy.ex <filename> -- ---------------------------------------------------------------- ---------------------------------------------------------------- ---------------------------------------------------------------- -- tidy.ex : version 1.00 -- jiri babor -- jbabor@paradise.net.nz -- 12-Dec-03 ---------------------------------------------------------------- -- source code beautifier: -- removes horizontal tabs - only spaces used -- provides consistent, uniform indentation -- adjustable: change the first two constants below -- usage: ex tidy [inputfile [outputfile]] -- parameters in square brackets are optional -- if input file is not specified, a prompt will be shown -- if both files are not specified, default 'out' file will -- be created and the modified file written into it -- IMPORTANT: input source code must be syntactically correct! ---------------------------------------------------------------- include std/filesys.e include std/console.e constant indent = 4 -- change it to whatever you fancy constant cc = 41 -- normal comment start column constant spaces = repeat(32,cc-1) constant S = { "for","function","if","procedure","while", "loop", "switch", "type", "ifdef" -- tidy 1.2 } ----------------------------------- constant TRUE = 1, FALSE = 0 object o sequence filename,out,backup,previous_word,s,s1,s2,word integer f,f1,f2,level,n,n1 integer in_hex,in_num,in_string,in_word -- flags -- tidy 1.2 sequence msg = " " integer TIDY = TRUE function ltrim(sequence s) -- discard leading spaces integer n n = length(s) for i = 1 to n do if s[i]!=32 then return s[i..n] end if end for return {} end function function rtrim(sequence s) -- discard leading spaces for i = length(s) to 1 by -1 do if s[i] != 32 then return s[1..i] end if end for return {} end function function t2s(sequence s) -- convert tabs to spaces for i = 1 to length(s) do if s[i]=9 then s[i]=32 end if end for return s end function type word_char(integer x) if x='_' or (x>='0' and x<='9') or (x>='A' and x<='Z') or (x>='a' and x<='z')then return TRUE end if return FALSE end type type lead_word_char(integer x) if (x>='A' and x<='Z') or (x>='a' and x<='z') then return TRUE end if return FALSE end type type num_char(integer x) if (x>='0' and x<='9') or x='.' then return TRUE end if return FALSE end type type hex_char(integer x) if in_hex and ((x>='0' and x<='9') or (x>='A' and x<='F')) then return TRUE end if return FALSE end type function tab() return repeat(32,level*indent) end function function comment_start(sequence s) integer in_string,n n = length(s) if n<2 then return FALSE end if in_string = FALSE for i = 1 to n-1 do if s[i]='\"' then if not in_string then in_string = TRUE elsif i<3 or (s[i-2]!= '\\' and s[i-1]!='\\') then in_string = FALSE end if elsif not in_string and s[i]='-' and s[i+1]='-' then return i end if end for return FALSE end function function first() if match("end",s1)=1 or match("else",s1)=1 or match("elsif",s1)=1 then return TRUE end if return FALSE end function procedure parse() integer c,n for i = 1 to length(s1) do c = s1[i] if in_word then if word_char(c) then word &= c else n = find(word,S) if n then if equal(previous_word,"end") then level -= 1 else level+= 1 end if end if in_word = FALSE previous_word = word word = "" end if elsif in_num then if not num_char(c) then in_num = FALSE end if elsif in_hex then if not hex_char(c) then in_hex = FALSE end if elsif in_string then if c = '\"' then in_string = FALSE end if elsif lead_word_char(c) then in_word = TRUE word &= c elsif num_char(c) then in_num = TRUE elsif c='#' then in_hex = TRUE elsif c = '\"' then in_string = TRUE end if end for if in_word then n = find(word,S) if n then if equal(previous_word,"end") then level -= 1 else level+= 1 end if end if in_word = FALSE previous_word = word word = "" end if in_num = FALSE in_hex = FALSE in_string = FALSE -- error? end procedure -- tidy 1.2 global function tidy(sequence filename) sequence source = filename -- backup the input file backup = filename & "~" if copy_file(filename, filename & "~", 1) then TIDY = TRUE else TIDY = FALSE msg = sprintf("%s~ BACKUP FAILED!!! tidy.ex aborting.... ", {filename}) end if -------------------------------------------------------------------------------- if TIDY then f1 = open(filename,"r") -- input if f1=-1 then msg = sprintf("\n\tCouldn\'t open input file %s \n\taborting...", filename) TIDY = FALSE end if end if if TIDY then out = filename & ".tidy" f2 = open(out,"w") -- tidied file if f2=-1 then msg = "\n\tCouldn\'t open output file "& out &" for writing. \n\taborting..." TIDY = FALSE end if end if if TIDY then in_string = FALSE in_word = FALSE in_num = FALSE in_hex = FALSE word = "" previous_word = "" level = 0 while TRUE do o = gets(f1) if atom (o) then exit end if -- end of file s = t2s(o) s = ltrim(s) n = comment_start(s) if n>1 then s1 = rtrim(s[1..n-1]) -- code part n1 = length(s1) s2 = s[n..length(s)] -- comment part f = first() if f then level -= 1 end if n1 += level*indent if n1<(cc-1) then s = tab() & s1 & spaces[1..cc-n1-1] & s2 else s = tab() & s1 & ' ' & s2 end if if f then level += 1 end if elsif n=1 then s = tab() & s s1 = "" else -- no comment s1 = s f = first() if f then level -= 1 end if s = tab() & s if f then level += 1 end if end if puts(f2,s) parse() end while close(f1) -- tidied file = out = filename & ".tidy end if if TIDY then close(f2) -- input file -- tidy 1.2 if copy_file(out, source, 1) then msg = sprintf("\n\tThe file \"%s\" has been \"tidied\" \n\tand backed up as \"%s~\" !!", {source, source}) end if end if return msg end function