跳到主要内容

用于 iOS 的 Flet

· 阅读需 3 分钟
Feodor Fitsner
Flet 创始人和开发者

🎉 哇哦,Flet 应用现已上架 App Store!🎉

有了 Flet iOS 应用,您可以在 iPhone 或 iPad 上查看 Flet Python 应用的外观和行为,而应用程序本身正在您的计算机上运行。

但这不仅仅是测试手机上的 Flet 应用程序!Flet 移动应用程序本身是用 Python 编写的,其发布到 App Store 是整个 Flet 项目中的一个重要里程碑。这是一个成功的证明,表明您可以仅使用 Python 创建出色的移动应用程序,并将其打包以便在 App Store 中被接受!

按照本指南 开始在 iPhone 或 iPad 上测试您的 Flet 应用程序。探索应用程序、浏览图库、尝试示例项目和应用程序设置。

我要感谢 Kivy 项目 制作了一个 iOS 工具链,我们使用它来编译适用于 iOS 设备的 Python 解释器和依赖项。我们发布了 serious_python 包,用于将 Python 运行时添加到任何 Flutter 应用程序中。

常见问题解答

何时支持 Android?

很快。它现在是我们的首要任务,我们已经开始研究它。

如何将我的 Flet 应用程序打包到 App Store?

我们将提供一个项目模板,用于引导 Flutter 应用程序,并提供指南,说明如何将 Flutter、serious_python 包和您的 Python 应用程序结合在一起,创建一个独立的 iOS 应用程序并将其发布到 App Store。

今年晚些时候,我们将创建一个 CI 管道以完全自动化该过程。

请查看 serious_python 的自述文件,了解如何创建 Flutter 引导程序并打包您的 Python 应用程序以在其中运行。使用 flet_example 项目作为起点。

Flet v0.8.0 发行说明

要在 iOS 上进行测试,您需要将 Flet 安装升级到 v0.8.0。

在 v0.8.0 中 进行了很多更改,并且有一些重大更改。在您升级到 0.8.0 时请耐心等待,并让我们知道您是否遇到任何问题。

尽情享受吧!

滚动控件和主题化

· 阅读需 7 分钟
Feodor Fitsner
Flet创始人兼开发者

Flet 0.7.1 允许开发人员从 PageViewColumnRowListViewGridView 控件中更改滚动位置接收滚动通知

本次发布还引入了主题改进:

控制滚动位置

可滚动控件 (Page, View, Column, Row, ListViewGridView) 引入了 scroll_to() 方法,以将其滚动位置更改为绝对 offset,相对 delta 或跳转到指定 key 的控件。

通过移动到 key 指定的控件,可以模拟页面书签之间的导航,类似于使用 # 的 HTML href链接:

查看上述示例的源代码

有关控制滚动位置的更多详细信息,请参见 Column.scroll_to

接收滚动通知

所有可滚动的控件现在都提供了 on_scroll 事件处理程序,该处理程序在滚动位置发生变化时触发。通过事件对象的属性,您可以确定滚动操作是否已开始、已结束、改变了方向或滚动位置是否超出了滚动范围(滚动超出)。您还可以获取当前滚动位置的更新以及滚动区域的尺寸,例如:

import flet as ft

def main(page: ft.Page):
def on_column_scroll(e: ft.OnScrollEvent):
print(
f"Type: {e.event_type}, pixels: {e.pixels}, min_scroll_extent: {e.min_scroll_extent}, max_scroll_extent: {e.max_scroll_extent}"
)

cl = ft.Column(
spacing=10,
height=200,
width=200,
scroll=ft.ScrollMode.ALWAYS,
on_scroll=on_column_scroll,
)
for i in range(0, 50):
cl.controls.append(ft.Text(f"Text line {i}", key=str(i)))

page.add(
ft.Container(cl, border=ft.border.all(1)),
)

ft.app(main)

有关滚动通知的更多详细信息,请参见 Column.on_scroll

查看无限滚动示例

颜色方案定制

在此之前,控制应用程序的颜色方案的唯一方法是在创建新的 ft.Theme 对象时指定 color_scheme_seed

本版本允许您根据 Material 设计规范 和 Flet 的各种控件使用的 30 种颜色进行精细调整。

您甚至可以使用 Material Theme Builder 并将导出的颜色调色板应用到您的应用程序,例如:

page.theme = ft.Theme(
color_scheme=ft.ColorScheme(
primary=ft.colors.GREEN,
primary_container=ft.colors.GREEN_200
# ...
),
)

有关更多详细信息,请参见 ColorScheme

嵌套主题

此版本的另一个很棒的功能是嵌套主题!

您可以让应用程序的某个部分使用不同的主题,或者为特定控件覆盖一些主题样式。

还记得 page 对象有 themetheme_mode 属性吗?现在 Container 也有 themetheme_mode 属性!

