Nodes/comfyui-lrw-nodes/Parallel Transport (LRW)
ComfyUI Node

Parallel Transport (LRW)

Carry a style direction across latent space

By lajjadred·Created 3 months ago·Updated 3 months ago· 12
Parallel Transport (LRW)
  • latent_from
  • latent_to
  • latent_vector
  • metric
  • transported_vector
method
n_rungs5

The style-transfer trick this pack is built around lives here. The idea: you find a direction in latent space that means something - "add a hat," "shift the lighting" - via LRW_LatentVectorFromDiff, but that direction was measured at one specific location in latent space, and latent space is curved. Move the vector to a different image and a naive copy of it might point somewhere meaningless. Parallel Transport is the node that carries the vector from where you measured it to where you want to use it, keeping its meaning intact along the way.

How it works

You give it a start latent, an end latent, and the vector you want moved. It computes a geodesic between start and end on your metric, then drags the vector along that path frame by frame using one of two classic algorithms:

  • Schild's Ladder - the default pick. Builds the transported vector with a series of parallelogram-ish steps; robust and well-understood.
  • Pole Ladder - an alternative that can be more accurate when the path is long but is a bit more sensitive to how you configure it.

n_rungs (default 5) is how many steps the ladder uses along the path. More rungs = more faithful transport, more compute. If the result looks off, nudge this up.

The inputs:

  • latent_from, latent_to - the source and destination latent points.
  • latent_vector - the direction you're carrying, straight from LRW_LatentVectorFromDiff.
  • metric - required. From LRW_VAEDecoderBridge or LRW_PullbackMetric. No metric, no curved path, and the node will just refuse the wire.
  • method, n_rungs - the ladder algorithm and its resolution.

Output is one transported_vector (a LATENT), which you then add onto your target latent with LRW_ApplyTransportedVector. Full chain: VAEEncode(A), VAEEncode(B)LRW_LatentVectorFromDiffLRW_ParallelTransport (with A as latent_from, your target as latent_to) → LRW_ApplyTransportedVector → KSampler. The pack ships a style-transfer example workflow doing exactly this.

Managing expectations

Parallel transport is the mathematically serious node in this pack - it's the one that genuinely can't be replicated with a few standard nodes, and it's the thing the author's latent-riemannian-world package was built to do. But it only shines when the metric is meaningful, which means the expensive pullback-metric path (LRW_VAEDecoderBridge/LRW_PullbackMetric). On the WAN side that's off the table, which is why this node has no WAN counterpart in the pack. Also, transport between very different latents (huge geometry change) is a hard problem even with a good metric; keep experiments to plausible pairs.

Install

Part of comfyui-lrw-nodes by lajjadred. Search the pack in ComfyUI Manager, or:

cd ComfyUI/custom_nodes
git clone https://github.com/lajjadred/comfyui-lrw-nodes
cd comfyui-lrw-nodes
pip install -r requirements.txt

Restart ComfyUI. Real deps: latent-riemannian-world >= 0.3.0, torch >= 2.4, Python 3.12+. The pack had early registration/import bugs that made nodes show as broken or UNKNOWN - fixed upstream, so git pull + full restart, and make sure you don't have two copies of the pack in custom_nodes. License is BSL-1.1.

Categorylrw/transport

Inputs (6)

NameTypeDefaultDescription
latent_fromLATENT
latent_toLATENT
latent_vectorLATENT
metricMETRIC
methodCOMBO2 options: PoleLadder, SchildsLadder
n_rungsINT51–20

Outputs (1)

NameTypeDescription
transported_vectorLATENT