Below is a short script illustrating wrapping a Tcl application into a single file executable.
The example uses wish on Windows. Other platforms would be very similar.
For non-GUI apps, use a tclsh and omit copying of tk_library
.
The example uses the running program as the template for the target
executable. This must be a statically linked wish or tclsh. Alternatively, for
example using tclsh to build a wish-based application, or to use a non-static
shell to run the script, pass the (static) template executable as an additional
argument to zipfs mkimg
. You can find x86 and x64 static tclsh/wish
executables in the magicsplat download
site.
The example generates a main.tcl
at the top of the VFS. Normally, you
would copy your application's main.tcl there. This is responsible for all
initialization including setting up auto_path
appropriately so packages
copied into the zip are found by package require
.
Note one difference from Tcl 8.6 tclkits. Unlike 8.6 tclkits, 9.0 "zipkits"
still set up search paths using TCLLIBPATH
etc. If you do not want this,
you need to explicitly modify auto_path
, tm
paths etc. in your main.tcl
Run the script below as wish90s scriptname
...
# Make sure we are running a static wish
set exe_path [zipfs mount //zipfs:/app]
if {$exe_path eq ""} {
pack [ttk::label .e -text "Please use a static wish to make single-file exes!"]
pack [ttk::button .b -text Exit -command exit]
return
}
pack [ttk::label .l -text "Building twapi single file exe. Please wait ..."]
tk::PlaceWindow .
update
file delete -force twapi.vfs
file mkdir twapi.vfs
file copy $tcl_library [file join twapi.vfs tcl_library]
file copy $tk_library [file join twapi.vfs tk_library]
file mkdir [file join twapi.vfs lib]
file copy C:/Tcl/magic/lib/twapi5.0.2 [file join twapi.vfs lib twapi5.0.2]
writeFile [file join twapi.vfs main.tcl] {
lappend auto_path //zipfs:/app/lib
package require twapi
console show
puts "Twapi [twapi::get_version]"
}
zipfs mkimg twapi.exe twapi.vfs twapi.vfs "" $exe_path
.l configure -text "Done."
pack [ttk::button .b -text Exit -command exit]