Container.theme 接受与页面相同的 ft.Theme 对象。在容器中指定 theme_mode 意味着您不想继承父主题,而是希望为容器内的所有控件提供一个全新的、独特的方案。但是,如果容器没有设置 theme_mode 属性,那么其 theme 属性中的样式将覆盖父级继承主题中的样式:

import flet as ft

def main(page: ft.Page):
# 系统(默认)模式的黄色页面主题
page.theme = ft.Theme(
color_scheme_seed=ft.colors.YELLOW,
)

page.add(
# 页面主题
ft.Container(
content=ft.ElevatedButton("Page theme button"),
bgcolor=ft.colors.SURFACE_VARIANT,
padding=20,
width=300,
),

# 继承的主题,覆盖了主要颜色
ft.Container(
theme=ft.Theme(color_scheme=ft.ColorScheme(primary=ft.colors.PINK)),
content=ft.ElevatedButton("Inherited theme button"),
bgcolor=ft.colors.SURFACE_VARIANT,
padding=20,
width=300,
),

# 独特的总是深色主题
ft.Container(
theme=ft.Theme(color_scheme_seed=ft.colors.INDIGO),
theme_mode=ft.ThemeMode.DARK,
content=ft.ElevatedButton("Unique theme button"),
bgcolor=ft.colors.SURFACE_VARIANT,
padding=20,
width=300,
),
)

ft.app(main)

滚动条主题

现在您可以自定义应用程序中滚动条的外观和填充(或使用嵌套主题的特定滚动条)。

可以通过 page.theme.scrollbar_theme 属性来完成,例如:

page.theme = ft.Theme(
scrollbar_theme=ft.ScrollbarTheme(
track_color={
ft.ControlState.HOVERED: ft.colors.AMBER,
ft.ControlState.DEFAULT: ft.colors.TRANSPARENT,
},
track_visibility=True,
track_border_color=ft.colors.BLUE,
thumb_visibility=True,
thumb_color={
ft.ControlState.HOVERED: ft.colors.RED,
ft.ControlState.DEFAULT: ft.colors.GREY_300,
},
thickness=30,
radius=15,
main_axis_margin=5,
cross_axis_margin=10,
)
)

文本主题

Material 3 设计定义了5 组文本样式,每组有 3 种大小:"Display"、"Headline"、"Title"、"Label" 和 "Body",这些样式用于 Flet 控件。现在您可以使用 page.theme.text_theme 自定义每种样式,例如:

import flet as ft

def main(page: ft.Page):
page.theme = ft.Theme(
text_theme=ft.TextTheme(body_medium=ft.TextStyle(color=ft.colors.GREEN))
)

page.add(ft.Text("Hello, green world!"))

ft.app(main)

显然,Body MediumText 控件使用的默认样式。

有关更多详细信息,请参见 TextTheme

标签主题

现在,您可以控制 Tabs 控件的外观和感觉。在此版本中,Tabs 增加了许多新属性,并且有一个新的 page.theme.tabs_theme 属性来设置应用程序中所有标签的样式:

page.theme = ft.Theme(
tabs_theme=ft.TabsTheme(
divider_color=ft.colors.BLUE,
indicator_color=ft.colors.RED,
indicator_tab_size=True,
label_color=ft.colors.GREEN,
unselected_label_color=ft.colors.AMBER,
overlay_color={
ft.ControlState.FOCUSED: ft.colors.with_opacity(0.2, ft.colors.GREEN),
ft.ControlState.DEFAULT: ft.colors.with_opacity(0.2, ft.colors.PINK),
},
)
)

有关更多详细信息,请参见 TabsTheme

其他变化

Flutter 3.10

此 Flet 版本基于 Flutter 3.10,带来了新功能、性能和大小优化。因此,大多数 Flet 依赖项也提升了它们的版本,因此如果您发现任何问题,请告诉我们。

Web 应用中的彩色表情符号

Web 应用中的彩色表情符号支持回来了!在 Flutter 3.7 中,由于其字体大小(8 MB!),"CanvasKit" 渲染器(Flet 中的默认渲染器)中禁用了彩色表情符号,并在 Flutter 3.10 中以可选方式返回。您可以在 server-driven 应用程序中通过 use_color_emoji 参数启用彩色表情符号:

ft.app(main, use_color_emoji=True)

并且在将应用程序发布为静态网站时使用 --use-color-emoji 开关

今天就这些!

升级到最新版本的 Flet 模块(pip install flet --upgrade)并告诉我们您的想法!

画布

· 阅读需 4 分钟
Feodor Fitsner
Flet 创始人兼开发者

释放你的内心艺术家 🧑‍🎨,通过刚刚在 Flet 0.6.0 中发布的全新 Canvas 控件来提升你的 Flet 创意!

