Metadata-Version: 2.4
Name: pycoode
Version: 1.0.0
Summary: 让做游戏像写一行代码一样简单 —— 基于 pygame 的极简 2D 游戏开发包
Author: pycoode
License: MIT
Project-URL: Homepage, https://github.com/pycoode/pycoode
Project-URL: Documentation, https://github.com/pycoode/pycoode#readme
Keywords: game,pygame,2d,easy,beginner
Classifier: Development Status :: 4 - Beta
Classifier: Intended Audience :: Developers
Classifier: Intended Audience :: Education
Classifier: License :: OSI Approved :: MIT License
Classifier: Programming Language :: Python :: 3
Classifier: Topic :: Games/Entertainment
Requires-Python: >=3.8
Description-Content-Type: text/markdown
Requires-Dist: pygame>=2.0

# pycoode

**让做游戏像写一行代码一样简单。**

`pycoode` 是基于 pygame 的极简 2D 游戏开发包。它替你扛下了所有麻烦事：
窗口创建、中文字体、高 DPI、分辨率适配、游戏循环、输入、精灵、音效、场景管理。
你只需要写游戏逻辑。

## 特性

- **一行起跑** —— `pc.run()` 直接弹窗口；`pc.run(draw=...)` 就能画出东西
- **零适配问题** —— 游戏按设计分辨率（如 800x600）写坐标，窗口任意拉伸自动信箱缩放、不变形不错位；Windows 高 DPI（150% 缩放）自动适配
- **中文开箱即用** —— 自动匹配系统中文字体，`g.text("你好")` 不用准备字体文件
- **输入超简单** —— `g.key_held("space")`、`g.mouse_pressed(1)`，支持方向键/WASD/触屏
- **精灵系统** —— 移动、旋转、缩放、翻转、矩形/圆形碰撞、逐帧动画，`Sprite.solid("red", 50, 50)` 没有美术素材也能开工
- **音效一行播放** —— `pc.play("hit.wav")`、`pc.music("bgm.mp3")`，无声环境自动降级不崩溃
- **场景管理** —— 菜单 / 关卡 / 结算各自一个类，`self.switch(...)` 秒切换
- **跨平台** —— Windows / macOS / Linux，Python 3.8+

## 安装

```bash
pip install pygame pycoode
```

## 30 秒上手

**第 1 行代码：**

```python
import pycoode as pc

pc.run(draw=lambda g: g.text("Hello, pycoode!", 400, 300, size=48,
                             color="gold", center=True))
```

**一个能玩的小游戏（键盘控制 + 碰撞 + 计分）：**

```python
import pycoode as pc

player = pc.Sprite.solid("cyan", 48, 48, 400, 520)
coins, score = [], 0

def update(g, dt):
    global score
    dx = int(g.key_held("right")) - int(g.key_held("left"))
    player.x = pc.clamp(player.x + dx * 420 * dt, 24, 776)
    if pc.chance(dt * 3):
        coins.append(pc.Sprite.solid("gold", 22, 22, pc.rand(30, 770), -20))
    for c in coins:
        c.y += 260 * dt
        if player.collides_with(c):
            c.kill(); score += 1
    coins[:] = [c for c in coins if c.alive and c.y < 640]

def draw(g):
    g.clear("dark")
    for c in coins: c.draw(g)
    player.draw(g)
    g.text(f"得分 {score}", 16, 14, size=28, color="white")

pc.run(update=update, draw=draw, title="接金币")
```

**内置演示**（安装后直接玩）：

```python
import pycoode
pycoode.demo()
```

## API 速查

### 入口

| 写法 | 作用 |
|---|---|
| `pc.run()` | 弹出 800x600 窗口，ESC 退出 |
| `pc.run(update=f, draw=g)` | 带逻辑和绘制 |
| `pc.run(scene=Menu())` | 用场景管理 |
| `pc.run(width=960, height=640, title="...", fps=60, background="dark")` | 常用参数 |
| `pc.run(size="hd")` | 预设窗口大小：`small/md/large/square/hd/fullhd`，也可 `size=(1280,720)` |
| `pc.run(fit_screen=True)` | 窗口自动收缩到你的屏幕内（小笔记本不怕超出屏幕） |
| `pc.run(fullscreen=True, show_fps=True)` | 全屏 / 显示 FPS |
| `pc.run(mouse_visible=False)` | 隐藏鼠标指针 |
| `pc.run(icon="icon.png")` | 窗口图标 |

### 窗口控制（运行时）

| 写法 | 作用 |
|---|---|
| `g.toggle_fullscreen()` | 全屏/窗口切换（快捷键 **F11** 已内置） |
| `g.set_window_size(1024, 768)` | 随时改窗口大小，游戏画面自动缩放适配，逻辑不用动 |
| `g.screen_size` | 当前真实窗口像素大小，如 `(1280, 720)` |
| `g.set_mouse_visible(False)` | 随时隐藏/显示鼠标 |
| `g.width, g.height` | 游戏设计分辨率（画布大小，永远不变） |

