当前位置: 首页 > news >正文

【Python】PyWebIO 初体验:用 Python 写网页

目录

    • 前言
    • 1 使用方法
      • 1.1 安装 Pywebio
      • 1.2 输出内容
      • 1.3 输入内容
    • 2 示例程序
      • 2.1 BMI 计算器
      • 2.2 Markdown 编辑器
      • 2.3 聊天室
      • 2.4 五子棋

前言

前两天正在逛 Github,偶然看到一个很有意思的项目:PyWebIo

这是一个 Python 第三方库,可以只用 Python 语言写出一个网页,而且支持 Flask,Django,Tornado 等 web 框架。

甚至,它可以支持数据可视化图表的绘制,还提供了一行函数渲染 Markdown 文本。

那么话不多说,正片开始——

仓库地址:https://github.com/pywebio/PyWebIO

1 使用方法

1.1 安装 Pywebio

打开 CMD,在里面输入以下代码:

pip install pywebio

如果速度太慢,建议使用国内镜像:

pip install -i https://pypi.tuna.tsinghua.edu.cn/simple pywebio

1.2 输出内容

  • put_text() 输出文字
  • put_table() 输出表格
  • put_markdown() 输出 markdown 内容
  • put_file() 输出文件下载链接
  • put_image() 输出图片
  • put_button() 输出按钮

请看示例程序:

from pywebio.output import *def main():# 文本输出put_text("Hello world!")# 表格输出put_table([['商品', '价格'],['苹果', '5.5'],['香蕉', '7'],])# Markdown输出put_markdown('~~删除线~~')# 文件输出put_file('hello_word.txt', b'hello word!')if __name__ == '__main__':main()

pkzLkTI.png

1.3 输入内容

  • input() 和 python 一样的函数欸
from pywebio.input import *def main():name = input("请输入你的名字:")if __name__ == '__main__':main()

2 示例程序

这些都是官方给出的实例,代码都不到 100 行!

官方项目地址:https://pywebio-demos.pywebio.online/

2.1 BMI 计算器

from pywebio.input import input, FLOAT
from pywebio.output import put_textdef bmi():height = input("Your Height(cm):", type=FLOAT)weight = input("Your Weight(kg):", type=FLOAT)BMI = weight / (height / 100) ** 2top_status = [(14.9, 'Severely underweight'), (18.4, 'Underweight'),(22.9, 'Normal'), (27.5, 'Overweight'),(40.0, 'Moderately obese'), (float('inf'), 'Severely obese')]for top, status in top_status:if BMI <= top:put_text('Your BMI: %.1f, category: %s' % (BMI, status))breakif __name__ == '__main__':bmi()

2.2 Markdown 编辑器

from pywebio import start_serverfrom pywebio.output import *
from pywebio.pin import *
from pywebio.session import set_env, downloaddef main():"""Markdown Previewer"""set_env(output_animation=False)put_markdown("""# Markdown Live PreviewThe online markdown editor with live preview. The source code of this application is [here](https://github.com/wang0618/PyWebIO/blob/dev/demos/markdown_previewer.py).## Write your Markdown""")put_textarea('md_text', rows=18, code={'mode': 'markdown'})put_buttons(['Download content'], lambda _: download('saved.md', pin.md_text.encode('utf8')), small=True)put_markdown('## Preview')while True:change_detail = pin_wait_change('md_text')with use_scope('md', clear=True):put_markdown(change_detail['value'], sanitize=False)if __name__ == '__main__':start_server(main, port=8080, debug=True)

2.3 聊天室

