Skip to main content

A reactive, declarative TUI library for Python — indentation is your layout, state changes re-render for you. Powered by Textual.

Project description

tuikinter

响应式、声明式的现代终端 UI 库。 底层是 Textual,上层是一套极简的 API:用 with 块的缩进表达布局,用 state界面随数据自动刷新

A reactive, declarative TUI library for Python. Indentation is your layout; state changes re-render the UI for you.

import tuikinter as ui

count = ui.state(0)

with ui.App("我的应用") as app:
    with app.col(pady=1):
        ui.label(lambda: f"  计数: {count}")        # 读了 count,count 一变它自动刷新
        with app.row():
            ui.button("-1", on=lambda: count.set(count - 1), variant="error")
            ui.button("+1", on=lambda: count.set(count + 1), variant="success")
    ui.button("退出", on=app.quit)

app.run()

没有一句 .config(text=...),没有手动刷新。count 变了,那个 label 自己就变了。


安装

pip install tuikinter

需要 Python 3.9+。依赖 textual>=0.40

为什么是它

tuikinter 不是又一个 tkinter 克隆。它拿了两个现代 UI 框架的好思想,放进终端:

  • 缩进即布局。 with app.col(): / with app.row(): 的嵌套就是界面的层级。代码长什么样,界面就长什么样——像 Flutter / SwiftUI 那样。
  • 状态驱动。 ui.state(x) 是一个响应式値。渲染函数读了哪些 state,就自动订阅哪些;state 一变,只重渲染用到它的那几个控件——像 Vue / MobX 的自动依赖追踪。

核心概念

state —— 响应式状态

count = ui.state(0)

count.get()                 # 读
count.set(5)                # 写
count.value = 5            # 同上
count.update(lambda v: v+1) # 基于旧値算新値

# state 能直接参与运算和格式化,省掉 .get()
count - 1                   # = count.get() - 1
f"计数: {count}"            # 自动取値

把一个函数传给 ui.label(...)ui.progress(...),它就成了响应式的——函数里读到的 state 一变,控件自动重渲染:

ui.label(lambda: f"你好, {name}!")        # name 变 -> 文本变
ui.progress(lambda: count.get() * 10)     # count 变 -> 进度变

with 块 —— 布局

with ui.App("标题") as app:
    with app.col():      # 竖排 (column)
        ui.label("上")
        ui.label("下")
    with app.row():      # 横排 (row)
        ui.label("左")
        ui.label("右")
app.run()

col / row 接受 padx / pady 调间距。控件创建时自动认领当前 with 块作为父容器,不需要手动传 parent。

控件

工厂函数 说明
ui.label(text) 文本。text 可是字符串,也可是返回字符串的函数(响应式)
ui.button(text, on=fn) 按钮。on= 是点击回调;variant= 可选 default/primary/success/error/warning
ui.entry(state=s) 单行输入。state= 双向绑定;placeholder= / password=True
ui.checkbox(text, state=s) 勾选框。state= 双向绑定到布尔 state;on= 变化回调
ui.progress(value) 进度条。value 可是数字或函数(响应式);total= 默认 100

一个完整例子

import tuikinter as ui

count = ui.state(0)
name = ui.state("Joshua")

with ui.App("演示") as app:
    with app.col(pady=1):
        ui.label(lambda: f"  计数: {count}")
        with app.row():
            ui.button("-1", on=lambda: count.set(count - 1), variant="error")
            ui.button("+1", on=lambda: count.set(count + 1), variant="success")

    with app.row(pady=1):
        ui.label("名字:")
        ui.entry(state=name, placeholder="输入...")
    ui.label(lambda: f"  你好, {name}!")

    ui.progress(lambda: max(0, min(100, count.get() * 10)))
    ui.button("退出", on=app.quit)

app.run()

运行 python examples/demo.py 看实际效果。

许可

MIT License。详见 LICENSE

Project details


Download files

Download the file for your platform. If you're not sure which to choose, learn more about installing packages.

Source Distribution

tuikinter-0.2.0.tar.gz (12.2 kB view details)

Uploaded Source

Built Distribution

If you're not sure about the file name format, learn more about wheel file names.

tuikinter-0.2.0-py3-none-any.whl (9.7 kB view details)

Uploaded Python 3

File details

Details for the file tuikinter-0.2.0.tar.gz.

File metadata

  • Download URL: tuikinter-0.2.0.tar.gz
  • Upload date:
  • Size: 12.2 kB
  • Tags: Source
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/6.2.0 CPython/3.14.4

File hashes

Hashes for tuikinter-0.2.0.tar.gz
Algorithm Hash digest
SHA256 2c83d7668bae1ad255db902adec4c2bb40a90ff678c0ed45dccf9ff55164e6b1
MD5 067637726030eecd85729b46bb8f84c0
BLAKE2b-256 4c2b1a819341d497869d4aaa8bd6867f5b8f56aa8e6695c1d02b8e0f5eeda792

See more details on using hashes here.

File details

Details for the file tuikinter-0.2.0-py3-none-any.whl.

File metadata

  • Download URL: tuikinter-0.2.0-py3-none-any.whl
  • Upload date:
  • Size: 9.7 kB
  • Tags: Python 3
  • Uploaded using Trusted Publishing? No
  • Uploaded via: twine/6.2.0 CPython/3.14.4

File hashes

Hashes for tuikinter-0.2.0-py3-none-any.whl
Algorithm Hash digest
SHA256 e2354b4f1a360812be5715c8bb71427fd616f8f739e55fe13fd56359babe2a69
MD5 652b72178211d4b350d5e5795aae23e8
BLAKE2b-256 9661f29b4d0c5710942e8b8ffde3ee2940db385fc9d5f68ea02d1158f6019558

See more details on using hashes here.

Supported by

AWS Cloud computing and Security Sponsor Datadog Monitoring Depot Continuous Integration Fastly CDN Google Download Analytics Pingdom Monitoring Sentry Error logging StatusPage Status page