kingkont 0.7.42 → 0.7.44

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.
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "kingkont",
3
- "version": "0.7.42",
3
+ "version": "0.7.44",
4
4
  "description": "KingKont \u00b7 Chatium \u2014 \u043d\u043e\u0434-\u0440\u0435\u0434\u0430\u043a\u0442\u043e\u0440 \u0441\u0446\u0435\u043d \u0441 AI-\u0433\u0435\u043d\u0435\u0440\u0430\u0446\u0438\u0435\u0439 (\u043a\u0430\u0440\u0442\u0438\u043d\u043a\u0438/\u0432\u0438\u0434\u0435\u043e/\u0433\u043e\u043b\u043e\u0441/SFX/\u043c\u0443\u0437\u044b\u043a\u0430/\u0442\u0435\u043a\u0441\u0442)",
5
5
  "main": "main.js",
6
6
  "bin": {
@@ -492,9 +492,42 @@ function attachResize(el, node, handle) {
492
492
  e.stopPropagation();
493
493
  const startX = e.clientX, startY = e.clientY;
494
494
  const startW = el.offsetWidth, startH = el.offsetHeight;
495
+
496
+ // Aspect-lock для image/video: соблюдаем ratio оригинала. Берём nat-
497
+ // ural размеры media-элемента, считаем chrome (header + footer + padding)
498
+ // как разницу высоты ноды и высоты media. На этапе resize меняем ту ось,
499
+ // куда юзер двигает сильнее, вторая подстраивается. Если media ещё не
500
+ // загружена (naturalW/H = 0) — fallback на свободный resize как раньше.
501
+ let aspect = null, chromeH = 0;
502
+ if (node.type === 'image' || node.type === 'video') {
503
+ const mediaEl = el.querySelector('.node-body img, .node-body video');
504
+ const natW = mediaEl?.naturalWidth || mediaEl?.videoWidth || 0;
505
+ const natH = mediaEl?.naturalHeight || mediaEl?.videoHeight || 0;
506
+ const mediaH = mediaEl?.offsetHeight || 0;
507
+ if (natW && natH && mediaH > 0) {
508
+ aspect = natW / natH;
509
+ chromeH = Math.max(0, startH - mediaH);
510
+ }
511
+ }
512
+
495
513
  const onMove = ev => {
496
- const w = Math.max(180, startW + (ev.clientX - startX) / state.zoom);
497
- const h = Math.max(80, startH + (ev.clientY - startY) / state.zoom);
514
+ let w = Math.max(180, startW + (ev.clientX - startX) / state.zoom);
515
+ let h = Math.max(80, startH + (ev.clientY - startY) / state.zoom);
516
+ if (aspect) {
517
+ const dx = Math.abs(ev.clientX - startX);
518
+ const dy = Math.abs(ev.clientY - startY);
519
+ if (dx >= dy) {
520
+ // Ширина — ведущая, высота под неё.
521
+ h = w / aspect + chromeH;
522
+ } else {
523
+ // Высота — ведущая, ширина под неё.
524
+ const mediaH = h - chromeH;
525
+ if (mediaH > 0) w = mediaH * aspect;
526
+ }
527
+ // Заново соблюдаем минимумы после aspect-clamp.
528
+ if (w < 180) { w = 180; h = w / aspect + chromeH; }
529
+ if (h < 80) { h = 80; w = Math.max(180, (h - chromeH) * aspect); }
530
+ }
498
531
  node.width = w;
499
532
  node.height = h;
500
533
  el.style.width = w + 'px';
package/skill/SKILL.md CHANGED
@@ -1,6 +1,6 @@
1
1
  ---
2
2
  name: kingkont
3
- description: Use this skill when the user works with a KingKont project — a film/series scene editor where each scene is a folder with scene.json. Triggers — фразы вроде «открой/запусти kingkont», «открой редактор сцен», «добавь сцену/персонажа/локацию», «добавь ноду на холст», «сгенерируй картинку/видео/голос/SFX/музыку/текст», или работа с папкой содержащей _characters/ _locations/ <scene>/scene.json. Skill знает формат данных и использует CLI `kingkont <cmd>` (open/list/board/add-node/gen/connect/rm-node/upload/voices/balance) для управления нодами и запуска генераций — ключи берутся автоматически из настроек приложения. Для визуальной работы поднимает UI через `npx -y kingkont serve`.
3
+ description: Use this skill when the user works with a KingKont project — a film/series scene editor where each scene is a folder with scene.json. Triggers — фразы вроде «открой/запусти kingkont», «открой редактор сцен», «добавь сцену/персонажа/локацию», «добавь ноду на холст», «сгенерируй картинку/видео/голос/SFX/музыку/текст», или работа с папкой содержащей _characters/ _locations/ <scene>/scene.json. Skill знает формат данных и использует CLI `kingkont <cmd>` (open/list/board/add-node/gen/connect/rm-node/upload/voices/balance) для управления нодами и запуска генераций — ключи берутся автоматически из настроек приложения. ВАЖНО: каждая нода живёт в конкретной доске (сцене/персонаже/локации) — если юзер не указал доску явно, СПРОСИ его в какой добавить, не создавай новые сцены без явного запроса. Для визуальной работы поднимает UI через `npx -y kingkont serve`.
4
4
  ---
5
5
 
6
6
  # KingKont · Chatium — Skill
@@ -23,6 +23,42 @@ KingKont — нод-редактор сцен фильма/сериала с AI-
23
23
  - Любые правки тексту, перестановка нод, чистка истории, бэкап — все
24
24
  через прямую правку `scene.json` и `texts/*.md`.
25
25
 
26
+ ## ⚠️ ОБЯЗАТЕЛЬНОЕ ПРАВИЛО: всегда уточняй доску
27
+
28
+ **НИКОГДА не создавай новые сцены без явного запроса юзера.** Каждая нода
29
+ живёт в конкретной доске (сцене / персонаже / локации). Если юзер просит
30
+ «сгенерируй картинку», «добавь ноду», «вставь голос» — это значит
31
+ «внутри какой-то существующей доски», а не «создай новую».
32
+
33
+ ### Алгоритм перед любой операцией создания нод
34
+
35
+ 1. Запусти `kingkont open <project>` чтобы получить список существующих
36
+ досок проекта.
37
+ 2. Если юзер не указал доску явно — **спроси у него** в чём именно
38
+ работать:
39
+ - Если есть только одна сцена / `currentBoard` сохранён — используй её.
40
+ - Если несколько и юзер не уточнил — выведи нумерованный список и
41
+ спроси номер. Пример: «У тебя есть сцены: 1) Серия 1, 2) Серия 2,
42
+ 3) Серия 4.1. В какой добавить?»
43
+ 3. Не предлагай создать новую сцену пока юзер сам не попросит словами
44
+ вроде «новая сцена», «создай сцену», «добавь эпизод».
45
+ 4. Если юзер прислал N фото — все ноды идут в **одну** выбранную доску,
46
+ а не в N разных.
47
+
48
+ ### Как создавать новые сцены (только когда явно попросили)
49
+
50
+ Команды CLI для add-node — НЕ создают сцену; они работают только с
51
+ существующими досками. Чтобы создать новую сцену, нужно:
52
+
53
+ ```bash
54
+ mkdir -p <project>/<имя_новой_сцены>
55
+ echo '{"nodes":[],"connections":[]}' > <project>/<имя_новой_сцены>/scene.json
56
+ # Дальше — обычные kingkont add-node / kingkont gen с этой доской
57
+ ```
58
+
59
+ Аналогично для персонажа: `<project>/_characters/<имя>/scene.json`.
60
+ Для локации: `<project>/_locations/<имя>/scene.json`.
61
+
26
62
  ## Как открыть UI редактора
