use clap::{Arg, ArgAction, ArgMatches, Command};
fn build_app() -> Command {
Command::new("cargo pixel")
.author("zipxing@hotmail.com")
.about("RustPixel cargo tools")
.arg(Arg::new("pixel"))
.subcommand(common_arg(
Command::new("run")
.alias("r")
.about("Run RustPixel projects and tools")
.arg(Arg::new("mod_name").required(true))
.arg(
Arg::new("build_type")
.required(true)
.value_parser(["t", "w", "g", "wg", "term", "web", "wgpu"]),
)
.arg(Arg::new("other").action(ArgAction::Append)),
))
.subcommand(common_arg(
Command::new("build")
.alias("b")
.about("Build RustPixel projects for different targets")
.arg(Arg::new("mod_name").required(true))
.arg(
Arg::new("build_type")
.required(true)
.value_parser(["t", "w", "g", "wg", "term", "web", "wgpu"]),
),
))
.subcommand(common_arg(
Command::new("creat")
.alias("c")
.about("Create new RustPixel projects from templates")
.arg(Arg::new("mod_name").required(true))
.arg(Arg::new("standalone_dir_name").required(false)),
))
.subcommand(common_arg(
Command::new("convert_gif")
.alias("cg")
.about("Convert GIF animations to SSF sequence frame format")
.arg(Arg::new("gif").required(true))
.arg(Arg::new("ssf").required(true))
.arg(Arg::new("width").required(true))
.arg(Arg::new("height").required(true)),
))
.subcommand(
Command::new("asset")
.alias("a")
.about("Pack images into texture atlas and generate .pix files")
.arg(
Arg::new("input_folder")
.help("Folder containing images to pack")
.required(false)
.index(1),
)
.arg(
Arg::new("output_folder")
.help("Folder where output files will be written")
.required(false)
.index(2),
),
)
.subcommand(
Command::new("edit")
.alias("e")
.about("Run RustPixel image/sprite editor")
.arg(
Arg::new("mode")
.help("Running mode")
.required(false)
.value_parser(["t", "w", "g", "wg", "term", "web", "wgpu"])
.index(1),
)
.arg(
Arg::new("work_dir")
.help("Working directory")
.required(false)
.index(2),
)
.arg(
Arg::new("image_file")
.help("Image file to edit")
.required(false)
.index(3),
),
)
.subcommand(
Command::new("petii")
.alias("p")
.about("Convert images to PETSCII art")
.arg(
Arg::new("image_file")
.help("Input image file path")
.required(true)
.index(1),
)
.arg(
Arg::new("width")
.help("Output width in characters (default: 40)")
.required(false)
.index(2),
)
.arg(
Arg::new("height")
.help("Output height in characters (default: 25)")
.required(false)
.index(3),
)
.arg(
Arg::new("is_petscii")
.help("Use PETSCII characters: true/false (default: false)")
.required(false)
.index(4),
)
.arg(
Arg::new("crop_x")
.help("Crop start X coordinate (requires all crop params)")
.required(false)
.index(5),
)
.arg(
Arg::new("crop_y")
.help("Crop start Y coordinate")
.required(false)
.index(6),
)
.arg(
Arg::new("crop_width")
.help("Crop width")
.required(false)
.index(7),
)
.arg(
Arg::new("crop_height")
.help("Crop height")
.required(false)
.index(8),
),
)
.subcommand(
Command::new("ssf")
.alias("sf")
.about("Run SSF sequence frame player (fixed wgpu mode)")
.arg(
Arg::new("work_dir")
.help("Working directory")
.required(false)
.index(1),
)
.arg(
Arg::new("ssf_file")
.help("SSF file path (optional)")
.required(false)
.index(2),
),
)
.subcommand(
Command::new("symbol")
.alias("sy")
.about("Extract symbols/characters from images")
.arg(
Arg::new("image_file")
.help("Input image file path")
.required(false)
.index(1),
)
.arg(
Arg::new("symsize")
.help("Symbol size in pixels (e.g., 8 for 8x8 symbols)")
.required(false)
.index(2),
)
.arg(
Arg::new("start_x")
.help("Start X coordinate for processing area")
.required(false)
.index(3),
)
.arg(
Arg::new("start_y")
.help("Start Y coordinate for processing area")
.required(false)
.index(4),
)
.arg(
Arg::new("width")
.help("Width of processing area")
.required(false)
.index(5),
)
.arg(
Arg::new("height")
.help("Height of processing area")
.required(false)
.index(6),
),
)
.subcommand(
Command::new("ttf")
.alias("tt")
.about("Convert TTF font files to PNG character atlas")
.arg(
Arg::new("ttf_file")
.help("Input TTF font file path")
.required(false)
.index(1),
)
.arg(
Arg::new("output_file")
.help("Output PNG file path (default: font_atlas.png)")
.required(false)
.index(2),
)
.arg(
Arg::new("size")
.help("Character size in pixels (default: 16)")
.required(false)
.index(3),
)
.arg(
Arg::new("chars_per_row")
.help("Number of characters per row (default: 16)")
.required(false)
.index(4),
)
.arg(
Arg::new("verbose")
.help("Show detailed analysis: 0=false, 1=true (default: 0)")
.required(false)
.index(5),
),
)
.subcommand(
Command::new("gen")
.alias("g")
.about("Generate MDPT presentation using AI (Gemini API)")
.arg(
Arg::new("topic")
.help("Presentation topic (e.g., \"Rust语言入门\")")
.required(true)
.index(1),
)
.arg(
Arg::new("img")
.long("img")
.help("Also generate images for each slide")
.action(ArgAction::SetTrue),
),
)
.subcommand(
Command::new("symbols")
.alias("sym")
.about("Generate layered Texture2DArray with mipmap bitmaps for GPU rendering")
.arg(
Arg::new("padding")
.long("padding")
.help("Text character scale factor 0~1 (default: 0.92)")
.default_value("0.92"),
)
.arg(
Arg::new("output")
.short('o')
.long("output")
.help("Output directory (default: current directory)")
.default_value("."),
)
.arg(
Arg::new("font")
.short('f')
.long("font")
.help("Path to TUI font file (TTF/OTF)"),
),
)
}
pub fn common_arg(app: Command) -> Command {
app.arg(
Arg::new("release")
.short('r')
.long("release")
.action(ArgAction::SetTrue),
)
.arg(
Arg::new("webport")
.short('p')
.long("webport")
.default_value("8080"),
)
}
pub fn make_parser() -> ArgMatches {
build_app().get_matches()
}
pub fn make_parser_app() -> Command {
build_app()
}