### 输入（都接受 "space"/"a"/"up" 等名字）

| 写法 | 作用 |
|---|---|
| `g.key_held("right")` | 按住中 |
| `g.key_pressed("space")` | 本帧刚按下 |
| `g.key_released("esc")` | 本帧刚松开 |
| `g.mouse_x, g.mouse_y` / `g.mouse_pos` | 鼠标坐标（游戏内坐标） |
| `g.mouse_held(1)` / `g.mouse_pressed(1)` | 左键按住 / 刚按下 |
| `g.on_click = lambda x, y, button: ...` | 点击回调 |
| `g.touches` | 触屏触摸点列表 |

### 绘制

| 写法 | 作用 |
|---|---|
| `g.clear("dark")` | 清屏 |
| `g.rect(x, y, w, h, "red", width=0, radius=8)` | 矩形（width=0 实心） |
| `g.border(x, y, w, h, "white", width=2)` | 描边矩形 |
| `g.circle(x, y, r, "orange")` | 圆 |
| `g.ellipse(x, y, w, h, "cyan")` | 椭圆 |
| `g.line(x1, y1, x2, y2, "gold", width=2)` | 线段 |
| `g.polygon([(x,y), ...], "grass")` | 多边形 |
| `g.arc(x, y, r, 0, 3.14)` | 圆弧 |
| `g.text("你好", x, y, size=24, color="white", center=True)` | 文字，返回矩形可做命中检测 |
| `g.image(img, x, y, angle=0, scale=1.0)` | 图片 |

颜色支持 `"red"`、`"#ff0000"`、`(255,0,0)`，另附赠 `dark/gold/orange/cyan/skyblue/grass/brick` 等好看的名字。

### 精灵

```python
s = pc.sprite("hero.png", 400, 300)          # 从图片加载
s = pc.Sprite.solid("red", 50, 50, 400, 300) # 纯色块
s = pc.Sprite("walk.png", frames=4, fps=10)  # 逐帧动画

s.vx, s.vy = 200, -100      # 速度（像素/秒）
s.move(dt)                  # 按速度移动
s.animate(dt)               # 播放动画
s.bounce_in(800, 600)       # 撞墙反弹
s.collides_with(other)      # 矩形碰撞
s.collides_circle(other)    # 圆形碰撞
s.draw(g)                   # 画出来
s.kill()                    # 标记删除（配合 s.alive 过滤）
```

### 音频

```python
pc.play("hit.wav", volume=0.8)   # 音效
pc.music("bgm.mp3")              # 循环 BGM
pc.stop_music() / pc.pause_music() / pc.resume_music()
```

### 场景

```python
class Menu(pc.Scene):
    def draw(self, g):
        g.text("按空格开始", 400, 300, size=36, center=True)
    def update(self, g, dt):
        if g.key_pressed("space"):
            self.switch(Playing())

pc.run(scene=Menu)
```

`self.switch(s)` 换场景、`self.push(s)` 压栈（暂停界面）、`self.pop()` 返回。

### 小工具

`pc.clamp` `pc.lerp` `pc.dist` `pc.rand` `pc.randint` `pc.choice` `pc.chance` `pc.Vector`

## 示例

```bash
python examples/01_hello.py     # 一行代码
python examples/02_bounce.py    # 键盘 + 反弹
python examples/03_catch.py     # 完整小游戏
python examples/04_scene.py     # 场景管理
python examples/05_paint.py     # 鼠标画板
python examples/06_anim.py      # 逐帧动画
python examples/07_window.py    # 窗口大小 / 全屏 / 鼠标控制
```

## 它是怎么做到"零适配"的

1. **虚拟画布**：所有绘制先画在 800x600 的离屏画布上，再整体等比缩放贴到真实窗口（信箱式留边），所以窗口多大、玩家屏幕多稀奇，你的坐标永远对。
2. **高 DPI**：Windows 下自动声明 `per monitor` DPI 感知，笔记本 150% 缩放不再模糊错位。
3. **中文字体**：内置 Windows/macOS/Linux 三平台字体候选链，自动挑选第一个可用的。
4. **无声降级**：没有音频设备时音效函数静默跳过，游戏照常跑。

## 开发与测试

```bash
pip install -e .          # 可编辑安装
python tests/test_headless.py   # 无头测试（SDL dummy 驱动，无需显示器）
```

## 路线图

- [ ] 瓦片地图 / 摄像机跟随
- [ ] 简单物理（重力、平台碰撞）
- [ ] 打包成 exe 的辅助命令
