diff --git a/node_scene.py b/node_scene.py index ac996d6..93cd969 100644 --- a/node_scene.py +++ b/node_scene.py @@ -2280,7 +2280,7 @@ class SxCPScenePairOutput: hard_scene = _parse_scene(hardcore_scene) base_configs = _compat_configs(soft_scene, "softcore") hard_configs = _compat_configs(hard_scene, "hardcore") - shared_seed_config = _base_config(soft_scene, "seed_config") or base_configs["seed_config"] + shared_seed_config = _base_config(soft_scene, "seed_config") options_json = _pair_options(soft_scene, hard_scene) row = build_insta_of_pair( row_number=int(soft_scene.get("row_number", 1)), diff --git a/pair_rows.py b/pair_rows.py index f1b0c51..6acc7d0 100644 --- a/pair_rows.py +++ b/pair_rows.py @@ -74,6 +74,7 @@ def build_insta_pair_rows_result( soft_seed_config = parsed_softcore_seed_config or parsed_seed_config hard_seed_config = parsed_hardcore_seed_config or parsed_seed_config soft_content_rng = axis_rng(soft_seed_config, "content", seed, row_number + 311) + soft_pose_rng = axis_rng(soft_seed_config, "pose", seed, row_number + 313) hard_content_rng = axis_rng(hard_seed_config, "content", seed, row_number + 317) soft_person_rng = axis_rng(soft_seed_config, "person", seed, row_number) @@ -148,7 +149,7 @@ def build_insta_pair_rows_result( primary_softcore_outfit = slot_softcore_outfit(primary_slot, soft_content_rng) soft_row["item"] = primary_softcore_outfit or softcore_outfit(soft_content_rng, softcore_level_key) - soft_row["pose"] = softcore_pose(soft_content_rng, softcore_level_key) + soft_row["pose"] = softcore_pose(soft_pose_rng, softcore_level_key) soft_row["item_label"] = ( "Insta/OF softcore body exposure" if softcore_level_key == "explicit_nude" diff --git a/tools/prompt_route_simulation.py b/tools/prompt_route_simulation.py index 6445191..1ffbc76 100644 --- a/tools/prompt_route_simulation.py +++ b/tools/prompt_route_simulation.py @@ -1258,7 +1258,7 @@ def _pair_seed_pose_reroll_check(seed: int) -> dict[str, Any]: seed, name="pair_seed.pose_reroll", reroll_axis="pose", - changed_fields=("hard_position_key", "hard_item", "hard_source_role_graph"), + changed_fields=("soft_pose", "hard_position_key", "hard_item", "hard_source_role_graph"), stable_fields=( "shared_cast_descriptors", "soft_cast_descriptor_text", @@ -1266,7 +1266,6 @@ def _pair_seed_pose_reroll_check(seed: int) -> dict[str, Any]: "soft_scene_text", "hard_scene_text", "soft_item", - "soft_pose", "soft_composition", "hard_composition", ), @@ -1279,13 +1278,14 @@ def _pair_seed_content_reroll_check(seed: int) -> dict[str, Any]: seed, name="pair_seed.content_reroll", reroll_axis="content", - changed_fields=("soft_item", "soft_pose"), + changed_fields=("soft_item",), stable_fields=( "shared_cast_descriptors", "soft_cast_descriptor_text", "hard_cast_descriptor_text", "soft_scene_text", "hard_scene_text", + "soft_pose", "hard_item", "hard_position_key", "hard_source_role_graph", diff --git a/tools/prompt_smoke.py b/tools/prompt_smoke.py index 6690e35..cd18b0e 100644 --- a/tools/prompt_smoke.py +++ b/tools/prompt_smoke.py @@ -8277,7 +8277,7 @@ def smoke_prompt_route_simulation_policy() -> None: ) _expect( pair_seed_checks["pair_seed.pose_reroll"].get("changed") is True, - "Pair pose reroll should prove hard action can reroll while soft/cast/scene axes stay locked", + "Pair pose reroll should prove soft pose or hard action can reroll while cast/scene axes stay locked", ) sweep = prompt_route_simulation.run_simulation_sweep(seed=3901, count=3, seed_step=101, include_prompts=False) sweep_summary = sweep.get("summary") or {} @@ -9263,6 +9263,68 @@ def smoke_node_scene_chain_registration() -> None: content_hard_seed_config.get("pose_seed") == 8899 and content_hard_seed_config.get("role_seed") == 8899, "Hardcore branch content_pose reroll did not reach hardcore pose and role seeds", ) + + def _soft_pose_pair(soft_pose_seed: int) -> dict[str, Any]: + soft_pose_seed_options = nodes["SxCPSceneLayerSeedOptions"]().build( + "softcore_branch", + "fixed", + soft_pose_seed, + "pose", + "same_for_all_rows", + "replace_layer", + )[0] + soft_scene_pose, hard_scene_pose, _summary, _metadata = nodes["SxCPSceneBranchPair"]().build( + scene, + "same_creator_same_room", + "hybrid", + branch_options=branch_options, + seed_options=soft_pose_seed_options, + ) + soft_scene_pose = nodes["SxCPSoftcoreBranchOptions"]().build( + soft_scene_pose, + "same_as_hardcore", + "lingerie_tease", + True, + 0.45, + "from_camera_config", + "compact", + "", + branch_options=branch_options, + seed_options=soft_pose_seed_options, + )[0] + hard_scene_pose = nodes["SxCPHardcoreBranchOptions"]().build( + hard_scene_pose, + "couple", + 1, + 1, + "hardcore", + True, + 0.85, + "explicit_nude", + "from_camera_config", + "compact", + "balanced", + "", + branch_options=branch_options, + )[0] + return json.loads(nodes["SxCPScenePairOutput"]().build(soft_scene_pose, hard_scene_pose)[7]) + + soft_pose_pairs = [_soft_pose_pair(seed) for seed in (6677, 6678, 6679, 6680)] + soft_pose_items = {pair.get("softcore_row", {}).get("item") for pair in soft_pose_pairs} + soft_pose_values = {pair.get("softcore_row", {}).get("pose") for pair in soft_pose_pairs} + _expect(len(soft_pose_items) == 1, "Softcore branch pose reroll should not change softcore outfit/content") + _expect(len(soft_pose_values) > 1, "Softcore branch pose reroll did not change softcore pose") + for expected_seed, pose_pair in zip((6677, 6678, 6679, 6680), soft_pose_pairs): + soft_seed_config = pose_pair.get("softcore_row", {}).get("seed_config") if isinstance(pose_pair.get("softcore_row"), dict) else {} + hard_seed_config = pose_pair.get("hardcore_row", {}).get("seed_config") if isinstance(pose_pair.get("hardcore_row"), dict) else {} + _expect( + soft_seed_config.get("pose_seed") == expected_seed, + "Softcore branch pose seed did not reach softcore generator seed config", + ) + _expect( + hard_seed_config.get("pose_seed") != expected_seed, + "Softcore branch pose seed leaked into hardcore generator seed config", + ) choice_board_node = nodes["SxCPChoiceBoard"]() choice_board_output = choice_board_node.build( json.dumps(content_pair),