webview_app
A desktop application combining a web-based UI with native functionality.
Source Code
Path: examples/webview_app/
Features Demonstrated
- Webview integration for desktop apps
- Static file serving
- API endpoints for backend logic
- Server running in background thread
- C library integration (
@cImport) - Cross-platform desktop app development
Prerequisites
This example requires the webview library to be installed on your system.
Architecture
The application combines:
- Backend Server: Runs in a separate thread, serves static files and API endpoints
- Webview Window: Embeds a browser that loads the local server
zig
const App = struct {
server: tk.Server,
server_opts: tk.ServerOptions = .{},
routes: []const tk.Route = &.{
.get("/*", tk.static.dir("public", .{})),
.get("/api/hello", hello),
},
fn hello() ![]const u8 {
return "Hello, world!";
}
};How It Works
1. Create DI Container
zig
const ct = try tk.Container.init(gpa.allocator(), &.{App});
defer ct.deinit();2. Start Server in Background
zig
const server = try ct.injector.get(*tk.Server);
const port = server.http.config.port.?;
const thread = try server.http.listenInNewThread();
defer thread.join();3. Create and Show Webview
zig
const w = c.webview_create(if (builtin.mode == .Debug) 1 else 0, null);
defer _ = c.webview_destroy(w);
_ = c.webview_set_title(w, "Example");
_ = c.webview_set_size(w, 800, 500, c.WEBVIEW_HINT_NONE);
const url = try std.fmt.allocPrintSentinel(
gpa.allocator(),
"http://127.0.0.1:{}",
.{port},
0
);
defer gpa.allocator().free(url);
_ = c.webview_navigate(w, url);
_ = c.webview_run(w); // Blocks until window is closed
server.stop();Routes
Static Files
zig
.get("/*", tk.static.dir("public", .{}))Serves all files from the public/ directory. The frontend HTML/JS/CSS goes here.
API Endpoint
zig
.get("/api/hello", hello)Backend API that the frontend can call.
Frontend Integration
Your frontend JavaScript can call the backend API:
javascript
fetch('/api/hello')
.then(response => response.text())
.then(data => console.log(data));Development vs Production
The webview can show dev tools in debug mode:
zig
const w = c.webview_create(
if (builtin.mode == .Debug) 1 else 0, // 1 = show dev tools
null
);Running
sh
cd examples/webview_app
zig build runA desktop window will open showing your web UI.
Use Cases
This pattern is great for:
- Desktop applications with web UI
- Tools that need native OS integration
- Applications requiring file system access
- Cross-platform GUI apps without heavy frameworks
Architecture Benefits
- Familiar Technologies: Build UI with HTML/CSS/JavaScript
- Backend Power: Full Zig capabilities for system operations
- Small Binary: No Electron overhead
- Native Performance: Direct system access from Zig backend
Next Steps
- Add more API endpoints for your application logic
- Implement file system operations in the backend
- Use WebSockets for real-time communication
- Explore the webview library for more platform-specific features