Token导航 LogoToken导航

Agent Skill · 开发

playdate-dev(游戏约会开发者)

playdate-dev 用于处理 GitHub 仓库、Issue、Pull Request 和代码协作信息,适合在 Codex、Claude、Cursor、Gemini CLI 中需要围绕仓库状态、代码变更或协作事项进行整理时使用。可结合来源仓库、安装命令和原始 README 继续核验具体用法。安装前建议确认权限范围、维护状态,以及是否会触发联网、命令执行或文件读写。

playdate-dev 是开发类 Agent Skill,可用宿主为 Codex、Claude、Cursor、Gemini CLI,通过GitHub 仓库获取,权限为需要联网;许可证信息还不明确,第三方扫描已通过,按安装量在开发类的 21,746 个 Skill 里排第 18,498。

总安装 333周安装 14GitHub Stars 5下载 116核验 2026-05-01

安装说明

本站只整理中文说明,不托管安装包,也不代用户安装。
GitHub
许可证
unknown

安装方式

通过对话安装

复制提示词发给支持本地命令或 Skills 的 AI 助手,先确认命令和权限,再让它执行。

请帮我安装这个 Agent Skill:playdate-dev(游戏约会开发者)
来源仓库:https://github.com/ckorhonen/claude-skills
仓库路径:skills/playdate-dev
安装命令:
npx skills add https://github.com/ckorhonen/claude-skills --skill playdate-dev
安装前请先检查当前环境是否支持对应 CLI,并向我确认将要执行的命令、安装目录、联网范围和文件读写权限;确认后再执行。

命令行安装

复制命令到本机终端执行。该命令会通过 npx skills 从第三方来源获取 Skill;本站只展示命令,不托管安装包,也不自动执行。

skills.shnpx skills
npx skills add https://github.com/ckorhonen/claude-skills --skill playdate-dev

这个 Skill 是做什么的

开发类 Skill 面向写代码、改代码和排查问题,一般会读写仓库文件,部分还会执行构建或测试命令。

playdate-dev 用于处理 GitHub 仓库、Issue、Pull Request 和代码协作信息,适合在 Playdate 掌机开发项目中协调团队工作流时使用。适用于小型独立游戏开发、硬件适配或 SDK 集成等特定领域协作场景。

通过 npx skills add 命令从个人开发者仓库安装,需确认技能是否稳定及维护频率。建议在使用前查阅原始文档,了解其对 Playdate SDK 的具体支持范围。适用宿主包括 Codex、Claude、Cursor、Gemini CLI,接入前应确认版本、权限和运行环境要求。

来源仓库内路径:skills/playdate-dev

上手步骤

4 步
  1. 1

    确认自己的宿主工具

    公开资料标注支持 Codex、Claude、Cursor、Gemini CLI;先确认自己用的是其中之一,再按对应工具的 Skills 目录放置。

  2. 2

    拿到安装命令

    可以直接复制的命令是 npx skills add https://github.com/ckorhonen/claude-skills --skill playdate-dev;命令里的占位符换成自己的路径或密钥再执行。

  3. 3

    安装后重启宿主

    命令执行完要完全退出宿主工具再打开,让新装的 Skill 被重新扫描到,否则列表里可能看不到。

  4. 4

    按最小权限试用

    它需要需要联网,先在测试目录或测试账号里跑,确认没问题再放到正式项目。

常见问题

6 条

playdate-dev 怎么安装?

在终端执行 npx skills add https://github.com/ckorhonen/claude-skills --skill playdate-dev。装完完全退出宿主工具再打开,让它重新扫描本地 Skill。

playdate-dev 支持哪些 AI 工具?

公开资料标注支持 Codex、Claude、Cursor、Gemini CLI。其他工具只要能读取本地 Skill 目录,一般也能手动放进去,但要自己确认触发方式是否一致。

playdate-dev 需要什么权限?

权限级别是需要联网。该 Skill 可能需要联网访问来源站点、仓库或外部 API;具体网络访问范围需要结合源码和 README 复核。

playdate-dev 是免费的吗?

公开资料没有标注明确许可证,收费和商用限制都无法确认。正式使用前请到来源仓库核对授权说明。

playdate-dev 用的人多吗?

公开数据是累计安装 333 次,近一周安装 14 次,下载 116 次,GitHub 5 星。这些数字来自第三方目录统计,只能当作热度参考,不代表质量或安全性。

playdate-dev 安全吗?

第三方扫描结果为通过,但这只覆盖已知的静态检查项,不能替代自己读一遍源码和安装命令。

值得选的地方和要先想清楚的地方

值得选的地方

  • 同时适配 4 种工具,换客户端不用重新找替代品。
  • 第三方扫描已通过,常见的高风险行为没有命中。

