anime-prompt-kit 0.1.0__tar.gz

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -0,0 +1,21 @@
1
+ MIT License
2
+
3
+ Copyright (c) 2026 diaozxin007
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.
@@ -0,0 +1,2 @@
1
+ include templates.json index.js cli.js index.test.js package.json
2
+ recursive-include tests *.py
@@ -0,0 +1,131 @@
1
+ Metadata-Version: 2.4
2
+ Name: anime-prompt-kit
3
+ Version: 0.1.0
4
+ Summary: Local anime character prompt templates and composer with a Python API and CLI
5
+ Author: diaozxin007
6
+ License-Expression: MIT
7
+ Project-URL: Homepage, https://ai-anime-generator.io/
8
+ Project-URL: Documentation, https://ai-anime-generator.io/open-source
9
+ Project-URL: Source, https://github.com/diaozxin007/anime-prompt-kit
10
+ Project-URL: Issues, https://github.com/diaozxin007/anime-prompt-kit/issues
11
+ Keywords: anime,prompts,character-design,templates
12
+ Classifier: Programming Language :: Python :: 3
13
+ Classifier: Operating System :: OS Independent
14
+ Requires-Python: >=3.9
15
+ Description-Content-Type: text/markdown
16
+ License-File: LICENSE
17
+ Dynamic: license-file
18
+
19
+ # Anime Prompt Kit
20
+
21
+ Build editable anime character prompts from structured fields. Includes 12 original character concepts and dependency-free JavaScript and Python composers.
22
+
23
+ Made for use with [AI Anime Generator](https://ai-anime-generator.io/) or your preferred image generator. This toolkit assembles text locally; it does not generate images or call an API.
24
+
25
+ ## Python package
26
+
27
+ Requires Python 3.9 or later. Install from [PyPI](https://pypi.org/project/anime-prompt-kit/):
28
+
29
+ ```sh
30
+ python -m pip install anime-prompt-kit
31
+ anime-prompt-kit --list
32
+ anime-prompt-kit sky-courier --setting "a snowy train station"
33
+ python -m anime_prompt_kit moon-librarian
34
+ ```
35
+
36
+ ```python
37
+ from anime_prompt_kit import compose_prompt, from_template, list_templates
38
+
39
+ print(from_template("sky-courier", setting="a snowy train station"))
40
+ print(compose_prompt(subject="adult explorer", setting="forest"))
41
+ ```
42
+
43
+ The Python API and CLI run locally without dependencies, accounts or API keys.
44
+ [Documentation and project overview](https://ai-anime-generator.io/open-source).
45
+
46
+ ## JavaScript quick start
47
+
48
+ Requires Node.js 20 or later. No dependencies, account, or API key required.
49
+
50
+ ```sh
51
+ git clone https://github.com/diaozxin007/anime-prompt-kit.git
52
+ cd anime-prompt-kit
53
+ node cli.js --list
54
+ node cli.js sky-courier
55
+ node cli.js sky-courier --setting "a snowy train station" --composition "full body character sheet"
56
+ ```
57
+
58
+ Example output from `node cli.js sky-courier`:
59
+
60
+ > adult courier with short silver hair and amber eyes, navy flight jacket and brass goggles, holding a folded map, floating harbor at sunrise, anime illustration, clean line art, soft cel shading, soft cinematic lighting, three-quarter portrait
61
+
62
+ Copy the output into [AI Anime Generator](https://ai-anime-generator.io/) to generate an image. The website is a separate service with its own account, credit, and usage terms; running this kit is free.
63
+
64
+ ## Use in JavaScript
65
+
66
+ ```js
67
+ import { composePrompt, fromTemplate } from './index.js';
68
+
69
+ console.log(fromTemplate('moon-librarian', {
70
+ action: 'reading beside a window',
71
+ lighting: 'warm candlelight',
72
+ }));
73
+
74
+ console.log(composePrompt({
75
+ subject: 'adult explorer with dark curls and green eyes',
76
+ outfit: 'teal coat and leather satchel',
77
+ setting: 'a floating botanical garden',
78
+ style: 'anime illustration, soft cel shading',
79
+ }));
80
+ ```
81
+
82
+ Supported fields are `subject`, `outfit`, `action`, `setting`, `style`, `lighting`, and `composition`. Empty fields are omitted. Overrides replace the corresponding field without changing the stored template. Unknown template IDs and non-string field values throw an error.
83
+
84
+ This project is currently distributed through GitHub; no npm install is required.
85
+
86
+ ## Character templates
87
+
88
+ | ID | Concept |
89
+ | --- | --- |
90
+ | `sky-courier` | Sky courier |
91
+ | `forest-botanist` | Forest botanist |
92
+ | `moon-librarian` | Moon librarian |
93
+ | `desert-mechanic` | Desert mechanic |
94
+ | `rain-detective` | Rain detective |
95
+ | `tea-alchemist` | Tea alchemist |
96
+ | `snow-ranger` | Snow ranger |
97
+ | `ocean-cartographer` | Ocean cartographer |
98
+ | `rooftop-musician` | Rooftop musician |
99
+ | `garden-guardian` | Garden guardian |
100
+ | `star-engineer` | Star engineer |
101
+ | `village-baker` | Village baker |
102
+
103
+ The canonical templates live in [`templates.json`](./templates.json), so you can also copy and edit them without using JavaScript.
104
+
105
+ ## Keep a character recognizable
106
+
107
+ 1. Keep the `subject` and signature `outfit` fixed between prompts.
108
+ 2. Change one field at a time, such as `action` or `setting`.
109
+ 3. Keep a record of the model and settings used in your image generator.
110
+ 4. Where supported, use the same reference image to guide later generations.
111
+
112
+ These are text starting points, not a guarantee of character consistency. Different models interpret prompts differently. The included templates have not been individually image-tested; no generated results or performance claims are implied.
113
+
114
+ Python distribution data is copied from `templates.json`; the parity test checks both copies and all 12 JavaScript/Python outputs. Update both JSON files when adding templates.
115
+
116
+ ## Privacy
117
+
118
+ The composer and CLI run locally. They have no network calls, tracking, or credentials. Following a website link opens a separate external service.
119
+
120
+ ## Development and contributions
121
+
122
+ ```sh
123
+ npm test
124
+ PYTHONPATH=python python3 -m unittest discover -s tests -v
125
+ ```
126
+
127
+ Contributions are welcome: add original templates, improve examples, or report bugs through GitHub issues. Include the exact command and Node.js version for bug reports. Keep secrets and private prompts out of issues. Please use original character concepts and do not contribute copyrighted artwork or copied prompt collections.
128
+
129
+ ## License
130
+
131
+ [MIT](./LICENSE), covering the code and included template text.
@@ -0,0 +1,113 @@
1
+ # Anime Prompt Kit
2
+
3
+ Build editable anime character prompts from structured fields. Includes 12 original character concepts and dependency-free JavaScript and Python composers.
4
+
5
+ Made for use with [AI Anime Generator](https://ai-anime-generator.io/) or your preferred image generator. This toolkit assembles text locally; it does not generate images or call an API.
6
+
7
+ ## Python package
8
+
9
+ Requires Python 3.9 or later. Install from [PyPI](https://pypi.org/project/anime-prompt-kit/):
10
+
11
+ ```sh
12
+ python -m pip install anime-prompt-kit
13
+ anime-prompt-kit --list
14
+ anime-prompt-kit sky-courier --setting "a snowy train station"
15
+ python -m anime_prompt_kit moon-librarian
16
+ ```
17
+
18
+ ```python
19
+ from anime_prompt_kit import compose_prompt, from_template, list_templates
20
+
21
+ print(from_template("sky-courier", setting="a snowy train station"))
22
+ print(compose_prompt(subject="adult explorer", setting="forest"))
23
+ ```
24
+
25
+ The Python API and CLI run locally without dependencies, accounts or API keys.
26
+ [Documentation and project overview](https://ai-anime-generator.io/open-source).
27
+
28
+ ## JavaScript quick start
29
+
30
+ Requires Node.js 20 or later. No dependencies, account, or API key required.
31
+
32
+ ```sh
33
+ git clone https://github.com/diaozxin007/anime-prompt-kit.git
34
+ cd anime-prompt-kit
35
+ node cli.js --list
36
+ node cli.js sky-courier
37
+ node cli.js sky-courier --setting "a snowy train station" --composition "full body character sheet"
38
+ ```
39
+
40
+ Example output from `node cli.js sky-courier`:
41
+
42
+ > adult courier with short silver hair and amber eyes, navy flight jacket and brass goggles, holding a folded map, floating harbor at sunrise, anime illustration, clean line art, soft cel shading, soft cinematic lighting, three-quarter portrait
43
+
44
+ Copy the output into [AI Anime Generator](https://ai-anime-generator.io/) to generate an image. The website is a separate service with its own account, credit, and usage terms; running this kit is free.
45
+
46
+ ## Use in JavaScript
47
+
48
+ ```js
49
+ import { composePrompt, fromTemplate } from './index.js';
50
+
51
+ console.log(fromTemplate('moon-librarian', {
52
+ action: 'reading beside a window',
53
+ lighting: 'warm candlelight',
54
+ }));
55
+
56
+ console.log(composePrompt({
57
+ subject: 'adult explorer with dark curls and green eyes',
58
+ outfit: 'teal coat and leather satchel',
59
+ setting: 'a floating botanical garden',
60
+ style: 'anime illustration, soft cel shading',
61
+ }));
62
+ ```
63
+
64
+ Supported fields are `subject`, `outfit`, `action`, `setting`, `style`, `lighting`, and `composition`. Empty fields are omitted. Overrides replace the corresponding field without changing the stored template. Unknown template IDs and non-string field values throw an error.
65
+
66
+ This project is currently distributed through GitHub; no npm install is required.
67
+
68
+ ## Character templates
69
+
70
+ | ID | Concept |
71
+ | --- | --- |
72
+ | `sky-courier` | Sky courier |
73
+ | `forest-botanist` | Forest botanist |
74
+ | `moon-librarian` | Moon librarian |
75
+ | `desert-mechanic` | Desert mechanic |
76
+ | `rain-detective` | Rain detective |
77
+ | `tea-alchemist` | Tea alchemist |
78
+ | `snow-ranger` | Snow ranger |
79
+ | `ocean-cartographer` | Ocean cartographer |
80
+ | `rooftop-musician` | Rooftop musician |
81
+ | `garden-guardian` | Garden guardian |
82
+ | `star-engineer` | Star engineer |
83
+ | `village-baker` | Village baker |
84
+
85
+ The canonical templates live in [`templates.json`](./templates.json), so you can also copy and edit them without using JavaScript.
86
+
87
+ ## Keep a character recognizable
88
+
89
+ 1. Keep the `subject` and signature `outfit` fixed between prompts.
90
+ 2. Change one field at a time, such as `action` or `setting`.
91
+ 3. Keep a record of the model and settings used in your image generator.
92
+ 4. Where supported, use the same reference image to guide later generations.
93
+
94
+ These are text starting points, not a guarantee of character consistency. Different models interpret prompts differently. The included templates have not been individually image-tested; no generated results or performance claims are implied.
95
+
96
+ Python distribution data is copied from `templates.json`; the parity test checks both copies and all 12 JavaScript/Python outputs. Update both JSON files when adding templates.
97
+
98
+ ## Privacy
99
+
100
+ The composer and CLI run locally. They have no network calls, tracking, or credentials. Following a website link opens a separate external service.
101
+
102
+ ## Development and contributions
103
+
104
+ ```sh
105
+ npm test
106
+ PYTHONPATH=python python3 -m unittest discover -s tests -v
107
+ ```
108
+
109
+ Contributions are welcome: add original templates, improve examples, or report bugs through GitHub issues. Include the exact command and Node.js version for bug reports. Keep secrets and private prompts out of issues. Please use original character concepts and do not contribute copyrighted artwork or copied prompt collections.
110
+
111
+ ## License
112
+
113
+ [MIT](./LICENSE), covering the code and included template text.
@@ -0,0 +1,22 @@
1
+ #!/usr/bin/env node
2
+ import { templates, fromTemplate } from './index.js';
3
+ const args = process.argv.slice(2);
4
+ const allowed = new Set(['subject', 'outfit', 'action', 'setting', 'style', 'lighting', 'composition']);
5
+ try {
6
+ if (args.length === 0 || args[0] === '--help') {
7
+ console.log('Usage: node cli.js <template-id> [--field "value"]\n node cli.js --list\nFields: ' + [...allowed].join(', '));
8
+ } else if (args[0] === '--list' && args.length === 1) {
9
+ console.log(templates.map(t => `${t.id}: ${t.name}`).join('\n'));
10
+ } else {
11
+ const overrides = {};
12
+ for (let i = 1; i < args.length; i += 2) {
13
+ const key = args[i].slice(2);
14
+ if (!args[i].startsWith('--') || !allowed.has(key) || args[i + 1] === undefined || args[i + 1].startsWith('--')) throw new Error(`Invalid option: ${args[i]}`);
15
+ overrides[key] = args[i + 1];
16
+ }
17
+ console.log(fromTemplate(args[0], overrides));
18
+ }
19
+ } catch (error) {
20
+ console.error(error.message);
21
+ process.exitCode = 1;
22
+ }
@@ -0,0 +1,16 @@
1
+ import { readFileSync } from 'node:fs';
2
+ export const templates = JSON.parse(readFileSync(new URL('./templates.json', import.meta.url), 'utf8'));
3
+ const fields = ['subject', 'outfit', 'action', 'setting', 'style', 'lighting', 'composition'];
4
+ export function composePrompt(options = {}) {
5
+ if (!options || typeof options !== 'object' || Array.isArray(options)) throw new TypeError('Expected a prompt options object');
6
+ for (const key of fields) {
7
+ if (options[key] !== undefined && typeof options[key] !== 'string') throw new TypeError(`${key} must be a string`);
8
+ }
9
+ return fields.map(key => options[key]?.trim()).filter(Boolean).join(', ');
10
+ }
11
+ export function fromTemplate(id, overrides = {}) {
12
+ const template = templates.find(item => item.id === id);
13
+ if (!template) throw new Error(`Unknown template: ${id}. Use --list to see available templates.`);
14
+ if (!overrides || typeof overrides !== 'object' || Array.isArray(overrides)) throw new TypeError('Expected an overrides object');
15
+ return composePrompt({ ...template, ...overrides });
16
+ }
@@ -0,0 +1,32 @@
1
+ import test from 'node:test';
2
+ import assert from 'node:assert/strict';
3
+ import { spawnSync } from 'node:child_process';
4
+ import { composePrompt, fromTemplate, templates } from './index.js';
5
+ test('all templates have unique IDs and produce complete prompts', () => {
6
+ assert.equal(templates.length, 12);
7
+ assert.equal(new Set(templates.map(t => t.id)).size, 12);
8
+ for (const t of templates) {
9
+ const result = fromTemplate(t.id);
10
+ for (const field of ['subject', 'outfit', 'action', 'setting', 'style', 'lighting', 'composition']) assert.ok(result.includes(t[field]));
11
+ }
12
+ });
13
+ test('overrides preserve identity and do not mutate templates', () => {
14
+ const original = fromTemplate('sky-courier');
15
+ const changed = fromTemplate('sky-courier', { setting: 'a winter station' });
16
+ assert.ok(changed.includes(templates[0].subject));
17
+ assert.ok(changed.includes('a winter station'));
18
+ assert.equal(fromTemplate('sky-courier'), original);
19
+ });
20
+ test('blank fields and invalid inputs', () => {
21
+ assert.equal(composePrompt({ subject: ' pilot ', setting: '' }), 'pilot');
22
+ assert.throws(() => fromTemplate('missing'), /Unknown template/);
23
+ assert.throws(() => composePrompt({ subject: 7 }), TypeError);
24
+ assert.throws(() => fromTemplate('sky-courier', null), TypeError);
25
+ });
26
+ test('CLI supports overrides and rejects incomplete or unknown flags', () => {
27
+ const run = (...args) => spawnSync(process.execPath, ['cli.js', ...args], { cwd: new URL('.', import.meta.url), encoding: 'utf8' });
28
+ assert.equal(run('--list').stdout.trim().split('\n').length, 12);
29
+ assert.ok(run('sky-courier', '--setting', 'winter station').stdout.includes('winter station'));
30
+ assert.equal(run('sky-courier', '--setting').status, 1);
31
+ assert.equal(run('sky-courier', '--unknown', 'x').status, 1);
32
+ });
@@ -0,0 +1,20 @@
1
+ {
2
+ "name": "anime-prompt-kit",
3
+ "version": "0.1.0",
4
+ "private": true,
5
+ "type": "module",
6
+ "description": "Dependency-free anime character prompt templates and composer",
7
+ "engines": {
8
+ "node": ">=20"
9
+ },
10
+ "scripts": {
11
+ "test": "node --test",
12
+ "list": "node cli.js --list"
13
+ },
14
+ "license": "MIT",
15
+ "homepage": "https://ai-anime-generator.io",
16
+ "repository": {
17
+ "type": "git",
18
+ "url": "https://github.com/diaozxin007/anime-prompt-kit.git"
19
+ }
20
+ }
@@ -0,0 +1,30 @@
1
+ [build-system]
2
+ requires = ["setuptools>=77.0.3"]
3
+ build-backend = "setuptools.build_meta"
4
+
5
+ [project]
6
+ name = "anime-prompt-kit"
7
+ version = "0.1.0"
8
+ description = "Local anime character prompt templates and composer with a Python API and CLI"
9
+ readme = "README.md"
10
+ requires-python = ">=3.9"
11
+ license = "MIT"
12
+ license-files = ["LICENSE"]
13
+ authors = [{name = "diaozxin007"}]
14
+ keywords = ["anime", "prompts", "character-design", "templates"]
15
+ classifiers = ["Programming Language :: Python :: 3", "Operating System :: OS Independent"]
16
+
17
+ [project.urls]
18
+ Homepage = "https://ai-anime-generator.io/"
19
+ Documentation = "https://ai-anime-generator.io/open-source"
20
+ Source = "https://github.com/diaozxin007/anime-prompt-kit"
21
+ Issues = "https://github.com/diaozxin007/anime-prompt-kit/issues"
22
+
23
+ [project.scripts]
24
+ anime-prompt-kit = "anime_prompt_kit.cli:main"
25
+
26
+ [tool.setuptools.packages.find]
27
+ where = ["python"]
28
+
29
+ [tool.setuptools.package-data]
30
+ anime_prompt_kit = ["templates.json"]
@@ -0,0 +1,37 @@
1
+ """Compose anime character prompts locally, without network access."""
2
+ import json
3
+ from importlib.resources import files
4
+ from collections.abc import Mapping
5
+
6
+ __version__ = "0.1.0"
7
+ FIELDS = ("subject", "outfit", "action", "setting", "style", "lighting", "composition")
8
+
9
+
10
+ def list_templates():
11
+ """Return fresh template dictionaries; callers cannot mutate stored templates."""
12
+ return json.loads(files(__package__).joinpath("templates.json").read_text(encoding="utf-8"))
13
+
14
+
15
+ def compose_prompt(options=None, **fields):
16
+ """Join nonempty fields in a stable order. Keyword arguments override options."""
17
+ if options is None:
18
+ options = {}
19
+ if not isinstance(options, Mapping):
20
+ raise TypeError("Expected a prompt options mapping")
21
+ values = dict(options, **fields)
22
+ for key in FIELDS:
23
+ if key in values and not isinstance(values[key], str):
24
+ raise TypeError(f"{key} must be a string")
25
+ return ", ".join(values.get(key, "").strip() for key in FIELDS if values.get(key, "").strip())
26
+
27
+
28
+ def from_template(template_id, overrides=None, **fields):
29
+ """Compose a named template, replacing any supplied fields."""
30
+ if overrides is None:
31
+ overrides = {}
32
+ if not isinstance(overrides, Mapping):
33
+ raise TypeError("Expected an overrides mapping")
34
+ template = next((item for item in list_templates() if item["id"] == template_id), None)
35
+ if template is None:
36
+ raise ValueError(f"Unknown template: {template_id}. Use --list to see available templates.")
37
+ return compose_prompt(dict(template, **overrides), **fields)
@@ -0,0 +1,3 @@
1
+ from .cli import main
2
+
3
+ raise SystemExit(main())
@@ -0,0 +1,30 @@
1
+ """Command-line prompt composer."""
2
+ import argparse
3
+ from . import FIELDS, __version__, from_template, list_templates
4
+
5
+
6
+ def main(argv=None):
7
+ parser = argparse.ArgumentParser(description="Compose anime prompts locally; no API key required.")
8
+ parser.add_argument("template", nargs="?")
9
+ parser.add_argument("--list", action="store_true", help="List available templates")
10
+ parser.add_argument("--version", action="version", version=__version__)
11
+ for field in FIELDS:
12
+ parser.add_argument(f"--{field}")
13
+ args = parser.parse_args(argv)
14
+ overrides = {key: getattr(args, key) for key in FIELDS if getattr(args, key) is not None}
15
+ if args.list:
16
+ if args.template or overrides:
17
+ parser.error("--list cannot be combined with a template or overrides")
18
+ for item in list_templates():
19
+ print(f"{item['id']}: {item['name']}")
20
+ return 0
21
+ if not args.template:
22
+ if overrides:
23
+ parser.error("a template is required with field overrides")
24
+ parser.print_help()
25
+ return 0
26
+ try:
27
+ print(from_template(args.template, overrides))
28
+ except (ValueError, TypeError) as error:
29
+ parser.error(str(error))
30
+ return 0
@@ -0,0 +1,134 @@
1
+ [
2
+ {
3
+ "id": "sky-courier",
4
+ "name": "Sky courier",
5
+ "subject": "adult courier with short silver hair and amber eyes",
6
+ "outfit": "navy flight jacket and brass goggles",
7
+ "action": "holding a folded map",
8
+ "setting": "floating harbor at sunrise",
9
+ "style": "anime illustration, clean line art, soft cel shading",
10
+ "lighting": "soft cinematic lighting",
11
+ "composition": "three-quarter portrait"
12
+ },
13
+ {
14
+ "id": "forest-botanist",
15
+ "name": "Forest botanist",
16
+ "subject": "adult botanist with braided brown hair and green eyes",
17
+ "outfit": "linen coat and leather satchel",
18
+ "action": "examining a glowing leaf",
19
+ "setting": "quiet forest greenhouse",
20
+ "style": "anime illustration, clean line art, soft cel shading",
21
+ "lighting": "soft cinematic lighting",
22
+ "composition": "three-quarter portrait"
23
+ },
24
+ {
25
+ "id": "moon-librarian",
26
+ "name": "Moon librarian",
27
+ "subject": "adult librarian with long violet hair and round glasses",
28
+ "outfit": "indigo robe with embroidered stars",
29
+ "action": "carrying an open book",
30
+ "setting": "moonlit library",
31
+ "style": "anime illustration, clean line art, soft cel shading",
32
+ "lighting": "soft cinematic lighting",
33
+ "composition": "three-quarter portrait"
34
+ },
35
+ {
36
+ "id": "desert-mechanic",
37
+ "name": "Desert mechanic",
38
+ "subject": "adult mechanic with curly black hair and copper eyes",
39
+ "outfit": "sand-colored overalls and work gloves",
40
+ "action": "repairing a small robot",
41
+ "setting": "desert workshop",
42
+ "style": "anime illustration, clean line art, soft cel shading",
43
+ "lighting": "soft cinematic lighting",
44
+ "composition": "three-quarter portrait"
45
+ },
46
+ {
47
+ "id": "rain-detective",
48
+ "name": "Rain detective",
49
+ "subject": "adult detective with cropped blue hair and gray eyes",
50
+ "outfit": "charcoal raincoat",
51
+ "action": "holding a transparent umbrella",
52
+ "setting": "rainy city street",
53
+ "style": "anime illustration, clean line art, soft cel shading",
54
+ "lighting": "soft cinematic lighting",
55
+ "composition": "three-quarter portrait"
56
+ },
57
+ {
58
+ "id": "tea-alchemist",
59
+ "name": "Tea alchemist",
60
+ "subject": "adult alchemist with auburn hair and freckles",
61
+ "outfit": "sage apron over a cream shirt",
62
+ "action": "pouring tea into a glass cup",
63
+ "setting": "warm herbal shop",
64
+ "style": "anime illustration, clean line art, soft cel shading",
65
+ "lighting": "soft cinematic lighting",
66
+ "composition": "three-quarter portrait"
67
+ },
68
+ {
69
+ "id": "snow-ranger",
70
+ "name": "Snow ranger",
71
+ "subject": "adult ranger with white braids and brown eyes",
72
+ "outfit": "teal winter coat and wool scarf",
73
+ "action": "watching distant mountains",
74
+ "setting": "snow-covered trail",
75
+ "style": "anime illustration, clean line art, soft cel shading",
76
+ "lighting": "soft cinematic lighting",
77
+ "composition": "three-quarter portrait"
78
+ },
79
+ {
80
+ "id": "ocean-cartographer",
81
+ "name": "Ocean cartographer",
82
+ "subject": "adult cartographer with dark curls and hazel eyes",
83
+ "outfit": "white shirt and blue waistcoat",
84
+ "action": "drawing a sea chart",
85
+ "setting": "sunlit ship cabin",
86
+ "style": "anime illustration, clean line art, soft cel shading",
87
+ "lighting": "soft cinematic lighting",
88
+ "composition": "three-quarter portrait"
89
+ },
90
+ {
91
+ "id": "rooftop-musician",
92
+ "name": "Rooftop musician",
93
+ "subject": "adult musician with pink bobbed hair and dark eyes",
94
+ "outfit": "burgundy jacket and black trousers",
95
+ "action": "playing a violin",
96
+ "setting": "city rooftop at dusk",
97
+ "style": "anime illustration, clean line art, soft cel shading",
98
+ "lighting": "soft cinematic lighting",
99
+ "composition": "three-quarter portrait"
100
+ },
101
+ {
102
+ "id": "garden-guardian",
103
+ "name": "Garden guardian",
104
+ "subject": "adult guardian with dark green hair and golden eyes",
105
+ "outfit": "layered moss-colored cloak",
106
+ "action": "holding a wooden staff",
107
+ "setting": "overgrown stone garden",
108
+ "style": "anime illustration, clean line art, soft cel shading",
109
+ "lighting": "soft cinematic lighting",
110
+ "composition": "three-quarter portrait"
111
+ },
112
+ {
113
+ "id": "star-engineer",
114
+ "name": "Star engineer",
115
+ "subject": "adult engineer with short black hair and blue eyes",
116
+ "outfit": "orange utility suit",
117
+ "action": "inspecting a holographic diagram",
118
+ "setting": "orbital observatory",
119
+ "style": "anime illustration, clean line art, soft cel shading",
120
+ "lighting": "soft cinematic lighting",
121
+ "composition": "three-quarter portrait"
122
+ },
123
+ {
124
+ "id": "village-baker",
125
+ "name": "Village baker",
126
+ "subject": "adult baker with sandy hair and warm brown eyes",
127
+ "outfit": "cream apron and rolled-up sleeves",
128
+ "action": "carrying a basket of bread",
129
+ "setting": "cozy village bakery",
130
+ "style": "anime illustration, clean line art, soft cel shading",
131
+ "lighting": "soft cinematic lighting",
132
+ "composition": "three-quarter portrait"
133
+ }
134
+ ]
@@ -0,0 +1,131 @@
1
+ Metadata-Version: 2.4
2
+ Name: anime-prompt-kit
3
+ Version: 0.1.0
4
+ Summary: Local anime character prompt templates and composer with a Python API and CLI
5
+ Author: diaozxin007
6
+ License-Expression: MIT
7
+ Project-URL: Homepage, https://ai-anime-generator.io/
8
+ Project-URL: Documentation, https://ai-anime-generator.io/open-source
9
+ Project-URL: Source, https://github.com/diaozxin007/anime-prompt-kit
10
+ Project-URL: Issues, https://github.com/diaozxin007/anime-prompt-kit/issues
11
+ Keywords: anime,prompts,character-design,templates
12
+ Classifier: Programming Language :: Python :: 3
13
+ Classifier: Operating System :: OS Independent
14
+ Requires-Python: >=3.9
15
+ Description-Content-Type: text/markdown
16
+ License-File: LICENSE
17
+ Dynamic: license-file
18
+
19
+ # Anime Prompt Kit
20
+
21
+ Build editable anime character prompts from structured fields. Includes 12 original character concepts and dependency-free JavaScript and Python composers.
22
+
23
+ Made for use with [AI Anime Generator](https://ai-anime-generator.io/) or your preferred image generator. This toolkit assembles text locally; it does not generate images or call an API.
24
+
25
+ ## Python package
26
+
27
+ Requires Python 3.9 or later. Install from [PyPI](https://pypi.org/project/anime-prompt-kit/):
28
+
29
+ ```sh
30
+ python -m pip install anime-prompt-kit
31
+ anime-prompt-kit --list
32
+ anime-prompt-kit sky-courier --setting "a snowy train station"
33
+ python -m anime_prompt_kit moon-librarian
34
+ ```
35
+
36
+ ```python
37
+ from anime_prompt_kit import compose_prompt, from_template, list_templates
38
+
39
+ print(from_template("sky-courier", setting="a snowy train station"))
40
+ print(compose_prompt(subject="adult explorer", setting="forest"))
41
+ ```
42
+
43
+ The Python API and CLI run locally without dependencies, accounts or API keys.
44
+ [Documentation and project overview](https://ai-anime-generator.io/open-source).
45
+
46
+ ## JavaScript quick start
47
+
48
+ Requires Node.js 20 or later. No dependencies, account, or API key required.
49
+
50
+ ```sh
51
+ git clone https://github.com/diaozxin007/anime-prompt-kit.git
52
+ cd anime-prompt-kit
53
+ node cli.js --list
54
+ node cli.js sky-courier
55
+ node cli.js sky-courier --setting "a snowy train station" --composition "full body character sheet"
56
+ ```
57
+
58
+ Example output from `node cli.js sky-courier`:
59
+
60
+ > adult courier with short silver hair and amber eyes, navy flight jacket and brass goggles, holding a folded map, floating harbor at sunrise, anime illustration, clean line art, soft cel shading, soft cinematic lighting, three-quarter portrait
61
+
62
+ Copy the output into [AI Anime Generator](https://ai-anime-generator.io/) to generate an image. The website is a separate service with its own account, credit, and usage terms; running this kit is free.
63
+
64
+ ## Use in JavaScript
65
+
66
+ ```js
67
+ import { composePrompt, fromTemplate } from './index.js';
68
+
69
+ console.log(fromTemplate('moon-librarian', {
70
+ action: 'reading beside a window',
71
+ lighting: 'warm candlelight',
72
+ }));
73
+
74
+ console.log(composePrompt({
75
+ subject: 'adult explorer with dark curls and green eyes',
76
+ outfit: 'teal coat and leather satchel',
77
+ setting: 'a floating botanical garden',
78
+ style: 'anime illustration, soft cel shading',
79
+ }));
80
+ ```
81
+
82
+ Supported fields are `subject`, `outfit`, `action`, `setting`, `style`, `lighting`, and `composition`. Empty fields are omitted. Overrides replace the corresponding field without changing the stored template. Unknown template IDs and non-string field values throw an error.
83
+
84
+ This project is currently distributed through GitHub; no npm install is required.
85
+
86
+ ## Character templates
87
+
88
+ | ID | Concept |
89
+ | --- | --- |
90
+ | `sky-courier` | Sky courier |
91
+ | `forest-botanist` | Forest botanist |
92
+ | `moon-librarian` | Moon librarian |
93
+ | `desert-mechanic` | Desert mechanic |
94
+ | `rain-detective` | Rain detective |
95
+ | `tea-alchemist` | Tea alchemist |
96
+ | `snow-ranger` | Snow ranger |
97
+ | `ocean-cartographer` | Ocean cartographer |
98
+ | `rooftop-musician` | Rooftop musician |
99
+ | `garden-guardian` | Garden guardian |
100
+ | `star-engineer` | Star engineer |
101
+ | `village-baker` | Village baker |
102
+
103
+ The canonical templates live in [`templates.json`](./templates.json), so you can also copy and edit them without using JavaScript.
104
+
105
+ ## Keep a character recognizable
106
+
107
+ 1. Keep the `subject` and signature `outfit` fixed between prompts.
108
+ 2. Change one field at a time, such as `action` or `setting`.
109
+ 3. Keep a record of the model and settings used in your image generator.
110
+ 4. Where supported, use the same reference image to guide later generations.
111
+
112
+ These are text starting points, not a guarantee of character consistency. Different models interpret prompts differently. The included templates have not been individually image-tested; no generated results or performance claims are implied.
113
+
114
+ Python distribution data is copied from `templates.json`; the parity test checks both copies and all 12 JavaScript/Python outputs. Update both JSON files when adding templates.
115
+
116
+ ## Privacy
117
+
118
+ The composer and CLI run locally. They have no network calls, tracking, or credentials. Following a website link opens a separate external service.
119
+
120
+ ## Development and contributions
121
+
122
+ ```sh
123
+ npm test
124
+ PYTHONPATH=python python3 -m unittest discover -s tests -v
125
+ ```
126
+
127
+ Contributions are welcome: add original templates, improve examples, or report bugs through GitHub issues. Include the exact command and Node.js version for bug reports. Keep secrets and private prompts out of issues. Please use original character concepts and do not contribute copyrighted artwork or copied prompt collections.
128
+
129
+ ## License
130
+
131
+ [MIT](./LICENSE), covering the code and included template text.
@@ -0,0 +1,19 @@
1
+ LICENSE
2
+ MANIFEST.in
3
+ README.md
4
+ cli.js
5
+ index.js
6
+ index.test.js
7
+ package.json
8
+ pyproject.toml
9
+ templates.json
10
+ python/anime_prompt_kit/__init__.py
11
+ python/anime_prompt_kit/__main__.py
12
+ python/anime_prompt_kit/cli.py
13
+ python/anime_prompt_kit/templates.json
14
+ python/anime_prompt_kit.egg-info/PKG-INFO
15
+ python/anime_prompt_kit.egg-info/SOURCES.txt
16
+ python/anime_prompt_kit.egg-info/dependency_links.txt
17
+ python/anime_prompt_kit.egg-info/entry_points.txt
18
+ python/anime_prompt_kit.egg-info/top_level.txt
19
+ tests/test_python.py
@@ -0,0 +1,2 @@
1
+ [console_scripts]
2
+ anime-prompt-kit = anime_prompt_kit.cli:main
@@ -0,0 +1,4 @@
1
+ [egg_info]
2
+ tag_build =
3
+ tag_date = 0
4
+
@@ -0,0 +1,134 @@
1
+ [
2
+ {
3
+ "id": "sky-courier",
4
+ "name": "Sky courier",
5
+ "subject": "adult courier with short silver hair and amber eyes",
6
+ "outfit": "navy flight jacket and brass goggles",
7
+ "action": "holding a folded map",
8
+ "setting": "floating harbor at sunrise",
9
+ "style": "anime illustration, clean line art, soft cel shading",
10
+ "lighting": "soft cinematic lighting",
11
+ "composition": "three-quarter portrait"
12
+ },
13
+ {
14
+ "id": "forest-botanist",
15
+ "name": "Forest botanist",
16
+ "subject": "adult botanist with braided brown hair and green eyes",
17
+ "outfit": "linen coat and leather satchel",
18
+ "action": "examining a glowing leaf",
19
+ "setting": "quiet forest greenhouse",
20
+ "style": "anime illustration, clean line art, soft cel shading",
21
+ "lighting": "soft cinematic lighting",
22
+ "composition": "three-quarter portrait"
23
+ },
24
+ {
25
+ "id": "moon-librarian",
26
+ "name": "Moon librarian",
27
+ "subject": "adult librarian with long violet hair and round glasses",
28
+ "outfit": "indigo robe with embroidered stars",
29
+ "action": "carrying an open book",
30
+ "setting": "moonlit library",
31
+ "style": "anime illustration, clean line art, soft cel shading",
32
+ "lighting": "soft cinematic lighting",
33
+ "composition": "three-quarter portrait"
34
+ },
35
+ {
36
+ "id": "desert-mechanic",
37
+ "name": "Desert mechanic",
38
+ "subject": "adult mechanic with curly black hair and copper eyes",
39
+ "outfit": "sand-colored overalls and work gloves",
40
+ "action": "repairing a small robot",
41
+ "setting": "desert workshop",
42
+ "style": "anime illustration, clean line art, soft cel shading",
43
+ "lighting": "soft cinematic lighting",
44
+ "composition": "three-quarter portrait"
45
+ },
46
+ {
47
+ "id": "rain-detective",
48
+ "name": "Rain detective",
49
+ "subject": "adult detective with cropped blue hair and gray eyes",
50
+ "outfit": "charcoal raincoat",
51
+ "action": "holding a transparent umbrella",
52
+ "setting": "rainy city street",
53
+ "style": "anime illustration, clean line art, soft cel shading",
54
+ "lighting": "soft cinematic lighting",
55
+ "composition": "three-quarter portrait"
56
+ },
57
+ {
58
+ "id": "tea-alchemist",
59
+ "name": "Tea alchemist",
60
+ "subject": "adult alchemist with auburn hair and freckles",
61
+ "outfit": "sage apron over a cream shirt",
62
+ "action": "pouring tea into a glass cup",
63
+ "setting": "warm herbal shop",
64
+ "style": "anime illustration, clean line art, soft cel shading",
65
+ "lighting": "soft cinematic lighting",
66
+ "composition": "three-quarter portrait"
67
+ },
68
+ {
69
+ "id": "snow-ranger",
70
+ "name": "Snow ranger",
71
+ "subject": "adult ranger with white braids and brown eyes",
72
+ "outfit": "teal winter coat and wool scarf",
73
+ "action": "watching distant mountains",
74
+ "setting": "snow-covered trail",
75
+ "style": "anime illustration, clean line art, soft cel shading",
76
+ "lighting": "soft cinematic lighting",
77
+ "composition": "three-quarter portrait"
78
+ },
79
+ {
80
+ "id": "ocean-cartographer",
81
+ "name": "Ocean cartographer",
82
+ "subject": "adult cartographer with dark curls and hazel eyes",
83
+ "outfit": "white shirt and blue waistcoat",
84
+ "action": "drawing a sea chart",
85
+ "setting": "sunlit ship cabin",
86
+ "style": "anime illustration, clean line art, soft cel shading",
87
+ "lighting": "soft cinematic lighting",
88
+ "composition": "three-quarter portrait"
89
+ },
90
+ {
91
+ "id": "rooftop-musician",
92
+ "name": "Rooftop musician",
93
+ "subject": "adult musician with pink bobbed hair and dark eyes",
94
+ "outfit": "burgundy jacket and black trousers",
95
+ "action": "playing a violin",
96
+ "setting": "city rooftop at dusk",
97
+ "style": "anime illustration, clean line art, soft cel shading",
98
+ "lighting": "soft cinematic lighting",
99
+ "composition": "three-quarter portrait"
100
+ },
101
+ {
102
+ "id": "garden-guardian",
103
+ "name": "Garden guardian",
104
+ "subject": "adult guardian with dark green hair and golden eyes",
105
+ "outfit": "layered moss-colored cloak",
106
+ "action": "holding a wooden staff",
107
+ "setting": "overgrown stone garden",
108
+ "style": "anime illustration, clean line art, soft cel shading",
109
+ "lighting": "soft cinematic lighting",
110
+ "composition": "three-quarter portrait"
111
+ },
112
+ {
113
+ "id": "star-engineer",
114
+ "name": "Star engineer",
115
+ "subject": "adult engineer with short black hair and blue eyes",
116
+ "outfit": "orange utility suit",
117
+ "action": "inspecting a holographic diagram",
118
+ "setting": "orbital observatory",
119
+ "style": "anime illustration, clean line art, soft cel shading",
120
+ "lighting": "soft cinematic lighting",
121
+ "composition": "three-quarter portrait"
122
+ },
123
+ {
124
+ "id": "village-baker",
125
+ "name": "Village baker",
126
+ "subject": "adult baker with sandy hair and warm brown eyes",
127
+ "outfit": "cream apron and rolled-up sleeves",
128
+ "action": "carrying a basket of bread",
129
+ "setting": "cozy village bakery",
130
+ "style": "anime illustration, clean line art, soft cel shading",
131
+ "lighting": "soft cinematic lighting",
132
+ "composition": "three-quarter portrait"
133
+ }
134
+ ]
@@ -0,0 +1,40 @@
1
+ import json
2
+ from pathlib import Path
3
+ import subprocess
4
+ import sys
5
+ import unittest
6
+ from anime_prompt_kit import compose_prompt, from_template, list_templates
7
+
8
+
9
+ class PromptTests(unittest.TestCase):
10
+ def test_shared_templates(self):
11
+ root = Path(__file__).resolve().parents[1]
12
+ self.assertEqual(list_templates(), json.loads((root / "templates.json").read_text()))
13
+ self.assertEqual(len(list_templates()), 12)
14
+ for template in list_templates():
15
+ js = subprocess.check_output(["node", "cli.js", template["id"], "--setting", "a snowy station"], cwd=root, text=True).strip()
16
+ self.assertEqual(from_template(template["id"], setting="a snowy station"), js)
17
+
18
+ def test_overrides_do_not_mutate(self):
19
+ original = from_template("sky-courier")
20
+ self.assertIn("a snowy station", from_template("sky-courier", {"setting": "a snowy station"}))
21
+ self.assertEqual(from_template("sky-courier"), original)
22
+ items = list_templates()
23
+ items[0]["subject"] = "changed"
24
+ self.assertEqual(from_template("sky-courier"), original)
25
+
26
+ def test_validation(self):
27
+ self.assertEqual(compose_prompt(subject=" explorer ", outfit=" ", setting="forest"), "explorer, forest")
28
+ for value in ([], 1, "text"):
29
+ with self.assertRaises(TypeError):
30
+ compose_prompt(value)
31
+ with self.assertRaises(TypeError):
32
+ compose_prompt(subject=None)
33
+ with self.assertRaises(ValueError):
34
+ from_template("missing")
35
+
36
+ def test_cli_errors(self):
37
+ for args in (["missing"], ["sky-courier", "--unknown", "x"], ["--list", "sky-courier"]):
38
+ result = subprocess.run([sys.executable, "-m", "anime_prompt_kit", *args], capture_output=True, text=True)
39
+ self.assertNotEqual(result.returncode, 0)
40
+ self.assertNotIn("Traceback", result.stderr)