thisisthepy
Ecosystem생태계 / Projects프로젝트 / pythonx-compose
pythonx

pythonx-compose

Build Compose Multiplatform UIs in Python: Python Declarative UI Framework.Python으로 Compose Multiplatform UI를 만듭니다: Python 선언형 UI 프레임워크.

GitHub · Guide · PyPI

Overview개요

pythonx-compose lets a Python programmer build real Jetpack and Compose Multiplatform interfaces without learning Kotlin first. Composables are Python functions with a decorator, the widgets are Compose's own, the screen is declared with @app, and state is Compose's saved state, readable and writable from anywhere, a notebook cell included.

pythonx-compose는 Python 개발자가 Kotlin을 먼저 배우지 않고 진짜 Jetpack과 Compose Multiplatform 화면을 만들게 합니다. 컴포저블은 데코레이터 붙은 Python 함수이고, 위젯은 Compose 자신의 것이며, 화면은 @app으로 선언하고, 상태는 노트북 셀을 포함해 어디서든 읽고 쓰는 Compose의 저장 상태입니다.

The problem it solves푸는 문제

It began as a lecture, "Python app development", for people who know Python and want to build an app. The lecture's notebook replaces a running app's screen and changes its state one cell at a time. Doing that on a real native UI, not a drawing of one, needs Compose itself to be usable from Python.

시작은 Python을 알고 앱을 만들고 싶은 사람들을 위한 강의 "Python 앱 개발 특강"이었습니다. 강의 노트북은 실행 중인 앱의 화면을 셀 하나씩 바꾸고 상태를 고칩니다. 그림이 아니라 진짜 네이티브 UI에서 그렇게 하려면 Compose 자체를 Python에서 쓸 수 있어야 합니다.

How it works동작 방식

from pythonx.compose.runtime import Composable, app, remember_saveable
from pythonx.compose.material3 import Column, Text, TextField
from pythonx.compose.foundation.text.input import TextFieldState

field = TextFieldState("")

@app
@Composable
def App():
    App.messages = messages = remember_saveable("hello")
    Column(content=lambda: {
        Text(messages.getValue()),
        TextField(state=field),
    })
  • Widgets are androidx's own, reached through python-multiplatform's binder and re-exported by package, with snake_case keywords.
  • The app root is declared with @app; redeclaring it replaces the screen. There is no update function.
  • State comes from remember_saveable, Compose's rememberSaveable, so it survives rotation and process death. The notebook reads and writes it as main.App.messages.getValue() and setValue(...).
  • Text input stays inside Compose: TextField takes a TextFieldState, so input-method composition never round-trips through Python per keystroke.
from pythonx.compose.runtime import Composable, app, remember_saveable
from pythonx.compose.material3 import Column, Text, TextField
from pythonx.compose.foundation.text.input import TextFieldState

field = TextFieldState("")

@app
@Composable
def App():
    App.messages = messages = remember_saveable("hello")
    Column(content=lambda: {
        Text(messages.getValue()),
        TextField(state=field),
    })
  • 위젯은 androidx 자신의 것이고, python-multiplatform의 바인더로 닿아 패키지 단위로 다시 내보내며, 키워드는 snake_case입니다.
  • 앱 루트는 @app으로 선언하고, 다시 선언하면 화면이 바뀝니다. 업데이트 함수는 없습니다.
  • 상태는 Compose의 rememberSaveable인 remember_saveable에서 와서 화면 회전과 프로세스 종료 뒤에도 살아남습니다. 노트북은 main.App.messages.getValue()와 setValue(...)로 읽고 씁니다.
  • 글자 입력은 Compose 안에 머뭅니다. TextField가 TextFieldState를 받아서 입력기 조합이 키마다 Python을 오가지 않습니다.

Design decisions설계 결정

  • The notebook is the specification, in its own spelling: main.App.messages.getValue() and setValue(), with .value as an alias.
  • Declared, not updated. No update function, by the maintainer's decision.
  • A real package over real Compose. pythonx.compose never renames androidx; it arranges it.
  • One namespace. pythonx is a namespace package shared with every other pythonx library.
  • 노트북이 스펙이고 노트북의 표기 그대로입니다. main.App.messages.getValue()와 setValue(), 별칭 .value.
  • 갱신하지 않고 선언한다. 메인테이너의 결정으로 업데이트 함수는 없습니다.
  • 진짜 Compose 위의 진짜 패키지. pythonx.compose는 androidx의 이름을 바꾸지 않고 정리만 합니다.
  • 하나의 네임스페이스. pythonx는 다른 모든 pythonx 라이브러리와 함께 쓰는 네임스페이스 패키지입니다.

Where it fits생태계 안의 위치

It runs on python-multiplatform's binder and Compose host. Coroutine scopes for UI work come from pythonx-concurrent; Material 3 and its design system come through compose-multiplatform-core-extended; 3D views from pythonx-graphics sit inside its layouts.

python-multiplatform의 바인더와 Compose 호스트 위에서 돕니다. UI 작업용 코루틴 스코프는 pythonx-concurrent에서, Material 3와 디자인 시스템은 compose-multiplatform-core-extended에서 오고, pythonx-graphics의 3D 화면은 이 레이아웃 안에 들어갑니다.

Where it stands현재 상태

Verified: the lecture notebook runs end to end from an installed wheel against the real Compose jars, 20 scenarios pixel-equal to the same UI written in Kotlin, including Korean input composition. Published: 0.1.0a1; 0.1.0a2 prepared.

검증: 강의 노트북이 설치된 wheel로 진짜 Compose jar 위에서 처음부터 끝까지 돌고, 시나리오 20개가 Kotlin으로 쓴 같은 UI와 픽셀까지 같으며 한글 입력 조합도 포함합니다. 배포: 0.1.0a1, 0.1.0a2 준비.

Future design미래 설계

  • Coroutine scopes (DefaultCoroutineScope, MainCoroutineScope) on pythonx-concurrent.
  • Material 3 colour schemes and the ecosystem's design system.
  • Live editing of a running app from a notebook as the normal way to build UI.
  • pythonx-concurrent 위의 코루틴 스코프(DefaultCoroutineScope, MainCoroutineScope).
  • Material 3 색 구성표와 생태계의 디자인 시스템.
  • 노트북에서 실행 중인 앱을 고치는 것이 UI를 만드는 평범한 방법이 되는 것.

Roadmap로드맵

  1. 0.1.0a2: notebook spelling, remember_saveable.
  2. 0.1.0b1, 2026-11-20: the whole lecture notebook from PyPI.
  1. 0.1.0a2: 노트북 표기, remember_saveable.
  2. 0.1.0b1, 2026-11-20: 강의 노트북 전체를 PyPI에서.