先想清楚的地方

  • 许可证没有明确标注,能不能商用、能不能再分发都不确定。
  • 第三方目录整理,版本更新和行为细节以来源仓库为准。

适不适合你

更适合

  • 已经在用 Codex,想直接扩展它能力的人。
  • 需要处理开发类任务、又不想每次都手写提示词的人。

不太适合

  • 需要明确授权才能用到公司项目里的场景。
  • 需要厂商级技术支持和 SLA 的生产系统。

开发类 Skill 对比

6 个同类
Skill总安装GitHub 星权限许可证扫描
skill-vetter

技能审查员 · OpenClaw

8,779,018986操作浏览器MIT-0通过
ontology

本体论 · OpenClaw

6,636,960576只读MIT-0通过
entra-app-registration

内部应用程序注册 · Codex、Claude

6,631,872764接触敏感数据未明确通过
entra-app-registration

内部应用程序注册 · Codex、Claude

3,757,680201接触敏感数据未明确通过
nano-banana-pro

纳米香蕉专业版 · OpenClaw

3,526,898364接触敏感数据MIT-0有提醒
playdate-dev

游戏约会开发者 · 本页

3335需要联网未明确通过

按安装量取同分类前几名;数字来自第三方目录统计,只作热度参考,不代表质量结论。

SKILL.md 原文

Playdate Dev

Overview

Build Playdate games in Lua using the official Playdate SDK. The Playdate is a small yellow handheld with a 400×240 1-bit display, a physical crank, A/B buttons, and a D-pad. Understanding its constraints and unique input is essential.

Hardware specs:

  • Display: 400×240 pixels, 1-bit (black/white only)
  • Memory: ~16 MB RAM (aim for <8 MB peak usage)
  • CPU: 180 MHz Cortex-M7 (device is slower than simulator — always profile on hardware)
  • Input: A button, B button, D-pad (up/down/left/right), crank, menu button
  • Audio: 44.1kHz stereo, Synth + SamplePlayer APIs
  • Accelerometer: 3-axis, opt-in to save battery

Quick Start Workflow

  1. Clarify the request scope (gameplay goal, target device vs simulator, SDK version, release vs prototype).
  2. Choose inputs and accessibility (buttons, crank, accelerometer; provide non-crank alternatives; respect reduce-flashing setting).
  3. Choose rendering approach (sprites vs immediate draw, image sizes, refresh rate, 1x vs 2x scale).
  4. Implement the core loop (define playdate.update(), update game state, call playdate.graphics.sprite.update() and playdate.timer.updateTimers() when used).
  5. Add metadata and launcher assets (pdxinfo, buildNumber, launcher card and icon sizes).
  6. Test in the Simulator and on hardware (screen legibility, crank feel, audio balance, performance).

Starter Project

  • Copy assets/lua-starter into a new project folder.
  • Keep Source/main.lua and Source/pdxinfo in the source root.
  • Replace placeholder values in pdxinfo and extend the update loop.

Build with:

pdc Source GameName.pdx      # compile to .pdx bundle
# Then open GameName.pdx in the Simulator, or drag to device

Core Game Loop

-- main.lua
import "CoreLibs/object"
import "CoreLibs/graphics"
import "CoreLibs/sprites"
import "CoreLibs/timer"

local gfx <const> = playdate.graphics

-- Game state
local playerX, playerY = 200, 120

function playdate.update()
    -- 1. Handle input
    if playdate.buttonIsPressed(playdate.kButtonLeft) then
        playerX -= 2
    elseif playdate.buttonIsPressed(playdate.kButtonRight) then
        playerX += 2
    end

    -- 2. Handle crank
    local crankDelta = playdate.getCrankChange()  -- degrees since last update
    playerY += crankDelta * 0.1                    -- map crank to movement

    -- 3. Update sprites and timers (required each frame if used)
    gfx.sprite.update()
    playdate.timer.updateTimers()

    -- 4. Draw (if not using sprites)
    gfx.clear()
    gfx.fillCircleAtPoint(playerX, playerY, 10)
end

Input API

Buttons

-- Check if button is held this frame
playdate.buttonIsPressed(playdate.kButtonA)
playdate.buttonIsPressed(playdate.kButtonB)
playdate.buttonIsPressed(playdate.kButtonUp)
playdate.buttonIsPressed(playdate.kButtonDown)
playdate.buttonIsPressed(playdate.kButtonLeft)
playdate.buttonIsPressed(playdate.kButtonRight)

-- Single-frame press/release events
local pressed, released = playdate.getButtonState()
if pressed & playdate.kButtonA ~= 0 then
    -- A was pressed this frame
end

-- Callbacks (simpler for menu-style code)
function playdate.AButtonDown()
    -- A pressed
end
function playdate.AButtonUp()
    -- A released
end

Crank

