TF Resume From Level
The node that makes an edit real
- levels
- pipeline
- levels
- info
Here's the node people quietly skip and then get confused: TF Feature Edit and TF Shape Edit don't produce a finished image - they edit a canvas at level l*, and this node is what turns that into a new image. TF Resume From Level re-samples every level above l*, conditioned on the edited canvas sitting there. Levels below l* are left exactly as they were. That's not a design choice so much as a mathematical consequence: sampling is Markov in the level index, so an edit can only ever propagate upward. An un-resumed edit leaves the finer levels stale - TF Levels Info will literally say "EDITED at level 2, not yet resumed."
It also does no sampling itself until you look at the inputs. levels is the edited trajectory, seed (default 592) drives the re-sampling of everything above l*, and level defaults to -1 - auto - which means resume from whichever level the upstream edit wrote to. That's the node's smartest bit: wired right after an edit, it can't drift. If you set a level yourself it resumes from there instead, which is legal and occasionally useful, but the tooltip warns the default is what an edit normally wants. class_id defaults to -1 auto too, keeping the trajectory's own class - right for an edit, since changing class mid-edit is almost never intended (it's advanced for a reason). pipeline is only for trajectories that lost their provenance, like ones from TF Load Levels.
The mechanics under the hood are a small marvel of reuse worth knowing about: rather than reimplement Trajectory Forcing's sampling, the pack routes the resume through the upstream Pipeline.edit with a no-op token exchange (one token copied onto itself), because "install this canvas at level l*, then re-sample every finer level" is the edit operation with the exchange bolted on. The pack does its actual edits in numpy and hands the finished canvas to the model; this node neutralizes the exchange half and keeps the resume half.
What comes back on the levels output is a new trajectory: re-sampled above l*, identical below, with the edit history extended by one line and the dirty flag cleared - unless you resumed from a level above the edit, in which case the node correctly refuses to clear it, because those edited levels are exactly as stale as they were. That bookkeeping is the difference between a workflow that narrates its own state and one where you have to guess.
The failure mode the README points at: an edit "appearing to do nothing" is usually this node never having run, or running from the wrong level. If the levels above the edit look stale, TF Resume From Level has not run. If it ran and the result still looks off, check what was actually selected - an empty selection resumes nothing meaningful. And once you're comparing before and after, remember one pair of images can't separate the edit from the seed - that's TF Sweep Edit's job, which runs this same resume against a no-edit baseline per arm.
Install
Pack-standard, same story as every TF node: Manager → search Trajectory Forcing, or git clone https://github.com/korayulusan/ComfyUI-TrajectoryForcing into custom_nodes/. The whole pack runs JAX inside ComfyUI and needs its own Python 3.11 environment on CUDA 12; requirements.txt is deliberately empty so Manager can't rewrite the torch your other nodes depend on, and install.py either adds the JAX stack or declines with a printed reason. Declining is normal - README's env/setup.sh builds the separate venv. First-run downloads (flow checkpoint ~2 GB, RAE decoder ~1.6 GB) happen automatically. Health check:
cd ComfyUI/custom_nodes/ComfyUI-TrajectoryForcing
python -m tf_nodes.doctor
Inputs (5)
| Name | Type | Default | Description |
|---|---|---|---|
| levels | TF_LEVELS | — | |
| seed | INT | 5920–18446744073709550000 | Sampling seed. Re-sampling with the same seed and class reproduces a trajectory exactly. |
| level | INT | -1-1–15 | -1 (auto) resumes from whichever level the upstream edit wrote to. Set a level to resume from somewhere else instead. Levels below it are left untouched either way. |
| class_id | INT | -1-1–999 | Class the re-sampled levels are conditioned on. -1 (auto) keeps the trajectory's own class, which is what an edit normally wants. |
| pipelineopt | TF_PIPELINE | Usually unnecessary: the trajectory carries the pipeline that made it. Wire it for a trajectory from TF Load Levels. |
Outputs (2)
| Name | Type | Description |
|---|---|---|
| levels | TF_LEVELS | — |
| info | STRING | — |