1. Source Code Beautifier for WEE (and other editors)

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 
 
 
new topic     » topic index » view message » categorize

Search



Quick Links

User menu

Not signed in.

Misc Menu