-- Angle in degrees (0-359.99, clockwise = positive)
local angle = playdate.getCrankPosition()

-- Delta since last frame (positive = clockwise)
local delta = playdate.getCrankChange()

-- Detect if crank is docked (folded away)
if playdate.isCrankDocked() then
    -- Show "pull out crank" hint or use button fallback
end

-- Request dock/undock alerts
playdate.setCrankSoundsDisabled(true)  -- suppress built-in clicks

Accelerometer

-- Must opt-in (saves battery when off)
playdate.startAccelerometer()

-- Read in update()
local x, y, z = playdate.readAccelerometer()
-- x,y,z each in range ~[-1, 1] (1G = 1.0)
-- x: tilt left/right, y: tilt front/back, z: up/down

-- Remember to stop when not needed
playdate.stopAccelerometer()

Graphics

Drawing Modes

local gfx <const> = playdate.graphics

-- Screen is black (0) and white (1) only
gfx.setColor(gfx.kColorBlack)  -- or kColorWhite, kColorClear, kColorXOR
gfx.setImageDrawMode(gfx.kDrawModeFillBlack)  -- for rendering images

-- Immediate drawing (clears each frame)
function playdate.update()
    gfx.clear(gfx.kColorWhite)  -- clear to white
    gfx.drawRect(10, 10, 100, 50)
    gfx.fillRect(20, 20, 80, 30)
    gfx.drawLine(0, 0, 400, 240)
    gfx.drawCircleAtPoint(200, 120, 40)
    gfx.fillCircleAtPoint(200, 120, 40)
    gfx.drawText("Hello Playdate!", 10, 10)
end

Images

-- Load from .png file (must be in Source/)
local img = gfx.image.new("images/player")  -- no extension needed

-- Draw image
img:draw(x, y)
img:drawCentered(x, y)

-- Flip/transform
img:draw(x, y, gfx.kImageFlippedX)

-- Image tables (sprite sheets)
local table = gfx.imagetable.new("images/walk")  -- walk-table-32-32.png format
local frame = table:getImage(frameIndex)  -- 1-indexed

Fonts and Text

-- System fonts
local font = gfx.font.new("fonts/Roobert-10-Bold")  -- SDK includes several
gfx.setFont(font)
gfx.drawText("Score: " .. score, 10, 10)

-- Centered text
gfx.drawTextInRect("Hello!", 0, 100, 400, 30, nil, nil, kTextAlignment.center)

Sprite System

-- Create sprite
local playerSprite = gfx.sprite.new()
playerSprite:setImage(gfx.image.new("images/player"))
playerSprite:moveTo(200, 120)
playerSprite:setZIndex(10)
playerSprite:add()  -- add to sprite list

-- Custom sprite class (OOP pattern)
class('Player').extends(gfx.sprite)

function Player:init()
    Player.super.init(self)
    self:setImage(gfx.image.new("images/player"))
    self:add()
end

function Player:update()
    if playdate.buttonIsPressed(playdate.kButtonRight) then
        self:moveBy(2, 0)
    end
end

-- In playdate.update():
gfx.sprite.update()  -- required every frame

Collision Detection (via Sprites)

-- Set collision rect
playerSprite:setCollideRect(0, 0, playerSprite:getSize())

-- Query collisions after move
local actualX, actualY, cols, len = playerSprite:moveWithCollisions(newX, newY)

-- Collision response
for i = 1, len do
    local col = cols[i]
    print("Hit:", col.other:getTag())  -- other sprite's tag
end

Audio

-- Sample playback
local sfx = playdate.sound.sampleplayer.new("sounds/jump")  -- .wav or .aif
sfx:play()

-- Background music (loops by default)
local music = playdate.sound.fileplayer.new("sounds/bgm")
music:play(0)  -- 0 = loop forever
music:setVolume(0.7)

-- Synthesizer (procedural audio)
local synth = playdate.sound.synth.new(playdate.sound.kWaveformSquare)
synth:setFrequency(440)
synth:setVolume(0.5)
synth:playNote("A4", 0.5, 0.25)  -- note, volume, duration

Timers

import "CoreLibs/timer"

-- One-shot timer (fires after 2000ms)
playdate.timer.performAfterDelay(2000, function()
    print("Two seconds passed!")
end)

-- Repeating timer
local t = playdate.timer.new(500, function()
    -- fires every 500ms
end)
t.repeats = true

-- Value timer (lerp a value over time)
local vt = playdate.timer.new(1000, 0, 100)  -- 1000ms, from 0 to 100
-- In update: use vt.value

-- IMPORTANT: Must call every frame
playdate.timer.updateTimers()

pdxinfo Metadata

# Source/pdxinfo (required)
name=My Game
author=Your Name
description=A short game description
bundleID=com.yourname.mygame
version=1.0.0
buildNumber=1
imagePath=images/
launchSoundPath=sounds/launch
contentWarning=Contains flashing lights