27
63
 
28
64
  ```bash
@@ -345,6 +381,34 @@ kingkont upload <file> # печатает публичный URL
345
381
 
346
382
  **«Открой редактор»** → `npx -y kingkont serve` + сообщить URL для Chrome.
347
383
 
384
+ ### Юзер просит сгенерировать что-то (картинку/видео/голос/SFX/текст)
385
+
386
+ **Сначала всегда** — определи доску. Не угадывай и не создавай новую.
387
+
388
+ ```bash
389
+ kingkont open <project> # JSON со списком всех досок
390
+ ```
391
+
392
+ Если юзер уже назвал доску в реплике («добавь в Серию 1», «на сцене Прощание»)
393
+ — используй её. Иначе спроси: «У тебя есть сцены: 1) Серия 1, 2) Серия 2,
394
+ 3) Серия 4.1. В какой добавить?» — и **жди ответа**.
395
+
396
+ Если юзер прислал несколько фото/референсов и сказал «вот, сгенери что-то по
397
+ ним» — это НЕ повод создать N новых сцен по одной на каждое фото. Это
398
+ повод спросить «в какой сцене разложить эти N кадров?».
399
+
400
+ После того как доска определена:
401
+
402
+ ```bash
403
+ kingkont gen <project> <board> --kind=image --prompt="..." --refs=@ref1
404
+ ```
405
+
406
+ ### Юзер просит добавить персонажа / локацию / новую сцену
407
+
408
+ Только тогда создавай папки. Триггерные фразы: «новая сцена», «добавь
409
+ сцену», «создай эпизод», «новый персонаж», «добавь персонажа», «новая
410
+ локация».
411
+
348
412
  **«Добавь персонажа Анна»**:
349
413
  ```bash
