#!/usr/bin/wish # Name: xtexsh # # Author: Gerald Teschl # # Version: 1.4-2 # wm title . "xTeX Shell" # # Set some default values # set userconf "~/.xtexshrc" set allconf "/etc/xtexshrc" set programs {tex editor dviviewer psviewer pdfviewer spell makeindex bibtex xterm print dvips ps2pdf psnup} set auxfiles {aux bbl blg dvi glo idx ilg ind log lof lot out ps pdf toc} set printopts {abspagenumbers printtofile twoup} # Helper apps set tex "tex" set editor "emacs" set dviviewer "xdvi" set psviewer "gv" set pdfviewer "gv" set spell "ispell -t" set makeindex "makeindex" set bibtex "bibtex" set xterm "xterm" set print "lpr" set dvips "dvips" set ps2pdf "ps2pdf" # if you have psnup set psnup "psnup -q -2" # if you have pstops #set psnup "pstops -q \"2:0L@.7(21cm,0)+1L@.7(21cm,14.85cm)\"" # autotex set watchfile "n" set watchdelay "20" # stuff set geometry "" set interminal "y" set defaultview "dvi" set thisview $defaultview # Are the page numbers specified for dvips absolute (y=yes, n=no)? set abspagenumbers n # Should it be printed twoup? set twoup n # Should a ps file be written instead (y=yes, n=no)? set printtofile n # At startup open: f(iledialog) l(ast documenat) set startup l set n_recent 5 set defaultdir "" set searchpath "." # Which aux files shall be marked for removal (y=yes, n=no)? set bak y set aux y set bbl y set blg y set dvi n set idx y set ilg y set ind y set glo y set log y set lof y set lot y set out y set ps y set pdf y set toc y set rminclf y # Read environment variables foreach i $programs { set ui [string toupper $i] if [info exists env($ui)] {set $i $env($ui)} } # # End of default settings # set help_msg " The present program is a simple TeX interface for the X Window System based on \"wish\", respectively Tcl/Tk. It allows you to process a given TeX file by choosing operations from a menu or by pressing buttons, rather than typing the corresponding commands. I assume that tex, latex, pdftex, pdflatex, xdvi, dvips, makeindex, bibtex, etc. are installed on your system and that you are familiar with TeX. (1) STARTING xTeX Shell It can be invoked from the command line using xtexsh \[wish options\]\[file\[.tex\]\] Here \"wish options\" refers to any option understood by \"wish\" (e.g., -geometry or -display, see \"man wish\" for more info). You can also use \"file\" or \"file.\" instead of \"file.tex\" and specify a search path in the preferences. If no file is given, depending on the preferences set, a file dialog appears, your last file will be opened, or nothing happens. In addition, xtexsh -r\[n\] will open your n-th recent file (n=0 being the most recent). If a directory is given instead of a file (or if a default directory is set), the file dialog begins in that directory. (2) USING xTeX Shell Once you have chosen a file, its name will be displayed inside the window. All operations are performed with respect to this file (lets call it file.tex). The file will be typeset using tex unless it contains the strings \"\\documentclass\" or \"\\documentstyle\" in which case latex will be used. In addition, the command for typesetting can be changed using \"File->TeX command->Choose custom\" from the menu. Here is a short description of the possible operations: File->Open: Pops up a file dialog in order to change the current base file. File->Open recent: Lets you open an recent file. File->Edit: Opens file.tex with your favorite editor. File->Ispell: Opens file.tex with ispell (or any other spell checker). File->Print: Prints the typeset version of file.tex. You will be presented a dialog which asks for the first, last page to print. Absolute page numbers correspond to the page number when counting sheets, rather then to the numbers tex puts on each page. You can also print the document \"2up\" (provided you have \"psnup\" or \"pstops\" (which are part of the psutils package) installed. File->Remove aux files: This pops up a window which allows you to select and remove auxiliary files (produced by TeX). File->View aux file: Select an aux file and open it with your favorite editor. File->Execute command: Lets you execute a command. File->Open Shell: Opens a terminal window. File->Preferences: Set your personal preferences. File->Quit: Quits the program. Typeset->TeX: Compiles file.tex using the chosen TeX command. Typeset->TeX command->tex: Sets the current TeX command to \"tex\". Typeset->TeX command->latex: Sets the current TeX command to \"latex\" Typeset->TeX command->pdftex: Sets the current TeX command to \"pdftex\". Typeset->TeX command->pdflatex: Sets the current TeX command to \"pdflatex\" Typeset->TeX command->Choose custom: Chose a custom TeX command in the preferences (e.g., provide some options for tex). Typeset->AutoTeX: Automatically invoke TeX whenever the main file changes on disk. Typeset->Bibtex: Runs bibtex with the present file. Typeset->Makeindex: Runs makeindex with the present file. Typeset->Create PS: Create postscript file from dvi file. Typeset->Create PDF: Create pdf file from ps file (requires a revent version of ghostscript). Typeset->View: Allows you to view the present file. Typeset->Default View: Set the default viewing method. Typeset->Default View->dvi: View dvi file. Typeset->Default View->ps: View ps file. Typeset->Default View->pdf: View pdf file. Typeset->View DVI: Allows you to view the present dvi file. Typeset->View PS: Allows you to view the present ps file. Typeset->View PDF: Allows you to view the present pdf file. Help->About: Some general info about xTeX Shell. Help->Help: Displays the present help. Help->License: License information. The button bar provides shortcuts for the main operations for the corresponding menu items. (3) CUSTOMIZING xTeX Shell xTeX Shell can be easily customized using the menu item \"File->Preferences\". The programs invoked by xTeX Shell can be changed by choosing \"File->Preferences\" from the menu or by setting environment variables according to the following table: Program Environment variable Original setting TeX \$TEX tex / latex / pdftex /pdflatex Editor \$EDITOR xedit DVI viewer \$DVIVIEWER xdvi PS viewer \$PSVIEWER gv PS viewer \$PDFVIEWER gv Spelling \$SPELL ispell -t Makeindex \$MAKEINDEX makeindex Bibtex \$BIBTEX bibtex Xterm \$XTERM xterm Print \$PRINT lpr Dvips \$DVIPS dvips Ps2pdf \$PS2PDF ps2pdf Ps-n-up \$PSNUP psnup -q -2 Note that you can also specify options in addition to the command (e.g., \"xdvi -s 12\"). Printing will be done by using dvips (and psnup) and pipeing the resulting output to the print command. An alternative filter for producing the 2up version can be specified. In addition, you can change the startup behavior / geometry of xTeX Shell, the auxiliary files which are selected for removal, and the printing options. All preferences are stored in \"\~/.xtexshrc\". System wide preferences can be set in \"/etc/xtexshrc\". All recent files are stored in \"\~/.xtexsh_recent\". If this still is not enough for you, note that the script is a plain text file. So you can easily edit it to meet your own needs! (Always keep a copy of the original version, in case something goes wrong...) (4) ICON An icon \"xtexsh.xpm\" is included. If you used the rpm version it should be in the documentation directory (usually /usr/share/doc/xtexsh-1.4). (5) UPDATES The recent version can be found at Have fun, Gerald Teschl " set license_msg " Copyright (C) 1997 Gerald Teschl This program is free software; you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation; either version 2 of the License, or (at your option) any later version. This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. Please see the included file LICENSE for a copy of the GNU General Public License. If you used the rpm version it should be in the documentation directory (usually /usr/share/doc/xtexsh-1.4). If this file is missing, check out http://www.gnu.ai.mit.edu/copyleft/gpl.html or write to the Free Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA." # # Procedures # proc message {msg name {w .message}} { catch {destroy $w} toplevel $w wm title $w $name bind $w "destroy ." bind $w "destroy $w" bind $w "destroy $w" frame $w.buttons pack $w.buttons -side bottom -fill x button $w.buttons.ok -text OK -command "destroy $w" pack $w.buttons.ok -expand 1 text $w.text -yscrollcommand "$w.scroll set" -setgrid true \ -width 65 -height 26 -wrap word scrollbar $w.scroll -command "$w.text yview" pack $w.scroll -side right -fill y pack $w.text -expand yes -fill both $w.text tag configure big -font -*-Courier-Bold-R-Normal--*-140-*-*-*-*-*-* $w.text insert end "xTeX Shell\n" big $w.text insert end $msg } proc edit { file } { global editor eval "exec $editor $file &" } proc view {} { global thisview switch $thisview { "ps" viewps "pdf" viewpdf default viewdvi } } proc viewdvi {} { global dviviewer fileroot if [file isfile $fileroot.dvi] { eval "exec $dviviewer $fileroot.dvi &" }\ else { tk_messageBox -icon info -title "Warning"\ -message "Please create $fileroot.dvi first." } } proc viewps {} { global psviewer fileroot if [file isfile $fileroot.ps] { eval "exec $psviewer $fileroot.ps &"}\ else { tk_messageBox -icon info -title "Warning"\ -message "Please create $fileroot.ps first." } } proc viewpdf {} { global pdfviewer fileroot if [file isfile $fileroot.pdf] { eval "exec $pdfviewer $fileroot.pdf &"}\ else { tk_messageBox -icon info -title "Warning"\ -message "Please create $fileroot.pdf first." } } proc texit {} { global xterm file tex if [file isfile $file] { eval "exec $xterm -e $tex $file &" }\ else { tk_messageBox -icon info -title "Warning"\ -message "Please create $file first." } } proc watchit {} { global xterm tex file includefiles fileroot watchdelay watchfile if { $watchfile == "n" } { .tex configure -relief raised return } if [file isfile $file] { if [file isfile $fileroot.dvi] { set changed "n" if [expr [file mtime $file] > [file mtime $fileroot.dvi]] { set changed "y" } foreach i $includefiles { if { [file isfile $i] == 0 } {set i $i.tex } if [expr [file mtime $i] > [file mtime $fileroot.dvi]] { set changed "y" } } if { $changed == "y" } { exec touch -r $file $fileroot.dvi texit after [expr $watchdelay * 1000] watchit } else { after [expr $watchdelay * 1000] watchit } } else { exec touch $fileroot.dvi texit after [expr $watchdelay * 1000] watchit } } else { tk_messageBox -icon info -title "Warning"\ -message "Please create $file first." .tex configure -relief raised } } proc texpress {} { global file watchfile if {$watchfile == "y"} { if {[.tex cget -relief] == "raised"} { .tex configure -relief sunken watchit } else { .tex configure -relief raised after cancel watchit } } else { texit } } proc makeindex {} { global xterm makeindex fileroot if [file isfile $fileroot.idx] { eval "exec $xterm -e $makeindex $fileroot.idx &" }\ else { tk_messageBox -icon info -title "Warning"\ -message "Please create $fileroot.idx first." } } proc bibtex {} { global xterm bibtex fileroot if [file isfile $fileroot.aux] { eval "exec $xterm -e $bibtex $fileroot &"}\ else { tk_messageBox -icon info -title "Warning"\ -message "Please create $fileroot.aux first." } } proc dvips {} { global xterm dvips fileroot if [file isfile $fileroot.dvi] { eval "exec $xterm -e $dvips -o $fileroot.ps $fileroot.dvi &"}\ else { tk_messageBox -icon info -title "Warning"\ -message "Please create $fileroot.dvi first." } } proc ps2pdf {} { global xterm ps2pdf fileroot if [file isfile $fileroot.ps] { eval "exec $xterm -e $ps2pdf $fileroot.ps &"}\ else { tk_messageBox -icon info -title "Warning"\ -message "Please create $fileroot.ps first." } } proc spell { file } { global xterm spell if [file isfile $file] { eval "exec $xterm -e $spell $file &" }\ else { tk_messageBox -icon info -title "Warning"\ -message "Please create $file first." } } proc detect {} { global file tex defaultview thisview set tex tex set thisview $defaultview if [file isfile $file] { set line "" set dummy "" set match "" set myfile [open $file r] gets $myfile line close $myfile if [ regexp {^%&(.+)$} $line dummy match ] { set tex $match if [ regexp {pdf(la)?tex} $match ] { set thisview "pdf" } } else { if [exec sh -c "echo `grep -c \\documentclass $file`"] { set tex latex } if [exec sh -c "echo `grep -c \\documentstyle $file`"] { set tex latex } if [exec sh -c "echo `grep -c \"\\input amstex\" $file`"] { set tex tex } if { $thisview == "pdf" } { set tex "pdf$tex" } } } } proc labelentry {path text length default} { frame $path label $path.label -text $text entry $path.entry -width $length -relief sunken $path.entry insert end $default pack $path.label -side left -expand y pack $path.entry -side right -expand y } proc filebox {} { set types { {"TeX files" {.tex} } {"All files" *} } setfile [tk_getOpenFile -filetypes $types -parent .] } proc findfile { } { global file searchpath set oldpath [pwd] if { $file == "" } { return 0 } foreach path $searchpath { if [file isdirectory $path] { cd $path if [file isfile $file] { return 1} if [file isfile ${file}tex] { set file ${file}tex; return 1 } if [file isfile $file.tex] { set file $file.tex; return 1 } } else { puts stdout "xtexsh: $path: No such directory" } } cd $oldpath return 0 } proc setfile { newfile } { global recent n_recent m_recent includefiles file fileroot if { $newfile == "" && $file == "" } { set newfile $recent(0) } if { $newfile != "" } { if [file isdirectory [file dirname $newfile] ] { cd [file dirname $newfile] set newfile [file tail $newfile] } set file "[pwd]/$newfile" set rcfile [open ~/.xtexsh_recent w] set i 0 puts $rcfile $file if { $n_recent >= 1 } { if {$m_recent >= $n_recent} {set n [expr $n_recent-1]}\ else {set n $m_recent} while {$i <= $n} { if {$recent($i) != $file} { puts $rcfile $recent($i) }\ else { if {$n < $m_recent} { set n [expr $n+1] } } set i [expr $i+1] } } close $rcfile if { $m_recent >= 1 } { readrecentfiles } if { [file extension $newfile ] == ".tex" } { set fileroot [file rootname $newfile] }\ else { set fileroot $newfile } set file $newfile wm title . "xTeX: $file" detect if [file isfile $file] { set cline "grep \"^ *\\\\\\include\{.*\}\" $file | sed -e 'y/\{\}/@@/' | awk 'BEGIN\{FS=\"@\"\} \{print \$2\}'" set includefiles [exec bash -c "$cline; exit 0" ] }\ else { set includefiles "" } menufile } } proc execute {{w .execute}} { catch {destroy $w} toplevel $w wm title $w "Execute command" bind $w "destroy ." bind $w "destroy $w" bind $w "executeit $w" label $w.pwd -text "Current directory: [pwd]" labelentry $w.command "Command:" 50 "" checkbutton $w.interminal -text "Execute in xterminal" \ -onvalue "y" -offvalue "n" -relief flat frame $w.buttons button $w.buttons.cancel -text "Cancel" -underline 0 -command "destroy $w" button $w.buttons.ok -text "OK" -underline 0 -command "executeit $w" pack $w.buttons.cancel -side left pack $w.buttons.ok -side right pack $w.pwd $w.command $w.interminal $w.buttons -side top -anchor w } proc executeit { path } { global interminal xterm set command [$path.command.entry get] if {$command != ""} { if {$interminal == "y"} { eval "exec $xterm -e $command &" }\ else { eval "exec $command &" } } destroy $path } proc prefs {{w .prefs}} { catch {destroy $w} toplevel $w wm title $w "Set Preferences" global file bak auxfiles programs printopts geometry startup n_recent defaultdir searchpath env watchdelay defaultview userconf eval "global $programs" eval "global $auxfiles" eval "global $printopts" bind $w "destroy ." bind $w "destroy $w" bind $w "setprefs $w; destroy $w" bind $w "setprefs $w; destroy $w" bind $w "readprefs $userconf; destroy $w" bind $w "setprefs $w; saveprefs $w" labelentry $w.file "Current file :" 63 $file labelentry $w.searchpath "File search path:" 60 $searchpath label $w.pwd -text "Current directory: [pwd]" label $w.sp -text "" frame $w.page frame $w.page.aux label $w.page.aux.label -text "Aux files:" pack $w.page.aux.label -side top -anchor w checkbutton $w.page.aux.bak -text "bak,~" \ -onvalue "y" -offvalue "n" -variable bak -relief flat pack $w.page.aux.bak -side top -anchor w foreach i $auxfiles { checkbutton $w.page.aux.$i -text $i \ -onvalue "y" -offvalue "n" -variable $i -relief flat pack $w.page.aux.$i -side top -anchor w} checkbutton $w.page.aux.rminclf -text "aux include files" \ -onvalue "y" -offvalue "n" -variable rminclf -relief flat pack $w.page.aux.rminclf -side top -anchor w frame $w.page.print label $w.page.print.label1 -text "Print options:" pack $w.page.print.label1 -side top -anchor w foreach i $printopts { checkbutton $w.page.print.$i -text $i \ -onvalue "y" -offvalue "n" -relief flat pack $w.page.print.$i -side top -anchor w} label $w.page.print.label2 -text "At startup" labelentry $w.page.print.defaultdir "cd into:" 22 $defaultdir label $w.page.print.label3 -text "and open:" radiobutton $w.page.print.startf -text "file dialog" -variable startup -value f radiobutton $w.page.print.startl -text "last file" -variable startup -value l labelentry $w.page.print.nrecent "Number of recent files:" 2 $n_recent checkbutton $w.page.print.interminal -text "Execute commands in xterminal" \ -onvalue "y" -offvalue "n" -relief flat checkbutton $w.page.print.watchfile -text "AutoTeX" \ -onvalue "y" -offvalue "n" -relief flat labelentry $w.page.print.watchdelay "Delay in seconds between checks:" \ 3 $watchdelay label $w.page.print.label4 -text "Default view mode:" radiobutton $w.page.print.dvi -text "dvi" -variable defaultview -value dvi radiobutton $w.page.print.ps -text "ps" -variable defaultview -value ps radiobutton $w.page.print.pdf -text "pdf" -variable defaultview -value pdf pack $w.page.print.label2 $w.page.print.defaultdir $w.page.print.label3\ $w.page.print.startf $w.page.print.startl\ $w.page.print.nrecent $w.page.print.interminal\ $w.page.print.watchfile $w.page.print.watchdelay \ $w.page.print.label4 $w.page.print.dvi $w.page.print.ps $w.page.print.pdf\ -side top -anchor w button $w.page.print.getdefaultdir -text "Set current directory as default" -command " $w.page.print.defaultdir.entry delete 0 end $w.page.print.defaultdir.entry insert end [pwd]" pack $w.page.print.getdefaultdir -side top -anchor e frame $w.page.prog label $w.page.prog.label -text "Programs:" pack $w.page.prog.label -side top -anchor w foreach i $programs { labelentry $w.page.prog.$i "$i:" 20 [eval "format %s $$i"] pack $w.page.prog.$i -side top -anchor e} labelentry $w.page.prog.geometry "geometry:" 20 $geometry pack $w.page.prog.geometry -side top -anchor e button $w.page.prog.getgeometry -text "Get current window geometry" -command " $w.page.prog.geometry.entry delete 0 end $w.page.prog.geometry.entry insert end [wm geometry .]" pack $w.page.prog.getgeometry -side top -anchor e pack $w.page.prog $w.page.aux $w.page.print -pady 6 -side left -anchor n -padx 8 frame $w.buttons button $w.buttons.cancel -text "Cancel" -underline 0 -command "destroy $w" button $w.buttons.ok -text "OK" -underline 0 -command "setprefs $w; destroy $w" button $w.buttons.save -text "Read" -underline 0 -command "readprefs $userconf; destroy $w" button $w.buttons.read -text "Save" -underline 0 -command "setprefs $w; saveprefs $w" pack $w.buttons.save $w.buttons.cancel -side left pack $w.buttons.ok $w.buttons.read -side right pack $w.file $w.searchpath $w.pwd $w.sp -side top -anchor w pack $w.page $w.buttons -side top -fill x } proc readprefs { cfgfile } { global bak auxfiles rminclf programs printopts geometry startup n_recent\ defaultdir searchpath interminal watchfile watchdelay defaultview env eval "global $programs" eval "global $auxfiles" eval "global $printopts" if [file readable $cfgfile] { set rcfile [open $cfgfile r] while {[eof $rcfile] != 1} { gets $rcfile dummy set dummy [string trim $dummy] if { $dummy != "" } { if {[string index $dummy 0] != "#"} {eval "set $dummy" } } } close $rcfile } if {$geometry != ""} { wm geometry . $geometry } } proc setprefs { path } { global file programs geometry n_recent m_recent defaultdir searchpath watchdelay eval "global $programs" if {$file != [$path.file.entry get]} { set file [$path.file.entry get] findfile setfile $file} set searchpath [$path.searchpath.entry get] set geometry [$path.page.prog.geometry.entry get] if {$n_recent != [$path.page.print.nrecent.entry get]} { set n_recent [$path.page.print.nrecent.entry get] if {$n_recent < 0} { set n_recent 0 } if {$m_recent > $n_recent} { set m_recent $n_recent } menufile } set watchdelay [$path.page.print.watchdelay.entry get] if {$watchdelay < 1} { set watchdelay 1 } set defaultdir [$path.page.print.defaultdir.entry get] if {$geometry != ""} { wm geometry . $geometry } foreach i $programs { set $i [$path.page.prog.$i.entry get] } } proc saveprefs { path } { global bak auxfiles rminclf printopts programs geometry startup n_recent defaultdir searchpath interminal watchfile watchdelay defaultview userconf eval "global $programs" eval "global $auxfiles" eval "global $printopts" set rcfile [open $userconf w] puts $rcfile "geometry $geometry" puts $rcfile "# File stuff" puts $rcfile "startup $startup" puts $rcfile "n_recent $n_recent" puts $rcfile "defaultdir $defaultdir" puts $rcfile "searchpath \{$searchpath\}" puts $rcfile "# Which aux files shall be marked for removal (y=yes, n=no)?" puts $rcfile "bak $bak" foreach i $auxfiles { puts $rcfile "$i [eval "format %s $$i"]" } puts $rcfile "rminclf $rminclf" puts $rcfile "# Stuff" puts $rcfile "defaultview $defaultview" puts $rcfile "interminal $interminal" puts $rcfile "# AutoTeX" puts $rcfile "watchfile $watchfile" puts $rcfile "watchdelay $watchdelay" puts $rcfile "# Printing options" foreach i $printopts { puts $rcfile "$i [eval "format %s $$i"]" } puts $rcfile "# Programs" foreach i $programs { puts $rcfile "$i \"[eval "format %s $$i"]\"" } close $rcfile destroy $path } proc print {{w .printdialog}} { catch {destroy $w} toplevel $w wm title $w "Print" bind $w {destroy .} bind $w "destroy $w" bind $w "printit $w" bind $w "printit $w" frame $w.page labelentry $w.page.fpage "First page:" 6 "" labelentry $w.page.lpage "Last page:" 6 "" frame $w.flag checkbutton $w.flag.abspagenumbers -text "page numbers are absolute" \ -onvalue "y" -offvalue "n" -relief flat checkbutton $w.flag.twoup -text "2up" \ -onvalue "y" -offvalue "n" -relief flat checkbutton $w.flag.printtofile -text "print to file" \ -onvalue "y" -offvalue "n" -relief flat frame $w.buttons button $w.buttons.cancel -text "Cancel" -underline 0 -command "destroy $w" button $w.buttons.print -text "Print" -underline 0 -command "printit $w" pack $w.page.fpage $w.page.lpage -side left -padx 5 pack $w.flag.abspagenumbers $w.flag.twoup $w.flag.printtofile -side left pack $w.buttons.print -side right pack $w.buttons.cancel -side left pack $w.page $w.flag $w.buttons -side top -fill x } proc printit { path } { global printopts psnup print dvips fileroot eval "global $printopts" if [file isfile $fileroot.dvi] { set fpflag "-p"; set lpflag "-l"; set tuflag "" if {$abspagenumbers == "y"} {set fpflag "-p ="; set lpflag "-l ="} set fpage [$path.page.fpage.entry get] if {$fpage != ""} {set fpage "$fpflag$fpage"} set lpage [$path.page.lpage.entry get] if {$lpage != ""} {set lpage "$lpflag$lpage"} if {$printtofile == "y"} { if {$twoup == "y"} {exec sh -c "$dvips -o -q $fpage $lpage -f $fileroot.dvi | $psnup > $fileroot.ps" }\ else { exec sh -c "$dvips -o -q $fpage $lpage $fileroot.dvi" } }\ else { if {$twoup == "y"} {exec sh -c "$dvips -o -q $fpage $lpage -f $fileroot.dvi | $psnup | $print" }\ else { exec sh -c "$dvips -o -q $fpage $lpage -f $fileroot.dvi | $print" } } }\ else { tk_messageBox -icon info -title "Warning"\ -message "Please create $fileroot.dvi first." } destroy $path } proc rmaux {{w .rmaux}} { catch {destroy $w} toplevel $w wm title $w "Remove" bind $w {destroy .} bind $w "destroy $w" bind $w "rmit $w" global bak auxfiles includefiles rminclf file fileroot eval "global $auxfiles" frame $w.page if {[file isfile $file.bak] || [file isfile $file~]} { checkbutton $w.page.bak -onvalue "y" -offvalue "n" -relief flat\ -text "[if [file isfile $file~] {format "%s~" $file}] \ [if [file isfile $file.bak] {format "%s.bak" $file}]" pack $w.page.bak -side top -anchor w } foreach i $auxfiles { if [file isfile $fileroot.$i] { checkbutton $w.page.$i -text $fileroot.$i \ -onvalue "y" -offvalue "n" -relief flat pack $w.page.$i -side top -anchor w } } if { $includefiles != "" } { checkbutton $w.page.rminclf -text "Remove aux include files" \ -onvalue "y" -offvalue "n" -relief flat pack $w.page.rminclf -side top -anchor w } frame $w.buttons button $w.buttons.cancel -text "Cancel" -underline 0 -command "destroy $w" button $w.buttons.rm -text "Remove files" -borderwidth 3 -command "rmit $w" pack $w.buttons.rm -side right pack $w.buttons.cancel -side left pack $w.page $w.buttons -side top -fill x } proc rmit {w} { global file fileroot auxfiles bak includefiles rminclf eval "global $auxfiles" if {$bak == "y"} { file delete $file~; file delete $file.bak } foreach i $auxfiles { if { [eval "format %s $$i"] == "y" } { file delete $fileroot.$i } } if { $rminclf == "y" } { foreach i $includefiles { if { $aux == "y" } { file delete $i.aux } if { $bak == "y" } { file delete $i~; file delete $i.bak } } } destroy $w } proc viewaux {{w .viewaux}} { catch {destroy $w} toplevel $w wm title $w "View aux file" bind $w {destroy .} bind $w "destroy $w" global auxfiles fileroot eval "global $auxfiles" foreach i $auxfiles { if {[file isfile $fileroot.$i] && [expr {$i != "dvi"}]} { button $w.$i -text "Edit $fileroot.$i" \ -command "edit $fileroot.$i; destroy $w" pack $w.$i -side top -fill x -anchor w} } button $w.cancel -text "Cancel" -underline 0 -command "destroy $w" pack $w.cancel -side top } proc readrecentfiles {} { global recent m_recent n_recent set m_recent -1 set recent(0) "" if [file readable ~/.xtexsh_recent] { set rcfile [open ~/.xtexsh_recent r] while {[eof $rcfile] != 1 && $m_recent <= $n_recent } { gets $rcfile dummy set dummy [string trim $dummy] if { [file isfile $dummy] } { set m_recent [expr $m_recent+1] set recent($m_recent) $dummy } } close $rcfile } } proc menufile {} { global startup recent m_recent file fileroot includefiles set m .menu.file.m $m delete 0 end $m add command -label "Open" -underline 0 -accelerator -command { filebox } if { $m_recent >= 1 } { $m add cascade -label "Open recent" -underline 7 -menu $m.recent $m.recent delete 0 end set i 1 while { $i <= $m_recent } { $m.recent add command -label [file tail $recent($i) ] -command "setfile $recent($i)" set i [expr $i+1] } } $m add command -label "Edit" -underline 0 -accelerator -command { edit $file } if { $includefiles != "" } { $m add cascade -label "Edit include files" -underline 6 -menu $m.include $m.include delete 0 end $m add cascade -label "Ispell" -underline 0 -menu $m.spell $m.spell delete 0 end $m.spell add command -label $fileroot -command "spell $file" $m.spell add separator foreach i $includefiles { if [file isfile $i ] { set ii $i }\ else { set ii $i.tex } $m.include add command -label [file tail $i] -command "edit $ii" $m.spell add command -label [file tail $i] -command "spell $ii" } } else {\ $m add command -label "Ispell" -underline 0 -accelerator -command { spell $file } } $m add command -label "Print" -underline 0 -accelerator -command { print } $m add command -label "Remove aux files" -underline 0 -accelerator -command { rmaux } $m add command -label "View aux file" -underline 0 -command { viewaux } $m add command -label "Execute command" -underline 1 -accelerator -command { execute } $m add command -label "Open Shell" -underline 5 -accelerator -command { eval "exec $xterm &" } $m add separator $m add command -label "Preferences" -underline 3 -accelerator -command { prefs } $m add separator $m add command -label "Quit" -underline 0 -accelerator -command "destroy ." } # # Main program # bind . {destroy .} bind . {edit $file} bind . {texit} bind . {spell $file} bind . {filebox} bind . {prefs} bind . {message $help_msg Help} bind . {message $help_msg Help} bind . {bibtex} bind . {makeindex} bind . {bibtex} bind . {print} bind . {rmaux} bind . {view} bind . {execute} bind . {eval "exec $xterm &"} # Read the preferences and recent files readprefs $allconf readprefs $userconf if { $n_recent < 0 } { set n_recent 0 } readrecentfiles # Create main frame frame .menu -relief raised -bd 2 # Process the arguments and create the file menu menubutton .menu.file -text "File" -underline 0 -menu .menu.file.m menu .menu.file.m menu .menu.file.m.recent menu .menu.file.m.include menu .menu.file.m.spell # Create some default entries set m .menu.file.m $m add command -label "Open" -underline 0 -accelerator -command { filebox } $m add command -label "Execute command" -underline 1 -accelerator -command { execute } $m add command -label "Open Shell" -underline 5 -accelerator -command { eval "exec $xterm &" } $m add separator $m add command -label "Preferences" -underline 3 -accelerator -command { prefs } $m add separator $m add command -label "Quit" -underline 0 -accelerator -command "destroy ." if $argc>0 {set file [lindex $argv 0]} else {set file ""} if {[string range $file 0 1] == "-r"} { if {[catch {set i [expr [string range $file 2 end]]}] ==1} {set i 0} if {$i > $m_recent} {set i 0} set file $recent($i) } set path [file dirname $file] if [file isdirectory $path] { cd $path set file [file tail $file] } else { puts stdout "xtexsh: [pwd]/$path: No such directory" } if [file isdirectory $file ] {cd $file; set file ""} set ext [file extension $file ] foreach i $auxfiles { if { ".$i" == $ext } { set file [file rootname $file] } } if {[findfile] == 0 } { if {$file != ""} {tk_messageBox -icon info -title "Warning"\ -message "New file [pwd]/$file" } } if {$file != "" } { setfile $file }\ else { if { $startup == "l" && $m_recent >= 0 } { setfile $recent(0) }\ else { if {$defaultdir != ""} {cd $defaultdir} filebox } } # Typeset menu set m .menu.typeset.m menubutton .menu.typeset -text "Typeset" -underline 0 -menu $m menu $m $m add command -label "TeX" -underline 0 -accelerator -command { texit } $m add cascade -label "TeX command" -underline 4 -menu $m.radiotex $m add checkbutton -label "AutoTeX" -onvalue "y" -offvalue "n" -variable watchfile $m add separator $m add command -label "Bibtex" -underline 0 -accelerator -command { bibtex } $m add command -label "Makeindex" -underline 0 -accelerator -command { makeindex } $m add separator $m add command -label "Create PS" -underline 0 -command { dvips } $m add command -label "PS2PDF" -underline 2 -command { ps2pdf } $m add separator $m add command -label "View" -underline 0 -accelerator -command { view } $m add cascade -label "Default view" -underline 11 -menu $m.radioview $m add command -label "View DVI" -underline 5 -command { viewdvi } $m add command -label "View PS" -underline 5 -command { viewps } $m add command -label "View PDF" -underline 7 -command { viewpdf } set mm $m.radiotex menu $mm $mm add radio -label "tex" -variable tex -value tex $mm add radio -label "latex" -variable tex -value latex $mm add radio -label "pdftex" -variable tex -value pdftex $mm add radio -label "pdflatex" -variable tex -value pdflatex $mm add separator $mm add command -label "Choose custom" -command { prefs } $mm add separator set mm $m.radioview menu $mm $mm add radio -label "dvi" -variable thisview -value dvi $mm add radio -label "ps" -variable thisview -value ps $mm add radio -label "pdf" -variable thisview -value pdf # Help menue set m .menu.help.m menubutton .menu.help -text "Help" -menu $m -underline 0 menu $m $m add command -label "About" -underline 0 -command { tk_messageBox -icon info -title "About TeX Shell"\ -message "xTeX Shell - Version: 1.4-2 by Gerald Teschl" -type ok -parent . } $m add command -label "Help" -underline 0 -accelerator -command { message $help_msg Help } $m add command -label "License" -underline 0 -command { message $license_msg License } # Pack the menus pack .menu.help -side right pack .menu.file .menu.typeset -side left button .edit -text "Edit" -underline 0 -command { edit $file } button .tex -text "TeX" -underline 0 -command { texpress } button .dvi -text "View" -underline 0 -command { view } button .print -text "Print" -underline 0 -command { print } button .quit -text "Quit" -underline 0 -command { destroy . } pack .menu -side top -fill x pack .edit -side left pack .tex -side left pack .dvi -side left pack .print -side left pack .quit -side right