Canvas 允许你使用一组基本几何图形("形状")(如线条、圆、弧线、路径和文本)绘制任意图形。我敢打赌,你甚至可以使用 Canvas 控件实现你自己的图表

将 Canvas 与 GestureDetector 结合,你可以获得一个自由绘画应用 - Flet Brush 😀!

示例源码

Canvas 控件位于 flet.canvas 包中。你需要另一个导入才能使用它:

import flet.canvas as cv

以下是一个使用填充和描边 Paint 绘制笑脸的简单程序,使用了 CircleArc 形状:

import math
import flet as ft
import flet.canvas as cv

def main(page: ft.Page):
stroke_paint = paint = ft.Paint(stroke_width=2, style=ft.PaintingStyle.STROKE)
fill_paint = paint = ft.Paint(style=ft.PaintingStyle.FILL)
cp = cv.Canvas(
[
cv.Circle(100, 100, 50, stroke_paint),
cv.Circle(80, 90, 10, stroke_paint),
cv.Circle(84, 87, 5, fill_paint),
cv.Circle(120, 90, 10, stroke_paint),
cv.Circle(124, 87, 5, fill_paint),
cv.Arc(70, 95, 60, 40, 0, math.pi, paint=stroke_paint),
],
width=float("inf"),
expand=True,
)

page.add(cp)

ft.app(main)

文档中了解更多关于 Canvas 的信息,并探索 Canvas 示例

其他更改

富文本支持

Canvas 上绘制文本的工作中,作为对该版本的奖励,我们实现了一个新的 TextSpan 控件,现在可以与 Text.spans 一起使用以输出富文本。

查看富文本示例:

按钮的 url 属性

如果你需要通过点击按钮或任何其他带有 on_click 事件的控件打开一个 URL,你可以直接在 url 中提供该 URL,而无需在代码中使用 page.launch_url() 方法。

不再需要这样:

ft.ElevatedButton("Go to Google", on_click=lambda e: e.page.launch_url("https://google.com"))

只需要这样:

ft.ElevatedButton("前往谷歌", url="https://www.google.com")

新的 url 属性还解决了 Safari 上阻止弹窗的问题

Markdown 中的自动跟随链接

作为 url 属性的延续,Markdown 控件现在可以启用文档中的 URL 自动跟随:

import flet as ft

md = """
[Go to Google](https://www.google.com)
"""

def main(page: ft.Page):
page.add(
ft.Markdown(
md,
extension_set=ft.MarkdownExtensionSet.GITHUB_WEB,
auto_follow_links=True,
)
)

ft.app(main)

更好的 Web 支持

在这个版本中,我们还对Web支持进行了一些改进,例如在page.client_idpage.client_user_agent中捕获用户信息,同时修复了与路由相关的严重的#1333#1289错误。

今天就介绍到这里!

将Flet模块升级到最新版本(pip install flet --upgrade),试用一下画布和富文本,并让我们知道你的想法!

Flet 图表

· 阅读需 3 分钟
Feodor Fitsner
Flet 创始人兼开发者

去年,我们引入了对 Matplotlib 和 Plotly 图表 的支持。两个库都能够将图表导出为 SVG 图像,并在 Flet 应用中显示。然而,这些图表在可视化方面虽然能够满足需求,但缺乏交互性和动画效果。

今天,我们发布了基于出色的 fl_chart 库的内置图表 📊 的 Flet 0.5.2 版本!

我们引入了三个新的图表控件:

折线图(LineChart)

文档 · 示例

柱状图(BarChart)

文档 · 示例

饼图(PieChart)

文档 · 示例

备注

我们花了很多时间研究 fl_chart 库,并尝试以 Flet 的方式实现其大部分功能。然而,如果您发现 Flet 中缺少任何功能,而这些功能在库中可用,请 提交新的功能请求

其他变更

Pyodide 0.23

Pyodide是一个在浏览器中提供Python运行时的工具,用于将Flet应用作为静态网站运行。它已经升级到0.23版本,该版本基于Python 3.11.2,并且带来了一些大小和性能改进

内存泄漏修复

在这个版本中,我们非常关注 Flet 应用中的内存泄漏问题。现在,当用户会话关闭时,其内存会被可靠地释放并进行垃圾回收。这使得 Flet 准备好应用于拥有大量用户的生产应用。

升级 Flet 模块到最新版本(pip install flet --upgrade),尝试一下新图表,并 告诉我们 您的想法!

嘿,Flet 项目 已经达到了 ⭐️ 5000 星 ⭐️ - 感谢大家的持续支持!

使用 Pyodide 构建独立的 Flet Web 应用

· 阅读需 6 分钟
Feodor Fitsner
Flet 创始人和开发者

