LTX-2 Canny to Video
Generate high-quality videos from edge detection (Canny) guidance with synchronized audio-video generation using LTX-2. Features precise edge control, structural consistency, and efficient performance.
简介
The 'LTX-2 Canny to Video' workflow is designed to transform edge-detected images into high-quality videos with synchronized audio. Utilizing the LTX-2 model, this workflow leverages the Canny edge detection technique to ensure precise edge control and structural consistency throughout the video. The process begins with the 'LoadVideo' node to import your source video, which is then decomposed into its components using the 'GetVideoComponents' node. The 'Canny' node plays a crucial role by detecting edges in the images, providing a guide for the video generation process.
This workflow is particularly useful for creators who need to maintain the structural integrity of the original footage while enhancing it with AI-generated elements. The LTX-2 model, developed by Lightricks, ensures that the generated video maintains high quality and coherence. The workflow also includes nodes like 'ImageScaleBy' and 'ResizeImageMaskNode' for adjusting image dimensions, and 'SaveVideo' to compile and save the final video. By following the recommended settings and parameters, users can achieve optimal results with minimal manual intervention.
你需要提供
- 正在读取工作流
在 ComfyUI 中运行。 此工作流无法在本页面运行。你可以在 Comfy Cloud 中打开(已预先加载所需内容),或下载后在自己的 ComfyUI 中使用。
在 Cloud 中试用查看工作流内部
节点图的只读预览。在 Comfy Cloud 中打开或下载后即可编辑节点。
Loading the graph
Open full-size workflow preview- 作者
- ComfyUI
需要自定义节点
- 正在读取工作流
通过代码使用此工作流
尽可能根据工作流图和输入自动生成代码,否则显示已保存的示例。运行代码可能产生费用,请先核对凭据和端点。
What you need
- Runs on
- Comfy Cloud
- 密钥
- COMFY_API_KEY
需要付费的 Cloud 方案和额度。
# Python 3.10+: pip install comfy-sdk==0.4.0
import os
from comfy_sdk import Comfy
api_key = os.environ.get("COMFY_API_KEY", "").strip()
if not api_key: raise RuntimeError("Set COMFY_API_KEY")
os.environ.setdefault("COMFY_BASE_URL", "https://cloud.comfy.org")
client = Comfy(api_key=api_key)
workflow = client.workflows.from_json({
"127": {
"class_type": "LoadVideo",
"inputs": {
"file": "squirrel_in_flower_garden.mp4"
},
"_meta": {
"title": "Load Video"
}
},
"144": {
"class_type": "GetVideoComponents",
"inputs": {
"video": [
"127",
0
]
},
"_meta": {
"title": "Get Video Components"
}
},
"146": {
"class_type": "ImageScaleBy",
"inputs": {
"image": [
"164",
0
],
"scale_by": 0.5,
"upscale_method": "lanczos"
},
"_meta": {
"title": "Upscale Image By"
}
},
"152": {
"class_type": "ImageFromBatch",
"inputs": {
"batch_index": 0,
"image": [
"144",
0
],
"length": [
"168",
0
]
},
"_meta": {
"title": "Get Image from Batch"
}
},
"158": {
"class_type": "Canny",
"inputs": {
"high_threshold": 0.8,
"image": [
"146",
0
],
"low_threshold": 0.4
},
"_meta": {
"title": "Detect Edges (Canny)"
}
},
"160": {
"class_type": "LoadImage",
"inputs": {
"image": "ltx_2_canny_1st_frame.png"
},
"_meta": {
"title": "Load Image"
}
},
"164": {
"class_type": "ResizeImageMaskNode",
"inputs": {
"input": [
"152",
0
],
"resize_type": "scale dimensions",
"resize_type.crop": "center",
"resize_type.height": [
"167",
0
],
"resize_type.width": [
"166",
0
],
"scale_method": "lanczos"
},
"_meta": {
"title": "Resize Image/Mask"
}
},
"165": {
"class_type": "ResizeImageMaskNode",
"inputs": {
"input": [
"160",
0
],
"resize_type": "scale dimensions",
"resize_type.crop": "center",
"resize_type.height": [
"167",
0
],
"resize_type.width": [
"166",
0
],
"scale_method": "lanczos"
},
"_meta": {
"title": "Resize Image/Mask"
}
},
"166": {
"class_type": "PrimitiveInt",
"inputs": {
"value": 1280
},
"_meta": {
"title": "Width"
}
},
"167": {
"class_type": "PrimitiveInt",
"inputs": {
"value": 720
},
"_meta": {
"title": "Height"
}
},
"168": {
"class_type": "PrimitiveInt",
"inputs": {
"value": 121
},
"_meta": {
"title": "Frame Count"
}
},
"169": {
"class_type": "PrimitiveBoolean",
"inputs": {
"value": False
},
"_meta": {
"title": "Ignore First Frame?"
}
},
"175": {
"class_type": "SaveVideo",
"inputs": {
"filename_prefix": "video/LTX_2.0",
"format": "auto",
"format.codec": "auto",
"video": [
"143:106",
0
]
},
"_meta": {
"title": "Save Video"
}
},
"143:100": {
"class_type": "LatentUpscaleModelLoader",
"inputs": {
"model_name": "ltx-2-spatial-upscaler-x2-1.0.safetensors"
},
"_meta": {
"title": "Load Latent Upscale Model"
}
},
"143:101": {
"class_type": "LTXVConcatAVLatent",
"inputs": {
"audio_latent": [
"143:122",
1
],
"video_latent": [
"143:151",
0
]
},
"_meta": {
"title": "Concat AV Latent"
}
},
"143:103": {
"class_type": "CheckpointLoaderSimple",
"inputs": {
"ckpt_name": "ltx-2-19b-dev-fp8.safetensors"
},
"_meta": {
"title": "Load Checkpoint"
}
},
"143:104": {
"class_type": "LTXVCropGuides",
"inputs": {
"latent": [
"143:122",
0
],
"negative": [
"143:132",
1
],
"positive": [
"143:132",
0
]
},
"_meta": {
"title": "LTXVCropGuides"
}
},
"143:105": {
"class_type": "LoraLoaderModelOnly",
"inputs": {
"lora_name": "ltx-2-19b-distilled-lora-384.safetensors",
"model": [
"143:134",
0
],
"strength_model": 1
},
"_meta": {
"title": "Load LoRA"
}
},
"143:106": {
"class_type": "CreateVideo",
"inputs": {
"audio": [
"143:139",
0
],
"bit_depth": "auto",
"codec": "none",
"color_space": "sRGB",
"fps": [
"143:148",
0
],
"images": [
"143:144",
0
]
},
"_meta": {
"title": "Create Video"
}
},
"143:107": {
"class_type": "SamplerCustomAdvanced",
"inputs": {
"guider": [
"143:108",
0
],
"latent_image": [
"143:101",
0
],
"noise": [
"143:143",
0
],
"sampler": [
"143:98",
0
],
"sigmas": [
"143:99",
0
]
},
"_meta": {
"title": "SamplerCustomAdvanced"
}
},
"143:108": {
"class_type": "CFGGuider",
"inputs": {
"cfg": 1,
"model": [
"143:105",
0
],
"negative": [
"143:104",
1
],
"positive": [
"143:104",
0
]
},
"_meta": {
"title": "CFG Guider"
}
},
"143:110": {
"class_type": "GetImageSize",
"inputs": {
"image": [
"158",
0
]
},
"_meta": {
"title": "Get Image Size"
}
},
"143:111": {
"class_type": "LTXVEmptyLatentAudio",
"inputs": {
"audio_vae": [
"143:96",
0
],
"batch_size": 1,
"frame_rate": [
"143:145",
0
],
"frames_number": [
"143:110",
2
]
},
"_meta": {
"title": "Empty LTXV Latent Audio"
}
},
"143:112": {
"class_type": "LTXVLatentUpsampler",
"inputs": {
"samples": [
"143:104",
2
],
"upscale_model": [
"143:100",
0
],
"vae": [
"143:103",
2
]
},
"_meta": {
"title": "spatial"
}
},
"143:113": {
"class_type": "VAEDecode",
"inputs": {
"samples": [
"143:138",
0
],
"vae": [
"143:103",
2
]
},
"_meta": {
"title": "VAE Decode"
}
},
"143:114": {
"class_type": "LTXVConditioning",
"inputs": {
"frame_rate": [
"143:148",
0
],
"negative": [
"143:119",
0
],
"positive": [
"143:124",
0
]
},
"_meta": {
"title": "LTXVConditioning"
}
},
"143:115": {
"class_type": "EmptyLTXVLatentVideo",
"inputs": {
"batch_size": 1,
"height": [
"143:110",
1
],
"length": [
"143:110",
2
],
"width": [
"143:110",
0
]
},
"_meta": {
"title": "Empty LTXV Latent Video"
}
},
"143:116": {
"class_type": "LTXVConcatAVLatent",
"inputs": {
"audio_latent": [
"143:111",
0
],
"video_latent": [
"143:132",
2
]
},
"_meta": {
"title": "Concat AV Latent"
}
},
"143:119": {
"class_type": "CLIPTextEncode",
"inputs": {
"clip": [
"143:97",
0
],
"text": "blurry, low quality, still frame, frames, watermark, overlay, titles, has blurbox, has subtitles"
},
"_meta": {
"title": "CLIP Text Encode (Prompt)"
}
},
"143:122": {
"class_type": "LTXVSeparateAVLatent",
"inputs": {
"av_latent": [
"143:123",
0
]
},
"_meta": {
"title": "Separate AV Latent"
}
},
"143:123": {
"class_type": "SamplerCustomAdvanced",
"inputs": {
"guider": [
"143:93",
0
],
"latent_image": [
"143:116",
0
],
"noise": [
"143:126",
0
],
"sampler": [
"143:94",
0
],
"sigmas": [
"143:95",
0
]
},
"_meta": {
"title": "SamplerCustomAdvanced"
}
},
"143:124": {
"class_type": "CLIPTextEncode",
"inputs": {
"clip": [
"143:97",
0
],
"text": "A wide shot reveals a whimsical outdoor scene with a decorative tree-like structure crafted from brown branches. Golden spherical ornaments and delicate white artificial flowers adorn the branches, catching bright daylight. A small grey and white squirrel stands on a round, light-colored wooden platform at the base, its bushy tail slightly raised. The squirrel dips its head down, nibbling at something on the platform. The camera slowly pushes in, focusing on the squirrel's gentle movements. Soft forest sounds fill the air—rustling leaves, distant birdsong, and a gentle breeze. The golden ornaments shimmer in the sunlight as the squirrel continues to eat."
},
"_meta": {
"title": "CLIP Text Encode (Prompt)"
}
},
"143:126": {
"class_type": "RandomNoise",
"inputs": {
"noise_seed": 0
},
"_meta": {
"title": "RandomNoise"
}
},
"143:132": {
"class_type": "LTXVAddGuide",
"inputs": {
"frame_idx": 0,
"image": [
"158",
0
],
"latent": [
"143:149",
0
],
"negative": [
"143:114",
1
],
"positive": [
"143:114",
0
],
"strength": 1,
"vae": [
"143:103",
2
]
},
"_meta": {
"title": "LTXVAddGuide"
}
},
"143:134": {
"class_type": "LoraLoaderModelOnly",
"inputs": {
"lora_name": "ltx-2-19b-ic-lora-canny-control.safetensors",
"model": [
"143:103",
0
],
"strength_model": 1
},
"_meta": {
"title": "Load LoRA"
}
},
"143:138": {
"class_type": "LTXVSeparateAVLatent",
"inputs": {
"av_latent": [
"143:107",
1
]
},
"_meta": {
"title": "Separate AV Latent"
}
},
"143:139": {
"class_type": "LTXVAudioVAEDecode",
"inputs": {
"audio_vae": [
"143:96",
0
],
"samples": [
"143:138",
1
]
},
"_meta": {
"title": "LTXV Audio VAE Decode"
}
},
"143:143": {
"class_type": "RandomNoise",
"inputs": {
"noise_seed": 0
},
"_meta": {
"title": "RandomNoise"
}
},
"143:144": {
"class_type": "VAEDecodeTiled",
"inputs": {
"overlap": 64,
"samples": [
"143:138",
0
],
"temporal_overlap": 8,
"temporal_size": 4096,
"tile_size": 512,
"vae": [
"143:103",
2
]
},
"_meta": {
"title": "VAE Decode (Tiled)"
}
},
"143:145": {
"class_type": "PrimitiveInt",
"inputs": {
"value": 24
},
"_meta": {
"title": "Int"
}
},
"143:148": {
"class_type": "PrimitiveFloat",
"inputs": {
"value": 24
},
"_meta": {
"title": "Float"
}
},
"143:149": {
"class_type": "LTXVImgToVideoInplace",
"inputs": {
"bypass": [
"169",
0
],
"image": [
"165",
0
],
"latent": [
"143:115",
0
],
"strength": 1,
"vae": [
"143:103",
2
]
},
"_meta": {
"title": "LTXVImgToVideoInplace"
}
},
"143:151": {
"class_type": "LTXVImgToVideoInplace",
"inputs": {
"bypass": [
"169",
0
],
"image": [
"165",
0
],
"latent": [
"143:112",
0
],
"strength": 1,
"vae": [
"143:103",
2
]
},
"_meta": {
"title": "LTXVImgToVideoInplace"
}
},
"143:93": {
"class_type": "CFGGuider",
"inputs": {
"cfg": 3,
"model": [
"143:134",
0
],
"negative": [
"143:132",
1
],
"positive": [
"143:132",
0
]
},
"_meta": {
"title": "CFG Guider"
}
},
"143:94": {
"class_type": "KSamplerSelect",
"inputs": {
"sampler_name": "euler"
},
"_meta": {
"title": "KSamplerSelect"
}
},
"143:95": {
"class_type": "LTXVScheduler",
"inputs": {
"base_shift": 0.95,
"latent": [
"143:116",
0
],
"max_shift": 2.05,
"steps": 20,
"stretch": True,
"terminal": 0.1
},
"_meta": {
"title": "LTXVScheduler"
}
},
"143:96": {
"class_type": "LTXVAudioVAELoader",
"inputs": {
"ckpt_name": "ltx-2-19b-dev-fp8.safetensors"
},
"_meta": {
"title": "Load LTXV Audio VAE"
}
},
"143:97": {
"class_type": "LTXAVTextEncoderLoader",
"inputs": {
"ckpt_name": "ltx-2-19b-dev-fp8.safetensors",
"device": "default",
"text_encoder": "gemma_3_12B_it_fp4_mixed.safetensors"
},
"_meta": {
"title": "Load LTXV Audio Text Encoder"
}
},
"143:98": {
"class_type": "KSamplerSelect",
"inputs": {
"sampler_name": "gradient_estimation"
},
"_meta": {
"title": "KSamplerSelect"
}
},
"143:99": {
"class_type": "ManualSigmas",
"inputs": {
"sigmas": "0.909375, 0.725, 0.421875, 0.0"
},
"_meta": {
"title": "ManualSigmas"
}
}
})
# run() also passes api_key to the partner nodes in this workflow.
job = client.run(workflow, api_key=api_key)常见问答
The Canny node detects edges in video frames, providing a guide for the LTX-2 model to generate videos with precise edge control.
Yes, you can use high-resolution settings like 1920x1088, but ensure that width and height are divisible by 64, and frame count by 8+1.
The workflow will not produce errors but will adjust to the closest valid parameters to ensure smooth operation.
The LTX-2 model maintains structural consistency and enhances visual details, ensuring high-quality video output.