Length, quiet weeks and filler
generate --include steers a new cut and has the selection protections described here. A web pool tick saves an owner revision without scoring or choosing pictures again.
A film's target length is where it starts, not a promise. A month with three photographed days gets about 20 seconds, not a minute, and a quiet month with a week of nothing in it spends no shot on that week. When a film runs out of pictures worth showing, it ends early. A shorter film with every shot earned beats a full one padded with the fridge, the ceiling and a screenshot.
Taken to the end, a period can hold nothing worth a film at all: three pictures of a floor
being laid, say. Then no film is made, the run says Nothing worth a film in February 2019 and
exits 0. That is an answer, not a failure. But one shot worth showing is a film: a special day
that keeps two good clips gets a 13-second film, not nothing. The only exception is on this day,
which is about a day coming back, so it needs two years that hold something. A period with no pictures in it at all (a wrong date
range, a filter, Immich unreachable) still ends in an error and exit 1.
How the target itself is set (per memory type, per active day, --duration) is on
Film lengths.
How long a shot is held
The constants live in analysis/editorial_structure_budget.py.
| Shot | Hold |
|---|---|
| A still, no-model draft | 4.0 s when starred or someone Immich knows is in it, 3.5 s otherwise |
| A still, model-planned film | 4.0 s |
| A video | its length, up to 6.0 s; to the end of a sentence when someone is talking at the cut, never past 12 s from the start |
| A video under 2.0 s | not a shot at all |
| A Live Photo playing as motion | its clip, up to 6.0 s |
| A Live Photo playing as its still | 3.5 s in the rules draft without a favourite or known person; 4.0 s after motion measurement |
| The film's first and last still | +0.5 s, never past 5.0 s |
Fitting the length
A film has more candidate shots than seconds, so two passes fit it.
The trim (trim_to_timing_budget, run after the draft and again once motion and speech are
measured) drops whole shots, lightest story first: none and glimpse stories, then the extra
shots of the lightest story, then its only shot, and the heaviest story's only shot last. Inside one
story the latest shot goes first. A picture passed with generate --include is never dropped, and a favourite is never
dropped while a shot nothing vouches for (no star, no recorded video, nobody Immich knows, not included with --include)
is still in the film. In a film that gives every year a shot (a long person film, a custom film over
several ranges), a year's only shot goes after every other one.
The shave takes 0.5 s off the longest hold, over and over, while the film is over length. It never takes a hold under 3.5 s (or under the shot's own length, if that was shorter) and never cuts through a sentence. A video is never dropped for being long.
Quiet weeks get no shot
On the no-model path, a happening with no indicator of its own reads as background, and background
weighs none, which is 0 slots (GATE_WEIGHT and weight_caps, see
Moments, episodes and stories). An indicator is
any of: a favourite, a video, close family in it, a day four times busier than your median day, being
away from home or outside your 12 usual cities, or being the only happening of a part the film must
cover. A favourite, video, close-family presence or required-part indicator reads maybe (a glimpse, one shot); a busy day or being away reads remarkable (a minor story). Album happenings also read remarkable.
A week of ordinary evenings at home with no star, no video and no close family is exactly that
case. Three favourites or a big close-family story still lift a story to major, so a quiet week
that holds something you care about is never quiet to the editor. On this day is the exception:
every year of it gets a shot, however quiet
(Every year gets a shot).
Mostly quiet is a different household
That rule assumes the film has plenty of indicated weeks to carry it, and a quiet week here or
there just steps aside. A library of a cat, with a weekly photo and nothing else, has no stars, no
videos, no close family on any of it: every week would read none and the film would come out
empty.
So when at least two thirds of a period's at-home weeks have no indicator at all, the no-model path stops treating that as the ordinary case and funds each of them with its own best picture instead: sharpest frame, no SOFT, DARK or BLOWN OUT warning, not a screenshot or a document, not on hold. A week whose only pictures fail every one of those stays unfunded anyway, same as before, and the reason why is kept on the record. Below two thirds, the ordinary rule still applies: a quiet week among mostly-indicated ones goes short, same as it always did.
Filler nothing vouches for
A quiet month can still have more slots than shots anyone vouches for, and the leftover slots go to
whatever stands. So every film drafted from the rules gets one last removal pass
(drop_filler_nothing_vouches_for), after the duplicate review. In order: read the settled
shot, keep every indicator and protected shot, check the empty-frame evidence, then remove
unsupported filler without refilling the slot.
It runs on the no-model film and on a polished one alike. The polish refines the no-model film, so it never keeps what that film would drop: a caption that misreads a printed recipe as a posed child does not get it past this pass. A screen that plays as a Live Photo, or shows someone Immich knows, still stays. So does one shot of a year this pass would leave empty, in a film that gives every year a shot: the one that stands best. The run record keeps what this pass left out; see what a run leaves behind.
An album handed over with a written subject (--from-album ... --subject ...) skips this pass. Every
picture in it was picked for that subject, so a loaf in a bread film is the film, not filler
(Picking each shot).
Going short, on purpose
The draft tries to reach its length before it gives up the seconds:
- Depth. When the film still has content seconds free after every pass, it spends them
inside the moments it already shows (
editorial_story_depth_fill.py): first moments no pick took, then further frames of each chosen moment, one round at a time, round-robin across every funded story so one story never drains a round meant for its neighbours. A 36-minute moment of laps on a track can fill a short film this way. A frame only counts once it is its own shot: a video counts once its window clears every kept video's window, anything else counts once it is a real five minutes from every kept shot of the same capture group, and a heap of frames sharing one timestamp (a placeholder date, a burst, a pile of scans) is one shot, not many. Capacity is distinct shots, with no flat per-day or per-moment ceiling: a dense day is not held to the same cap as a quiet one. Videos come before stills, frames are spread across the moment's time, and the story's place bound grows with the slots it now spends. Eligible favourites come first; equally preferred frames spread furthest in time from those already in. Every one must stand and must not look like its neighbours. The fill stops once the film's content seconds reach the budget, minus the usual 15% tolerance; when distinct shots run out first, the run logs how many distinct shots it found and how many seconds short of the budget the film landed. A film of one repeated scene stays short. - Readmission. A frame refused for looking like another, or for crowding its place, comes back when nothing else can fill the slot. A favourite refused for crowding its place comes back sooner. While the film has a free slot it takes that one and nobody leaves. Once the film is full, it comes back before a shot nothing vouches for keeps the slot it freed. That shot leaves (the weakest first, a story's only shot last, and never a year's only shot in a film that gives every year one). The run record keeps which shot was displaced for a favourite.
- With a model, a film still short by S seconds reads up to 2 × ceil(S / 3.5) episodes it never reached, and seats the ones whose reading records something (What a model adds).
What never happens: a slot filled with a frame nothing vouches for, a filler frame dropped by the pass above refilled, or a film padded with a still repeated for time. The final scene-duplicate check also accepts a shorter film: falling below the target's 15 % tolerance does not protect a repeated scene. Owner-required shots and someone's only family appearance keep their existing protections.
The run record says how it landed: near_target when the film is within 15 % of its content length,
search_limited or editorial_shortfall when it ran shorter, with the seconds behind it.