メインコンテンツへスキップ
ComfyUI 組み込み Pika 2.2 Scenes ノード Pika 2.2 Scenes ノードは、複数の画像をアップロードし、それらの要素を統合した高品質な動画を生成できます。このノードは Pika の 2.2 API を利用して、入力画像間の滑らかなシーン遷移を実現します。

パラメーター

必須パラメーター

パラメーターデフォルト値説明
prompt_text文字列""動画の内容およびシーンを説明するテキストプロンプト
negative_prompt文字列""動画に含めたくない要素
seed整数0生成時の乱数シード
ingredients_mode選択肢”creative”画像の組み合わせモード
resolution選択肢API のデフォルト値出力動画の解像度
duration選択肢API のデフォルト値出力動画の長さ
aspect_ratio浮動小数点数1.7777777777777777 (16:9)動画のアスペクト比(範囲:0.4~2.5)

オプションパラメーター

パラメーター説明
image_ingredient_1画像最初のシーン画像
image_ingredient_2画像2番目のシーン画像
image_ingredient_3画像3番目のシーン画像
image_ingredient_4画像4番目のシーン画像
image_ingredient_5画像5番目のシーン画像

出力

出力説明
VIDEO動画生成された動画

動作原理

Pika 2.2 Scenes ノードは、すべての入力画像を解析し、それらの画像要素を含む動画を生成します。このノードは、画像とパラメーターを Pika の API サーバーに送信し、サーバー側で処理された後に生成された動画を返却します。 ユーザーはプロンプトを用いて動画のスタイルや内容を制御でき、ネガティブプロンプトを用いて不要な要素を除外できます。このノードは最大5枚の入力画像を「素材(ingredients)」として受け付け、指定された組み合わせモード、解像度、再生時間、アスペクト比に基づいて最終的な動画を生成します。

ソースコード


class PikaScenesV2_2(PikaNodeBase):
    """Pika 2.2 Scenes Node."""

    @classmethod
    def INPUT_TYPES(cls):
        image_ingredient_input = (
            IO.IMAGE,
            {"tooltip": "Image that will be used as ingredient to create a video."},
        )
        return {
            "required": {
                **cls.get_base_inputs_types(
                    PikaBodyGenerate22C2vGenerate22PikascenesPost,
                ),
                "ingredients_mode": model_field_to_node_input(
                    IO.COMBO,
                    PikaBodyGenerate22C2vGenerate22PikascenesPost,
                    "ingredientsMode",
                    enum_type=IngredientsMode,
                    default="creative",
                ),
                "aspect_ratio": model_field_to_node_input(
                    IO.FLOAT,
                    PikaBodyGenerate22C2vGenerate22PikascenesPost,
                    "aspectRatio",
                    step=0.001,
                    min=0.4,
                    max=2.5,
                    default=1.7777777777777777,
                ),
            },
            "optional": {
                "image_ingredient_1": image_ingredient_input,
                "image_ingredient_2": image_ingredient_input,
                "image_ingredient_3": image_ingredient_input,
                "image_ingredient_4": image_ingredient_input,
                "image_ingredient_5": image_ingredient_input,
            },
            "hidden": {
                "auth_token": "AUTH_TOKEN_COMFY_ORG",
            },
        }

    DESCRIPTION = "Combine your images to create a video with the objects in them. Upload multiple images as ingredients and generate a high-quality video that incorporates all of them."
    RETURN_TYPES = ("VIDEO",)

    def api_call(
        self,
        prompt_text: str,
        negative_prompt: str,
        seed: int,
        resolution: str,
        duration: int,
        ingredients_mode: str,
        aspect_ratio: float,
        image_ingredient_1: Optional[torch.Tensor] = None,
        image_ingredient_2: Optional[torch.Tensor] = None,
        image_ingredient_3: Optional[torch.Tensor] = None,
        image_ingredient_4: Optional[torch.Tensor] = None,
        image_ingredient_5: Optional[torch.Tensor] = None,
        auth_token: Optional[str] = None,
    ) -> tuple[VideoFromFile]:
        """API call for Pika Scenes 2.2."""
        all_image_bytes_io = []
        for image in [
            image_ingredient_1,
            image_ingredient_2,
            image_ingredient_3,
            image_ingredient_4,
            image_ingredient_5,
        ]:
            if image is not None:
                image_bytes_io = tensor_to_bytesio(image)
                image_bytes_io.seek(0)
                all_image_bytes_io.append(image_bytes_io)

        # Prepare files data for multipart upload
        pika_files = [
            ("images", (f"image_{i}.png", image_bytes_io, "image/png"))
            for i, image_bytes_io in enumerate(all_image_bytes_io)
        ]

        # Prepare non-file data using the Pydantic model
        pika_request_data = PikaBodyGenerate22C2vGenerate22PikascenesPost(
            ingredientsMode=ingredients_mode,
            promptText=prompt_text,
            negativePrompt=negative_prompt,
            seed=seed,
            resolution=resolution,
            duration=duration,
            aspectRatio=aspect_ratio,
        )

        initial_operation = SynchronousOperation(
            endpoint=ApiEndpoint(
                path=PATH_PIKASCENES,
                method=HttpMethod.POST,
                request_model=PikaBodyGenerate22C2vGenerate22PikascenesPost,
                response_model=PikaGenerateResponse,
            ),
            request=pika_request_data,
            files=pika_files,
            content_type="multipart/form-data",
            auth_token=auth_token,
        )

        return self.execute_task(initial_operation, auth_token)