import asynciofrom pywebio import start_server
from pywebio.input import *
from pywebio.output import *
from pywebio.session import defer_call, info as session_info, run_asyncMAX_MESSAGES_CNT = 10 ** 4chat_msgs = []  # The chat message history. The item is (name, message content)
online_users = set()def t(eng, chinese):"""return English or Chinese text according to the user's browser language"""return chinese if 'zh' in session_info.user_language else engasync def refresh_msg(my_name):"""send new message to current session"""global chat_msgslast_idx = len(chat_msgs)while True:await asyncio.sleep(0.5)for m in chat_msgs[last_idx:]:if m[0] != my_name:  # only refresh message that not sent by current userput_markdown('`%s`: %s' % m, sanitize=True, scope='msg-box')# remove expired messageif len(chat_msgs) > MAX_MESSAGES_CNT:chat_msgs = chat_msgs[len(chat_msgs) // 2:]last_idx = len(chat_msgs)async def main():"""PyWebIO chat roomYou can chat with everyone currently online."""global chat_msgsput_markdown(t("## PyWebIO chat room\nWelcome to the chat room, you can chat with all the people currently online. You can open this page in multiple tabs of your browser to simulate a multi-user environment. This application uses less than 90 lines of code, the source code is [here](https://github.com/wang0618/PyWebIO/blob/dev/demos/chat_room.py)", "## PyWebIO聊天室\n欢迎来到聊天室,你可以和当前所有在线的人聊天。你可以在浏览器的多个标签页中打开本页面来测试聊天效果。本应用使用不到90行代码实现,源代码[链接](https://github.com/wang0618/PyWebIO/blob/dev/demos/chat_room.py)"))put_scrollable(put_scope('msg-box'), height=300, keep_bottom=True)nickname = await input(t("Your nickname", "请输入你的昵称"), required=True, validate=lambda n: t('This name is already been used', '昵称已被使用') if n in online_users or n == '📢' else None)online_users.add(nickname)chat_msgs.append(('📢', '`%s` joins the room. %s users currently online' % (nickname, len(online_users))))put_markdown('`📢`: `%s` join the room. %s users currently online' % (nickname, len(online_users)), sanitize=True, scope='msg-box')@defer_calldef on_close():online_users.remove(nickname)chat_msgs.append(('📢', '`%s` leaves the room. %s users currently online' % (nickname, len(online_users))))refresh_task = run_async(refresh_msg(nickname))while True:data = await input_group(t('Send message', '发送消息'), [input(name='msg', help_text=t('Message content supports inline Markdown syntax', '消息内容支持行内Markdown语法')),actions(name='cmd', buttons=[t('Send', '发送'), t('Multiline Input', '多行输入'), {'label': t('Exit', '退出'), 'type': 'cancel'}])], validate=lambda d: ('msg', 'Message content cannot be empty') if d['cmd'] == t('Send', '发送') and not d['msg'] else None)if data is None:breakif data['cmd'] == t('Multiline Input', '多行输入'):data['msg'] = '\n' + await textarea('Message content', help_text=t('Message content supports Markdown syntax', '消息内容支持Markdown语法'))put_markdown('`%s`: %s' % (nickname, data['msg']), sanitize=True, scope='msg-box')chat_msgs.append((nickname, data['msg']))refresh_task.close()toast("You have left the chat room")if __name__ == '__main__':start_server(main, debug=True)

2.4 五子棋

import timefrom pywebio import session, start_server
from pywebio.output import *goboard_size = 15
# -1 -> none, 0 -> black, 1 -> white
goboard = [[-1] * goboard_sizefor _ in range(goboard_size)
]def winner():  # return winner piece, return None if no winnerfor x in range(2, goboard_size - 2):for y in range(2, goboard_size - 2):# check if (x,y) is the win centerif goboard[x][y] != -1 and any([all(goboard[x][y] == goboard[m][n] for m, n in [(x - 2, y), (x - 1, y), (x + 1, y), (x + 2, y)]),all(goboard[x][y] == goboard[m][n] for m, n in [(x, y - 2), (x, y - 1), (x, y + 1), (x, y + 2)]),all(goboard[x][y] == goboard[m][n] for m, n in [(x - 2, y - 2), (x - 1, y - 1), (x + 1, y + 1), (x + 2, y + 2)]),all(goboard[x][y] == goboard[m][n] for m, n in [(x - 2, y + 2), (x - 1, y + 1), (x + 1, y - 1), (x + 2, y - 2)]),]):return ['⚫', '⚪'][goboard[x][y]]session_id = 0          # auto incremented id for each session
current_turn = 0        # 0 for black, 1 for white
player_count = [0, 0]   # count of player for two rolesdef main():"""Online Shared Gomoku GameA web based Gomoku (AKA GoBang, Five in a Row) game made with PyWebIO under 100 lines of Python code."""global session_id, current_turn, goboardif winner():  # The current game is over, reset gamegoboard = [[-1] * goboard_size for _ in range(goboard_size)]current_turn = 0my_turn = session_id % 2my_chess = ['⚫', '⚪'][my_turn]session_id += 1player_count[my_turn] += 1@session.defer_calldef player_exit():player_count[my_turn] -= 1session.set_env(output_animation=False)put_html("""<style> table th, table td { padding: 0px !important;} button {padding: .75rem!important; margin:0!important} </style>""")  # Custom styles to make the board more beautifulput_markdown(f"""# Online Shared Gomoku GameAll online players are assigned to two groups (black and white) and share this game. You can open this page in multiple tabs of your browser to simulate multiple users. This application uses less than 100 lines of code, the source code is [here](https://github.com/wang0618/PyWebIO/blob/dev/demos/gomoku_game.py)Currently online player: {player_count[0]} for ⚫, {player_count[1]} for ⚪. Your role is {my_chess}.""")def set_stone(pos):global current_turnif current_turn != my_turn:toast("It's not your turn!!", color='error')returnx, y = posgoboard[x][y] = my_turncurrent_turn = (current_turn + 1) % 2@use_scope('goboard', clear=True)def show_goboard():table = [[put_buttons([dict(label=' ', value=(x, y), color='light')], onclick=set_stone) if cell == -1 else [' ⚫', ' ⚪'][cell]for y, cell in enumerate(row)]for x, row in enumerate(goboard)]put_table(table)show_goboard()while not winner():with use_scope('msg', clear=True):current_turn_copy = current_turnif current_turn_copy == my_turn:put_text("It's your turn!")else:put_row([put_text("Your opponent's turn, waiting... "), put_loading().style('width:1.5em; height:1.5em')], size='auto 1fr')while current_turn == current_turn_copy and not session.get_current_session().closed():  # wait for next movetime.sleep(0.2)show_goboard()with use_scope('msg', clear=True):put_text('Game over. The winner is %s!\nRefresh page to start a new round.' % winner())if __name__ == '__main__':start_server(main, debug=True, port=8080)


