媒介
前两天正在逛 Github,偶然看到一个很故意思的项目:PyWebIo。
这是一个 Python 第三方库,可以只用 Python 语言写出一个网页,而且支持 Flask,Django,Tornado 等 web 框架。
甚至,它可以支持数据可视化图表的绘制,还提供了一行函数渲染 Markdown 文本。
那么话不多说,正片开始——
仓库地址:https://github.com/pywebio/PyWebIO
1 利用方法
1.1 安装 Pywebio
打开 CMD,在里面输入以下代码:
如果速度太慢,建议利用国内镜像:
- 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()
复制代码
1.3 输入内容
- 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_text
-
- def bmi():
- height = input("Your Height(cm):", type=FLOAT)
- weight = input("Your Weight(kg):", type=FLOAT)
-
- BMI = weight / (height / 100) ** 2
-
- top_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))
- break
-
- if __name__ == '__main__':
- bmi()
复制代码
2.2 Markdown 编辑器
- from pywebio import start_server
- from pywebio.output import *
- from pywebio.pin import *
- from pywebio.session import set_env, download
- def main():
- """Markdown Previewer"""
- set_env(output_animation=False)
- put_markdown("""# Markdown Live Preview
- The 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 聊天室
[code]import asyncio
from pywebio import start_server
from pywebio.input import *
from pywebio.output import *
from pywebio.session import defer_call, info as session_info, run_async
MAX_MESSAGES_CNT = 10 ** 4
chat_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 eng
async def refresh_msg(my_name):
"""send new message to current session"""
global chat_msgs
last_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 user
put_markdown('`%s`: %s' % m, sanitize=True, scope='msg-box')
# remove expired message
if len(chat_msgs) > MAX_MESSAGES_CNT:
chat_msgs = chat_msgs[len(chat_msgs) // 2:]
last_idx = len(chat_msgs)
async def main():
"""yWebIO chat room
You can chat with everyone currently online.
"""
global chat_msgs
put_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 == ' |