Page 1 of 1

Code beautifier

Posted: Sat Nov 26, 2005 3:10 pm
by Lewis
Can anyone point me to a PureBasic code beautifier (with or without source code)? :wink: Thanks in advance.

Posted: Sat Nov 26, 2005 3:57 pm
by DarkDragon
NicTheQuicks SourceOptimizer, but it doesn't work good anymore with PB 3.94(the declares are always at the bottom of the source)

http://forums.purebasic.com/german/arch ... =optimizer

Posted: Sun Nov 27, 2005 11:22 am
by thefool
here: works with the newest version too.
viewtopic.php?t=17204&highlight=auto+indent

hope that is what you want.

Posted: Sun Nov 27, 2005 4:22 pm
by Lewis
thefool wrote:here: works with the newest version too.
viewtopic.php?t=17204&highlight=auto+indent

hope that is what you want.
Yes, "Indentation" and "Right trim" functionality are important parts of a code beautifier. Many thanks. :D

Any chance of making the source code available (I'd much prefer English versions and even build further on your work)?

Cheers,
Lewis

Posted: Sun Nov 27, 2005 5:06 pm
by ts-soft
Lewis wrote:
thefool wrote:here: works with the newest version too.
viewtopic.php?t=17204&highlight=auto+indent

hope that is what you want.
Yes, "Indentation" and "Right trim" functionality are important parts of a code beautifier. Many thanks. :D

Any chance of making the source code available (I'd much prefer English versions and even build further on your work)?

Cheers,
Lewis
http://forums.purebasic.com/german/view ... autoindent
http://dostej.pureforge.net/Files/PB%20 ... Source.zip

Posted: Sun Nov 27, 2005 8:19 pm
by Lewis
ts-soft wrote:
Lewis wrote:
thefool wrote:here: works with the newest version too.
viewtopic.php?t=17204&highlight=auto+indent

hope that is what you want.
Yes, "Indentation" and "Right trim" functionality are important parts of a code beautifier. Many thanks. :D

Any chance of making the source code available (I'd much prefer English versions and even build further on your work)?

Cheers,
Lewis
http://forums.purebasic.com/german/view ... autoindent
http://dostej.pureforge.net/Files/PB%20 ... Source.zip
8) Much obliged. Now all I have to do is brush up on my German (no easy task)! :roll:

Posted: Sun Nov 27, 2005 8:25 pm
by ts-soft
But you can download this:
http://dostej.pureforge.net/Files/PB%20 ... Source.zip
The link included spaces!
The PureBasic-Source have in german the same syntax :wink:

Posted: Wed Nov 30, 2005 8:25 am
by Hurga
And some of the comments are in english. I have a little improvement and I ´ll change all comments to english.
I ´ll upload it tomorrow. (I drop the link here, when its done...)

Re: Code beautifier

Posted: Sun Feb 26, 2006 10:03 am
by Michael Vogel
Lewis wrote:Can anyone point me to a PureBasic code beautifier (with or without source code)? :wink: Thanks in advance.
I think, other programmers have done something like this already, so forgive me.

It's just the kernel, this should be integrated somehow into the IDE. It has also two functions (but these things I needed most for now):
- cleaning the source code from tab and space characters
- doing an auto indent

Michael

Code: Select all

; Define

Global indtxt.s=Chr(9); "   "

Global LeftC.w
Global LeftD.w
Global RightC.w
Global RightD.w
Global RightP.w

#Words=22
Global Dim Word.s(#Words)

For i=1 To #Words
	Read word(i)
Next i

DataSection
	Data.s "; Define"
	Data.s ";{"
	Data.s "Procedure "
	Data.s "Procedure."
	Data.s "DataSection"
	Data.s "If "
	Data.s "Select "
	Data.s "While "
	Data.s "For "
	Data.s "Repeat"
	
	Data.s "Case "	; kurzzeitig ''ausrücken''
	Data.s "ElseIf"	; detto
	
	Data.s "; EndDefine"
	Data.s ";}"
	Data.s "EndProcedure"
	Data.s "xxxxxxxxxxx"
	Data.s "EndDataSection"
	Data.s "EndIf"
	Data.s "EndSelect"
	Data.s "Wend"
	
	Data.s "Next"		; blöd, da kann nach 'Until' noch Text kommen...
	Data.s "Until "	; detto
	
EndDataSection

; EndDefine
Procedure.s RightTrim(s.s)
	l.w=Len(s)
	While l
		l-1
		b.w=PeekB(@s+l)
		If b<>9 And b<>32
			Break
		EndIf
	Wend
	ProcedureReturn Left(s,l+1)
EndProcedure
Procedure.s LeftTrim(s.s)
	l.w=Len(s)
	c.w=0
	While c<l
		b.w=PeekB(@s+c)
		If b<>9 And b<>32 ; Space & Tab
			Break
		EndIf
		c+1
	Wend
	ProcedureReturn Mid(s,c+1,l-c)
EndProcedure
Procedure FindCommas(s.s)
	LeftC=0
	LeftD=0
	RightC=0
	RightD=0
	RightP=1
	l.w=Len(s)
	c.w=0
	While c<l
		b.w=PeekB(@s+c)
		c+1
		Select b
		Case 59		; Semicolon
			RightC=c
			If LeftC=0 : LeftC=c : EndIf
		Case 34	; DoubleQuote
			RightD=c
			If LeftD=0 : LeftD=c : EndIf
		Case 58	; Colon
			RightP=c
		Case 9,32
			If c=RightP+1 : RightP+1 : EndIf
		EndSelect
		
	Wend
EndProcedure
Procedure.s RightCut(s.s,x.w)
	ProcedureReturn RTrim(Left(s,x-1))
EndProcedure
Procedure.s StringS(n, chars.s)
	; Function: returns a string consiting of n concatenated chars
	; LSet("",n,chars) nimmt nur das erste Zeichen!
	Protected s.s=""
	While n>0
		s+chars
		n-1
	Wend
	ProcedureReturn s
EndProcedure

Procedure Doit(mode.w)
	indent.w=0
	
	ReadFile(1,"Test.pb")
	CreateFile(2,"TestX.pb")
	While Not(Eof(1))
		z.s=ReadString(1)
		z=lefttrim(z)
		z=righttrim(z)
		
		If mode
			s.s=z
			FindCommas(s)
			; [1]	if a=0		; remark
			; [2]	if a=''x''	; remark
			; [3]	if a=0		; ''remark''
			; [x]	if a=''x''	; ''remark''
			If LeftC
				If LeftD=0 Or LeftC<LeftD	; [1], [3]
					s=RightCut(s,LeftC)
				ElseIf RightC>RightD		; [2]
					s=RightCut(s,RightC)
				EndIf
			EndIf
			
			afterburner.w=0
			
			For i=1 To #Words
				l.w=Len(word(i))
				Select i
				Case 1 To 12
					p.w=1
				Case 13 To 20
					p.w=Len(s)-l+1
				Case 21,22
					p.w=RightP
				EndSelect
				
				If Mid(s,p,l)=word(i)
					Select i
					Case 1 To 10
						afterburner.w+1
					Case 11,12
						indent-1
						afterburner.w+1
					Case 13 To 22
						If afterburner
							afterburner-1
							Else
							indent-1
						EndIf
						
					EndSelect
					
				EndIf
				
			Next i
			z=strings(indent,indtxt)+z
			;WriteStringN(2,s)
		EndIf
		WriteStringN(2,z)
		indent+afterburner
	Wend
	CloseFile(1)
	CloseFile(2)
EndProcedure

; Doit(0)	trims source code from space and tab characters
; Doit(1)	auto indent the source code

Doit(#True)

Posted: Sun Feb 26, 2006 10:06 am
by blueznl
this one does some reformatting:

http://www.xs4all.nl/~bluez/datatalk/pu ... _codecaddy

(oh, and it allows the use of the line continuation character)

Posted: Sun Feb 26, 2006 11:55 am
by Dare2
Another option is JaPBe. Even if you don't use it to write the code, you can paste the code into it to get indentation, etc.

Posted: Sun Feb 26, 2006 12:06 pm
by Berikco
Here is one i wrote and posted some time ago.
Must be installed as a tool, and reformats the source quick by hitting a shortcut

Code: Select all

;
; ------------------------------------------------------------
;
;           Source Formatting By Berikco
;
;
; ------------------------------------------------------------
;
; For Purebasic Toolmenu version 3.40 and up
; Will format the source with TABS(Spaces)
; Thanks to PB for his help on the ';' comment finder
;
; --- Toolbox settings ---------------------------------------
;
; Arguments:
; First  argument "%FILE"
; Second argument #Number of spaces for 1 Tab
; Third  argument if 1 extra Select indent
; Example: "%FILE" 2 [1]
;
; Wait Until tool Quits = On
; Reload source after program is finished = On
;
; ------------------------------------------------------------
;
; 
;

DestFileName$ = ProgramParameter()    ; Sourcefile to read
NumSpaces = Val(ProgramParameter())   ; Number of spaces
SelectTab= Val(ProgramParameter())   ; 1= Extra Indent At Select

SourceFileName$ = DestFileName$+"2" ; The backup file *.pb2

#Source=1
#Destination=2

If FileSize(DestFileName$) ; Do nothing if source empty
  
  If FileSize(SourceFileName$) ; If old backupFile exist, delete it
    DeleteFile(SourceFileName$)
  EndIf
  
  If RenameFile(DestFileName$, SourceFileName$) ; Rename source to backup
    
    If OpenFile(#Source,SourceFilename$)        ; Open Source, now with *.pb2 extension
      
      If CreateFile(#Destination,DestFileName$) ; Create new source
        
        While Eof(#source)=false
          
          UseFile(#Source)
          a$=ReadString()
          
          If Eof(#source)=false           ; Check if read is last line in source
            ;                               If this is the case, must not write CRLF
            
            a$=LTrim(a$)                  ;Remove old TABs (spaces in front)
            a$=RTrim(a$)                  ;Remove all spaces at end
            
            Tab+NextTab
            NextTab=0
            in=FindString(a$," ",1)       ; Find PureBasic Keyword
            
            If in>0
              Vgl$=LCase(Left(a$,in-1))          ; Get only Keyword
            Else
              Vgl$=LCase(a$)                     ; Nothing after Keyword, use whole string
            EndIf
            
            ; Check For Keyword that needs formatting
            
            If Left(a$,1)=";"
              ;nope
            ElseIf Vgl$="procedure" Or Vgl$="procedure.b" Or Vgl$="procedure.w" Or Vgl$="procedure.l"  Or Vgl$="procedure.s" Or Vgl$="procedure$" Or Vgl$="datasection" Or Vgl$="enumeration"
              
              Tab=0
              NextTab=1
            ElseIf Vgl$="endprocedure" Or Vgl$="enddatasection" Or Vgl$="endenumeration"
              
              Tab=0
              NextTab=0
              
            ElseIf Vgl$="foreach" Or Vgl$="if" Or Vgl$="with" Or vgl$="select" Or Vgl$="for" Or Vgl$="repeat" Or Vgl$="while" Or Vgl$="structure" Or Vgl$="compilerif" Or Vgl$="opensubmenu"
              
              
              
              b$=a$+";"  ;little trick, add comment to line, only one routine needed to scan
              KeyWord$=""
              
              For r=1 To Len(b$)
                a=Asc(Mid(b$,r,1))
                If a=34
                  q=1-q
                EndIf
                If a=58 And q=0
                  NextTab=0
                  r=Len(b$)
                Else
                  
                EndIf
                If a=59
                  If q=0
                    
                    KeyWord$=LTrim(KeyWord$)        ;Remove spaces in front
                    KeyWord$=LCase(RTrim(KeyWord$)) ;Remove all spaces at end and put lowercase
                    If KeyWord$="endif" Or KeyWord$="endstructure" Or KeyWord$="next" Or KeyWord$="until" Or KeyWord$="Wend" Or KeyWord$="ForEver"
                      If tab>0
                        tab-1
                        
                        
                      EndIf
                      
                    EndIf
                    
                    r=Len(b$)
                  EndIf
                  
                  If Vgl$="select" And SelectTab=1
                    NextTab=2
                  Else
                    NextTab=1
                  EndIf
                EndIf
                keyword$+Chr(a)
                
                
                
              Next
              
              If Vgl$="if"
                ;  Debug "if " + Str(nexttab) + "  " + a$
              EndIf
              
              
            ElseIf Vgl$="endif" Or Vgl$="endstructure" Or Vgl$="endwith" Or Vgl$="return" Or Vgl$="next" Or Vgl$="until" Or Vgl$="wend" Or Vgl$="forever" Or Vgl$="compilerendif"
              Tab-1
              NextTab=0
            ElseIf Vgl$="endselect"
              If SelectTab=1
                Tab-2
              Else
                Tab-1
              EndIf
              NextTab=0
            ElseIf Vgl$="elseif" Or Vgl$="else" Or Vgl$="case" Or Vgl$="compilerelse" Or Vgl$="default"
              Tab-1
              NextTab=1
            Else
              b$=a$+";"  ;little trick, add comment to line, only one routine needed to scan
              KeyWord$=""
              For r=1 To Len(b$)
                a=Asc(Mid(b$,r,1))
                If a=34 : q=1-q : EndIf
                If a=59 And q=0
                  KeyWord$=LTrim(KeyWord$)        ;Remove spaces in front
                  KeyWord$=LCase(RTrim(KeyWord$)) ;Remove all spaces at end and put lowercase
                  If KeyWord$="endif" Or KeyWord$="endstructure" Or KeyWord$="next" Or KeyWord$="until" Or KeyWord$="Wend" Or KeyWord$="ForEver"
                    If tab>0
                      tab-1
                      
                    EndIf
                  EndIf
                EndIf
                keyword$+Chr(a)
                If a=58 And q=0
                  If keyword$=a$
                    Tab=0
                    NextTab=1
                    r=Len(b$)
                  EndIf
                  KeyWord$=""
                EndIf
              Next
            EndIf
            
          
            If tab<0
              tab=0
            EndIf
            Front$=Space(Tab * NumSpaces) ; Create Spaces needed
            a$ = Front$ + a$              ; Put spaces before the line code
            UseFile(#Destination)
            WriteStringN(a$)              ; Write in new source
            
          Else
            UseFile(#Destination)
            WriteString(a$)
          EndIf
        Wend
        
        CloseFile(#source)
        CloseFile(#destination)
        DeleteFile(SourceFileName$)
        
      EndIf
    EndIf
  EndIf
EndIf
End


AutoIndent, more complex...

Posted: Mon Feb 27, 2006 11:43 am
by Michael Vogel
Sorry to post that long piece of code, but now it works as wanted...

- works with complete file or selected lines
- uses tab settings from IDE (real tab or space characters)
- is able to remove all heading and trailing space and tab chars also

Michael

Code: Select all

Procedure EditorBug()
EndProcedure

; AutoIndent by Michael Vogel
; -------------
; with pressed shift key:	eliminates tabs and spaces
; without shift key:			indents source code
; no selection:				complete source code is affected
; selection of lines:			only selected lines are changed

; known problems:			when cursor is in line 1, the procedure folds up (editor bug?)

; Define

#Words=41

Global indtxt.s=Chr(9); "   "

Global LeftC.w
Global LeftD.w
Global RightC.w
Global RightD.w
Global RightP.w

Global Dim Word.s(#Words)
Global Dim Border(3)

z.w=0
For i=1 To #Words
	Read Word(i)
	If Word(i)="!" And i<#Words
		Border(z)=i-1

		;Debug Str(z)+": "+Str(i-1)+" = "+word(border(z))
		z+1
		Read Word(i)
	EndIf
Next i
border(z)=#Words


DataSection
	Data.s "; Define"
	Data.s ";{"
	Data.s "Procedure "
	Data.s "Procedure."
	Data.s "ProcedureC"
	Data.s "ProcedureDLL"
	Data.s "DataSection"
	Data.s "If "
	Data.s "Select "
	Data.s "While "
	Data.s "For "
	Data.s "ForEach "
	Data.s "Repeat"
	Data.s "Structure "
	Data.s "Interface "
	Data.s "Enumeration "
	Data.s "CompilerIf "
	Data.s "CompilerSelect "
	Data.s "!"							; border(0)

	Data.s "Case "					; kurzzeitig ''ausrücken''
	Data.s "Else"						; detto
	Data.s "ElseIf"					; detto
	Data.s "Default"
	Data.s "CompilerElse"
	Data.s "CompilerCase"
	Data.s "CompilerDefault"
	Data.s "!"							; border(1)

	Data.s "; EndDefine"
	Data.s ";}"
	Data.s "EndProcedure"
	Data.s "EndDataSection"
	Data.s "EndIf"
	Data.s "EndSelect"
	Data.s "Wend"
	Data.s "ForEver"
	Data.s "EndStructure"
	Data.s "EndInterface"
	Data.s "EndEnumeration"
	;Data.s "CompilerEndIf"		; wird schon bei 'EndIf' entdeckt
	;Data.s "CompilerEndSelect"	; analog oben
	Data.s "!"							; border(2)

	Data.s "Next"						; blöd, da kann nach 'Until' noch Text kommen...
	Data.s "Until "					; detto
	Data.s "!"							; border(3)

EndDataSection
; EndDefine
Procedure.s RightTrim(s.s)
	l.w=Len(s)
	While l
		l-1
		b.w=PeekB(@s+l)
		If b<>9 And b<>32
			Break
		EndIf
	Wend
	ProcedureReturn Left(s,l+1)
EndProcedure
Procedure.s LeftTrim(s.s)
	l.w=Len(s)
	c.w=0
	While c<l
		b.w=PeekB(@s+c)
		If b<>9 And b<>32 ; Space & Tab
			Break
		EndIf
		c+1
	Wend
	ProcedureReturn Mid(s,c+1,l-c)
EndProcedure
Procedure FindCommas(s.s)
	LeftC=0
	LeftD=0
	RightC=0
	RightD=0
	RightP=0
	l.w=Len(s)
	c.w=0
	While c<l
		b.w=PeekB(@s+c)
		c+1
		Select b
		Case 59		; Semicolon
			RightC=c
			If LeftC=0 : LeftC=c : EndIf
		Case 34		; DoubleQuote
			RightD=c
			If LeftD=0 : LeftD=c : EndIf
		Case 58		; Colon
			RightP=c
		Case 9,32
			If c=RightP+1 : RightP+1 : EndIf
		EndSelect

	Wend
EndProcedure
Procedure.s RightCut(s.s,x.w)
	ProcedureReturn RTrim(Left(s,x-1))
EndProcedure
Procedure.s StringS(n, chars.s)
	Protected s.s=""
	While n>0
		s+chars
		n-1
	Wend
	ProcedureReturn s
EndProcedure

; AutoIndent (written by Michael Vogel)
;
; > install the tool using the parameter "%TEMPFILE" %SELECTION
; > use the PureBasic as the working directory (or adapt the OpenPreferences path below)
; > select 'Wait until tool quits' and 'Reload source aftzer tool has quit'

Procedure Init()

	; Dateinamen holen...
	CompilerIf 1
		If CountProgramParameters()<>2
			MessageBox_(0,"'AutoIndent' benötigt die Parameter"+#CR$+"%TEMPFILE und %SELECTION...","Fehler",#MB_ICONERROR| #MB_OK)
			End
		EndIf
		Global OutputFile.s=ProgramParameter()
	CompilerElse
		Global OutputFile.s="Test.pb"
	CompilerEndIf

	Global InputFile.s=OutputFile+"~"
	DeleteFile(InputFile)
	If RenameFile(OutputFile,InputFile)=0
		MessageBox_(0,"'AutoIndent' konnte keine Temporärdatei erstellen","Fehler",#MB_ICONERROR| #MB_OK)
		End
	EndIf

	; Selektion abfragen...
	Global zeile.w=0
	selektion.s=ProgramParameter()
	Global Startzeile.w=Val(StringField(selektion, 1, "x"))
	Global Endzeile.w=Val(StringField(selektion, 3, "x"))
	If startzeile=Endzeile
		startzeile=1
		Endzeile=#MAXSHORT
	EndIf

	; Tabulator-Einstellungen holen...
	OpenPreferences("PureBasic.prefs")
	PreferenceGroup("Global")
	If Val(ReadPreferenceString("RealTab","0"))
		indtxt.s=Chr(9)
	Else
		indtxt.s=Space(Val(ReadPreferenceString("TabLength", "2")))
	EndIf
	ClosePreferences()

EndProcedure
Procedure Doit(mode.w)

	; Doit(0)	auto indent the source code
	; Doit(1)	trims source code from space and tab characters

	init()

	ReadFile(1,InputFile)
	CreateFile(2,OutputFile)

	indent.w=0


	While Not(Eof(1))
		z.s=ReadString(1)
		zeile.w+1
		z=lefttrim(z)
		z=righttrim(z)

		If zeile>=Startzeile And zeile<=Endzeile
			afterburner.w=0

			If (mode=0) And (Len(z)>0)
				s.s=z
				FindCommas(s)
				; [1]	if a=0		; remark
				; [2]	if a=''x''	; remark
				; [3]	if a=0		; ''remark''
				; [x]	if a=''x''	; ''remark''
				If LeftC
					If LeftD=0 Or LeftC<LeftD	; [1], [3]
						s=RightCut(s,LeftC)
				ElseIf RightC>RightD		; [2]
						s=RightCut(s,RightC)
					EndIf
				EndIf

				For i=1 To #Words
					l.w=Len(word(i))
					Select i
					Case 1 To border(1)
						p.w=1
					Case 1 To border(2)
						p.w=Len(s)-l+1
					Case 1 To border(3)
						p.w=RightP+1
					EndSelect

					If Mid(s,p,l)=word(i)

						Select i
						Case 1 To border(0)
							afterburner.w+1

						Case 1 To border(1)
							indent-1
							afterburner.w+1

						Case 1 To border(3)
							If afterburner
								afterburner-1
							Else
								indent-1
							EndIf

						EndSelect
					EndIf

				Next i

				z=strings(indent,indtxt)+z
				;WriteStringN(2,s)

			EndIf ; mode

		EndIf ; Zeilenselektion

		WriteStringN(2,z)
		indent+afterburner
	Wend
	CloseFile(1)
	CloseFile(2)
EndProcedure

Doit(GetKeyState_(#VK_SHIFT) & 128)