稍微试了试这个第三方库,感觉功能十分的强大。

不只是上面的项目,它还有不同风格,能绘制不同图表,集成web框架。

有了这个库,我们就可以轻松地将 Python 程序展示在网页上,也就是实现使用 Python 开发前端!

本文就到这里,如果喜欢的话别望点赞收藏!拜~

相关文章:

  • 北京网站建设多少钱?
  • 辽宁网页制作哪家好_网站建设
  • 高端品牌网站建设_汉中网站制作
  • 006 | 资本资产定价模型 (CAPM)
  • MySQL学习(20):InnoDB引擎逻辑架构、物理架构
  • Unity入门2——编辑器常用功能
  • 投资 - 什么叫有资金托底
  • 当node节点kubectl 命令无法连接到 Kubernetes API 服务器
  • k8s创建secret并在container中获取secret
  • Spring框架面试总结
  • java最强本地缓存-Caffeine
  • 「数组」随机快速选择 / LeetCode LCR 076(C++)
  • VMWare虚拟机磁盘扩容
  • 【langchain学习】使用LangChain创建具有上下文感知的问答系统
  • 微服务-分布式事务-seata
  • 神经网络:智能时代的基石
  • 再分享API形式调用Dify项目应用
  • 大语言模型生成无人系统(如机械臂、无人机等)可以执行的指令序列
  • 【技术性】Search知识
  • 【刷算法】从上往下打印二叉树
  • git 常用命令
  • HashMap ConcurrentHashMap
  • input实现文字超出省略号功能
  • js
  • leetcode46 Permutation 排列组合
  • LeetCode刷题——29. Divide Two Integers(Part 1靠自己)
  • RxJS: 简单入门
  • Spring Cloud Alibaba迁移指南(一):一行代码从 Hystrix 迁移到 Sentinel
  • vue--为什么data属性必须是一个函数
  • WinRAR存在严重的安全漏洞影响5亿用户
  • 动手做个聊天室,前端工程师百无聊赖的人生
  • 马上搞懂 GeoJSON
  • 如何编写一个可升级的智能合约
  • 实现菜单下拉伸展折叠效果demo
  • 通过几道题目学习二叉搜索树
  • 微信端页面使用-webkit-box和绝对定位时,元素上移的问题
  • 系统认识JavaScript正则表达式
  • 小程序测试方案初探
  • 主流的CSS水平和垂直居中技术大全
  • 2017年360最后一道编程题
  • %@ page import=%的用法
  • (c语言版)滑动窗口 给定一个字符串,只包含字母和数字,按要求找出字符串中的最长(连续)子串的长度
  • (八)c52学习之旅-中断实验
  • (定时器/计数器)中断系统(详解与使用)
  • (论文阅读31/100)Stacked hourglass networks for human pose estimation
  • (牛客腾讯思维编程题)编码编码分组打印下标题目分析
  • (转)http-server应用
  • (转载)从 Java 代码到 Java 堆
  • ***检测工具之RKHunter AIDE
  • .h头文件 .lib动态链接库文件 .dll 动态链接库
  • .Net Web项目创建比较不错的参考文章
  • .Net(C#)自定义WinForm控件之小结篇
  • .NET/C# 将一个命令行参数字符串转换为命令行参数数组 args
  • .net实现客户区延伸至至非客户区
  • /usr/bin/python: can't decompress data; zlib not available 的异常处理
  • :not(:first-child)和:not(:last-child)的用法
  • ??eclipse的安装配置问题!??
  • @RequestBody与@ModelAttribute