Required launcher assets (put in images/ or configured imagePath):

  • launcher/card.png — 350×155 pixels
  • launcher/card~highlight.png — 350×155 pixels (highlighted state)
  • launcher/icon.png — 32×32 pixels
  • launcher/icon~highlight.png — 32×32 pixels

Performance Tips

  • Target 30fps on device (50fps max, but 30fps is standard)
  • Limit gfx.clear() — use gfx.sprite.update() dirty-rect rendering instead
  • Prefer sprite system for moving objects; avoids full-screen redraws
  • Pool objects — avoid creating new tables/objects every frame
  • Use playdate.display.setRefreshRate(30) if 50fps isn't needed
  • Profile on device — Simulator is 2-3x faster than hardware
-- Check frame time
playdate.display.setRefreshRate(30)

-- Draw FPS overlay (for profiling)
playdate.drawFPS(0, 0)

Accessibility

-- Respect "Reduce Flashing" system setting
if playdate.getReduceFlashing() then
    -- Avoid strobing effects, use slower transitions
end

-- Always provide button fallback for crank actions
if playdate.isCrankDocked() then
    showCrankHint = false  -- hide crank UI hints
    -- Let D-pad substitute for crank
end

Crank UI Indicators

import "CoreLibs/ui"

-- Show built-in crank indicator (hint to pull out crank)
local crankIndicator = playdate.ui.crankIndicator

function playdate.update()
    if playdate.isCrankDocked() then
        crankIndicator:draw()  -- draws in corner
    end
end

Menu Integration

-- Add items to the system pause menu
local menu = playdate.getSystemMenu()

-- Checkmark toggle
local soundItem, err = menu:addCheckmarkMenuItem("Sound", true, function(value)
    soundEnabled = value
end)

-- Options list
local diffItem, err = menu:addOptionsMenuItem("Difficulty", {"Easy","Normal","Hard"}, "Normal", function(value)
    difficulty = value
end)

Save/Load Data

-- Simple key-value store (persists between sessions)
-- Save
local data = {score = 1234, level = 5}
playdate.datastore.write(data)

-- Load
local data = playdate.datastore.read()
if data then
    score = data.score or 0
end

-- Delete save
playdate.datastore.delete()

Common Patterns

Scene Management

-- Simple scene switcher
local currentScene = nil

function switchScene(newScene)
    if currentScene and currentScene.leave then
        currentScene:leave()
    end
    gfx.sprite.removeAll()
    currentScene = newScene
    if currentScene.enter then
        currentScene:enter()
    end
end

-- Define scenes as tables
local titleScene = {}
function titleScene:enter() ... end
function titleScene:update() ... end

-- In playdate.update():
function playdate.update()
    if currentScene and currentScene.update then
        currentScene:update()
    end
    gfx.sprite.update()
    playdate.timer.updateTimers()
end

Crank-Driven Mechanic

-- Accumulate crank ticks for grid-based movement
local TICKS_PER_STEP = 12  -- degrees per step

local crankAccumulator = 0

function playdate.update()
    local delta = playdate.getCrankChange()
    crankAccumulator += delta

    while crankAccumulator >= TICKS_PER_STEP do
        crankAccumulator -= TICKS_PER_STEP
        moveRight()
    end
    while crankAccumulator <= -TICKS_PER_STEP do
        crankAccumulator += TICKS_PER_STEP
        moveLeft()
    end

    -- Button fallback (for docked crank)
    if playdate.buttonJustPressed(playdate.kButtonLeft) then moveLeft() end
    if playdate.buttonJustPressed(playdate.kButtonRight) then moveRight() end
end

Resources

  • references/designing-for-playdate.md — Screen, text, input, audio, UI, launcher guidance
  • references/inside-playdate-lua.md — Full Lua API names, file layout, workflow details
  • assets/lua-starter/ — Starter project template
  • Official SDK Docs — Authoritative Lua API reference
  • SDK Download — Free from Panic
  • Playdate Developer Forum — Community Q&A and examples

平台分布

Codex

33.37%
按下载量换算39

Claude

27.73%
按下载量换算32

Cursor

19.81%
按下载量换算23

Gemini CLI

9.73%
按下载量换算11

安全审计

Gen Agent Trust Hub

通过

Socket

通过

Snyk

通过

权限和风险

需要联网

该 Skill 可能需要联网访问来源站点、仓库或外部 API;具体网络访问范围需要结合源码和 README 复核。

安装前确认

本站仅展示第三方公开信息,不托管安装包,不提供自动安装或运行环境。安装前应自行审查源码、依赖和命令行为。目前只有一个公开来源,建议同时核对源仓库。

继续浏览同类 Skills