350
414
  mkdir -p <project>/_characters/Анна
@@ -354,26 +418,37 @@ kingkont gen <project> _characters/Анна --kind=image --name=sheet \
354
418
  --prompt="портрет молодой женщины-следователя" --model=nano-banana-2
355
419
  ```
356
420
 
357
- **«Добавь текстовую ноду на сцену "Прощание" с таким текстом …»**:
421
+ **«Создай новую сцену "Финал"»**:
422
+ ```bash
423
+ mkdir -p <project>/Финал
424
+ echo '{"nodes":[],"connections":[]}' > <project>/Финал/scene.json
425
+ ```
426
+ После этого можно сразу генерить ноды в неё:
427
+ ```bash
428
+ kingkont gen <project> Финал --kind=text --name=script --prompt="..."
429
+ ```
430
+
431
+ ### Узкие сценарии
432
+
433
+ **«Добавь текстовую ноду на сцену "Прощание"»**:
358
434
  ```bash
359
435
  kingkont add-node <project> Прощание --kind=text --name=plot --text="ТЕКСТ"
360
436
  ```
361
437
 
362
- **«Свяжи ноды @А и @Б»**:
438
+ **«Свяжи ноды @А и @Б»** (в одной доске):
363
439
  ```bash
364
440
  kingkont connect <project> Прощание А Б
365
441
  ```
366
442
 
367
- **«Сгенерируй SFX "камни сыпятся"»**:
443
+ **«Сгенерируй SFX "камни сыпятся" в Серии 1»**:
368
444
  ```bash
369
- kingkont gen <project> <board> --kind=audio --sub-kind=sfx \
445
+ kingkont gen <project> 'Серия 1' --kind=audio --sub-kind=sfx \
370
446
  --prompt="rocks falling, gravel cascading" --duration=3
371
447
  ```
372
448
  (SFX-модель ElevenLabs работает лучше на английском — переводи русский промпт.)
373
449
 
374
- **«Сделай i2v видео из этой картинки»**:
450
+ **«Сделай i2v видео из этой картинки»** (нода @hero уже в доске):
375
451
  ```bash
376
- # Нода @hero уже есть в этой доске:
377
452
  kingkont gen <project> <board> --kind=video --refs=@hero \
378
453
  --model=kling-3.0 --prompt="hero turns and walks away"
379
454
  ```