Merge branch 'main' into develop

This commit is contained in:
るみなー先生
2026-08-19 01:55:25 +09:00
7 changed files with 111 additions and 2 deletions
+2
View File
@@ -20,3 +20,5 @@ Thumbs.db
# --- ComfyUI/カスタムノード特有 ---
# もし一時ファイルやログを書き出す仕組みを作ったなら、それも追加じゃ
*.log
.ruff_cache/
+30
View File
@@ -9,6 +9,15 @@
フロー内に複数個置いても、それぞれ独立して動くぞ。
## v0.5.0
`Safe Random Seed` を追加したのじゃ。
- `Safe Random Seed`
- KSampler向けに、0以上のランダムseedだけを出力する小型ノード
- Python側で `secrets` を使って発番します
- 実行後、ノードタイトルを `Seed: 4897362896` のように書き換えます
## v0.4.0
`Prompt Random Choice Ex` を追加したのじゃ。
@@ -45,6 +54,10 @@
- 実行時にノードタイトルが `Choice: coffee shop` のように更新されるぞ。
- KSamplerのプレビューと見比べやすいのじゃ。
- **KSampler向けの安全なランダムseed生成**
- `Safe Random Seed` は、0以上のINTだけを出力するぞ。
- 実行後、ノードタイトルが `Seed: 4897362896` のように更新されるのじゃ。
- **複数設置に対応**
- 背景用、時間帯用、天気用など、複数ノードを置いてそれぞれ別々に使えるぞ。
@@ -175,6 +188,23 @@ day|day|day|sunset|night
- `change_every` が 1 なら毎回選び直す
- `change_every` が 2 以上なら、その回数ぶん同じ候補を維持する
- 実行時にタイトルへ `Choice: lake` や `Choice: (empty) (2/3)` のように表示する
- `Safe Random Seed` は実行時にタイトルへ `Seed: 4897362896` のように表示する
## Safe Random Seed
KSampler向けに、0以上のランダムseedを1つ生成します。
汎用の整数Primitiveを `randomize` すると負数が出る場合がありますが、このノードは負数を出しません。
SDE系サンプラーで `expected non-negative integer` が出る事故を避けるための小さな保険じゃ。
- 入力はありません
- 出力は `seed` だけです
- 乱数はComfyUIサーバー側、Pythonの `secrets` で生成します
- 発番はノード実行時です
- 出力値の範囲は `0` から `2^53 - 1` です
- 同じノードの出力を複数箇所へ接続した場合、同じseed値を配ります
- 別々のseedが欲しい場合は、`Safe Random Seed` ノードを複数置いてください
- 前回出力されたseed値は、次回の乱数生成には影響しません
- 実行後、ノードタイトルを `Seed: 4897362896` のように書き換えます
## Prompt Random Choice
+18
View File
@@ -1,3 +1,21 @@
## v0.5.0
`Safe Random Seed` を追加しました。
## 追加
- `Safe Random Seed`
- KSampler向けに、0以上のランダムseedだけを出力する小型ノード
- Python側の `secrets` を使って発番
- 実行後、ノードタイトルを `Seed: 4897362896` のように更新
- 同じノードの出力を複数箇所へ接続した場合は、同じseed値を配布
## 変更
- タイトル表示用JavaScriptで、`Prompt Random Choice Ex` の短縮文字数設定が反映されるように修正
---
## v0.4.0
`Prompt Random Choice Ex` を追加しました。
BIN
View File
Binary file not shown.

After

Width:  |  Height:  |  Size: 114 KiB

+32
View File
@@ -30,6 +30,7 @@ amusement park{ferris wheel|carousel|balloons}
MAX_EXPAND_STEPS = 64
MAX_EXPANDED_OPTIONS = 4096
MAX_SAFE_SEED = 2**53 - 1
def _split_options(options_text: str):
@@ -427,12 +428,43 @@ class PromptRandomChoiceEx(_RandomChoiceStateMixin):
}
class SafeRandomSeed:
@classmethod
def INPUT_TYPES(cls):
return {
"required": {},
}
RETURN_TYPES = ("INT",)
RETURN_NAMES = ("seed",)
FUNCTION = "generate"
CATEGORY = "utils/random"
@classmethod
def IS_CHANGED(cls, **kwargs):
# Force re-execution for each queued run.
return secrets.token_hex(16)
def generate(self):
seed = secrets.randbelow(MAX_SAFE_SEED + 1)
return {
"ui": {
"seed_title": [f"Seed: {seed}"],
"seed_value": [str(seed)],
},
"result": (seed,),
}
NODE_CLASS_MAPPINGS = {
"PromptRandomChoice": PromptRandomChoice,
"PromptRandomChoiceEx": PromptRandomChoiceEx,
"SafeRandomSeed": SafeRandomSeed,
}
NODE_DISPLAY_NAME_MAPPINGS = {
"PromptRandomChoice": "Prompt Random Choice",
"PromptRandomChoiceEx": "Prompt Random Choice Ex",
"SafeRandomSeed": "Safe Random Seed",
}
+18
View File
@@ -0,0 +1,18 @@
[project]
name = "prompt-random-choice"
version = "0.5.0"
description = "A ComfyUI custom node that randomly selects one item from a list of prompt suggestions each time it is executed."
license = { file = "LICENSE" }
readme = "README.md"
requires-python = ">=3.10"
dependencies = []
[project.urls]
Repository = "https://github.com/ruminar/ComfyUI-PromptRandomChoice"
Documentation = "https://github.com/ruminar/ComfyUI-PromptRandomChoice/blob/main/README.md"
"Bug Tracker" = "https://github.com/ruminar/ComfyUI-PromptRandomChoice/issues"
[tool.comfy]
PublisherId = "ruminar"
DisplayName = "Prompt Random Choice"
Icon = "https://raw.githubusercontent.com/ruminar/ComfyUI-PromptRandomChoice/main/icon.png"
+11 -2
View File
@@ -4,6 +4,7 @@ const EXTENSION_NAME = "ruminar.PromptRandomChoice";
const NODE_NAMES = new Set([
"PromptRandomChoice",
"PromptRandomChoiceEx",
"SafeRandomSeed",
]);
function shorten(text, maxLength = 40) {
@@ -30,14 +31,22 @@ app.registerExtension({
nodeType.prototype.onExecuted = function (message) {
originalOnExecuted?.apply(this, arguments);
if (nodeName === "SafeRandomSeed") {
this.title = String(message?.seed_title?.[0] ?? "Seed: ?");
this.setDirtyCanvas?.(true, true);
app.graph?.setDirtyCanvas?.(true, true);
return;
}
const selectedTitle = message?.selected_text_title?.[0] ?? "(empty)";
const repeatIndex = Number(message?.repeat_index?.[0] ?? 0);
const changeEvery = Number(message?.change_every?.[0] ?? 1);
if (changeEvery <= 1) {
this.title = `${prefix}: ${shorten(selectedTitle)}`;
this.title = `${prefix}: ${shorten(selectedTitle, maxTitleLength)}`;
} else {
this.title = `${prefix}: ${shorten(selectedTitle)} (${repeatIndex}/${changeEvery})`;
this.title = `${prefix}: ${shorten(selectedTitle, maxTitleLength)} (${repeatIndex}/${changeEvery})`;
}
this.setDirtyCanvas?.(true, true);