我们刚刚发布了Flet 0.4.0,它具有一个超级令人兴奋的新功能 - 将 Flet 应用打包成独立的静态网站,可以完全在浏览器中运行!该应用可以发布到任何免费的静态网站托管,如 GitHub Pages 或 Cloudflare Pages。这要归功于 Pyodide - 一个 WebAssembly 的 Python 移植版!

您可以快速构建完全用 Python 编写的精彩单页应用(SPA),并将其托管在任何地方!无需 HTML、CSS 或 JavaScript!

快速示例:使用Pyodide创建Flet应用

安装最新的 Flet 包:

pip install flet --upgrade

创建一个简单的 counter.py 应用:

counter.py
import flet as ft

def main(page: ft.Page):
page.title = "Flet 计数器示例"
page.vertical_alignment = ft.MainAxisAlignment.CENTER

txt_number = ft.TextField(value="0", text_align=ft.TextAlign.RIGHT, width=100)

def minus_click(e):
txt_number.value = str(int(txt_number.value) - 1)
page.update()

def plus_click(e):
txt_number.value = str(int(txt_number.value) + 1)
page.update()

page.add(
ft.Row(
[
ft.IconButton(ft.icons.REMOVE, on_click=minus_click),
txt_number,
ft.IconButton(ft.icons.ADD, on_click=plus_click),
],
alignment=ft.MainAxisAlignment.CENTER,
)
)

ft.app(main)

运行全新的 flet publish 命令,将 Flet 应用发布为静态网站:

flet publish counter.py

网站将发布到与 counter.py 同级的 dist 目录中。 使用内置的Python Web服务器进行测试:

python -m http.server --directory dist

打开浏览器中的 http://localhost:8000 以检查已发布的应用。

以下是一些托管在 Cloudflare Pages 上的实时 Flet 应用:

查看指南 了解更多关于将 Flet 应用发布为独立网站的信息。

Python 中的内置 Fletd 服务器

Flet 0.4.0 还实现了新的 Flet 桌面架构

它用一个轻量级的Python代码替换了Go编写的Fletd服务器,带来了如下优点:

  1. 运行 Flet 应用只需要两个系统进程:Python 解释器和 Flutter 客户端。
  2. 更少的通信开销(减少了 Python 和 Fletd 之间的两次网络跳跃)和更低的延迟(桩代码在 Windows 上使用 TCP,在 macOS/Linux 上使用 Unix 域套接字)。
  3. 默认情况下,桩代码绑定到 Windows 上的 127.0.0.1,更加安全。
  4. 使用 flet pack 生成的独立应用程序包的大小减少了约 8 MB。

该实现还支持 Pyodide(我们不能在浏览器中运行 Go Web 服务器,对吧?),为 iOS 和 Android 支持铺平了道路。

其他更改

  • 所有从 Web URL 加载资源的控件(Image.srcAudio.srcPage.fontsContainer.image_src)现在也可以从本地文件加载资源,方法是提供文件系统中的完整路径,以及通过提供相对路径从 assets 目录中加载资源。对于桌面应用程序,src 属性中的路径可以是以下之一:
    • 相对于 assets 目录的路径,带或不带开始的斜杠,例如:/image.pngimage.png。不应包含工件目录的名称。
    • 计算机文件系统中的绝对路径,例如 C:\projects\app\assets\image.png/Users/john/images/picture.png
    • 完整的 URL,例如 https://mysite.com/images/pic.png
    • 添加 page.on_error = lambda e: print("页面错误:", e.data) 以查看失败的图像。
  • flet Python 包分为两个包:flet-coreflet
  • 用 Poetry 替换 PDM。
  • beartype 已全面移除。

💥 重大更改

  • 默认路由方案从“hash”更改为“path”(应用 URL 末尾没有 /#/)。使用 ft.app(main, route_url_strategy="hash") 可获得原始行为。
  • 独立桌面 Flet 应用中不再支持 OAuth 认证。

异步支持

Flet 应用现在可以编写为异步应用,并与其他 Python 异步库一起使用 asyncio。在 Flet 中自然支持调用协程,因此无需包装它们以同步运行。

要开始使用异步 Flet 应用,您应该使 main() 方法成为 async

import flet as ft

async def main(page: ft.Page):
await page.add_async(ft.Text("Hello, async world!"))

ft.app(main)

阅读指南 了解更多关于编写异步 Flet 应用的信息。

结论

Flet 0.4.0 带来了以下令人兴奋的功能:

  • 使用 Pyodide 构建在浏览器中运行的独立 Web 应用并托管在廉价的托管上。
  • 具有内置 Fletd 服务器的更快和更安全的架构。
  • 异步应用支持。

将 Flet 模块升级到最新版本(pip install flet --upgrade),尝试 flet publish 命令并告诉我们 您的想法!

顺便说一句,Flet 项目 已经达到了 ⭐️ 4.2K 星 ⭐️(仅一个月增加了 1K) - 继续加油!