Problem
fly_georef() excludes non-square footprints, so the digital frames #32 just gave
footprints to cannot be georeferenced.
georef_one() maps image corners onto footprint corners positionally
(R/fly_georef.R, # fly_footprint builds: BL, BR, TR, TL, BL) and then shifts that
mapping by bearing_to_rotation(), a 90-degree quantization of the flight bearing. That
scheme was calibrated against north-up 9x9 negatives, where the footprint is square and
axis-aligned.
A digital footprint breaks both assumptions:
- It is already rotated onto the flight line by
fly_footprint(), so its ring
carries the bearing. Applying bearing_to_rotation() on top counts it twice.
- It is not square — 1.10:1 to 1.80:1. On a square, a wrong-by-90 corner mapping is
harmless. On a 1.76:1 rectangle it maps a landscape image onto a portrait quad and the
warp squashes it.
Why it was deferred rather than guessed
The right corner mapping for a pre-rotated rectangle depends on camera mounting relative
to flight direction. That is precisely what bearing_to_rotation() was empirically
fitted to, and it cannot be re-derived by reasoning — nothing in the test suite looks at
pixels, so a wrong warp would pass every assertion.
Corrected while doing the work. This section originally said the mapping could not
be established "without imagery to check the result against", and the approach below
was built on that. It was wrong, and it sent the plan toward licence-restricted
orthophotos. The catalogue publishes per-frame exterior orientation through
patb_georef_url — a column fly_fetch(type = "georef") already supported — and
consecutive frames overlap enough to check each other, so no external imagery is needed
at all. The corrected approach is below.
Digital frames had no footprint at all before #32, so excluding them is the same
coverage as before rather than a regression. It is now explicit and warned about instead
of silent.
Approach
Half the question is settled by geometry and needs no imagery: the image's long pixel
axis must land on the footprint's long ground edge, which rejects rotations 0 and 180.
That leaves 270 and 90, which differ by 180 degrees about the footprint centre — a
rectangle is symmetric under that, so nothing geometric separates them.
The remaining bit is settled three ways, all on public data:
- Per-frame exterior orientation from
patb_georef_url. Regress the camera's image
x-axis azimuth against the flight heading, and use sum-versus-difference as the
control — a rigid mount holds the difference constant, a ground frame read with its
axes swapped holds the sum constant, and the two are indistinguishable on a project
that flies one axis.
- Adjacent-frame overlap correlation. Consecutive frames overlap heavily, so at the
correct rotation their common ground agrees; a 180-degree error reflects each frame
about its own centre. Needs no reference imagery — the frames check each other.
- FWA lake darkness, as an outside opinion, on frames whose water sits off the
footprint centre so the test can discriminate.
Then remove the exclusion in fly_georef(), and pin an invariant that needs no reference
imagery so nothing here recurs.
Value
If we do it: the whole post-2010 catalogue becomes georeferenceable, not just
sizeable.
If we never do: digital frames get footprints, coverage and selection but no
georeferenced output — visibly excluded with a warning rather than silently wrong, which
is the important half.
Follows #32
Problem
fly_georef()excludes non-square footprints, so the digital frames #32 just gavefootprints to cannot be georeferenced.
georef_one()maps image corners onto footprint corners positionally(
R/fly_georef.R,# fly_footprint builds: BL, BR, TR, TL, BL) and then shifts thatmapping by
bearing_to_rotation(), a 90-degree quantization of the flight bearing. Thatscheme was calibrated against north-up 9x9 negatives, where the footprint is square and
axis-aligned.
A digital footprint breaks both assumptions:
fly_footprint(), so its ringcarries the bearing. Applying
bearing_to_rotation()on top counts it twice.harmless. On a 1.76:1 rectangle it maps a landscape image onto a portrait quad and the
warp squashes it.
Why it was deferred rather than guessed
The right corner mapping for a pre-rotated rectangle depends on camera mounting relative
to flight direction. That is precisely what
bearing_to_rotation()was empiricallyfitted to, and it cannot be re-derived by reasoning — nothing in the test suite looks at
pixels, so a wrong warp would pass every assertion.
Digital frames had no footprint at all before #32, so excluding them is the same
coverage as before rather than a regression. It is now explicit and warned about instead
of silent.
Approach
Half the question is settled by geometry and needs no imagery: the image's long pixel
axis must land on the footprint's long ground edge, which rejects rotations 0 and 180.
That leaves 270 and 90, which differ by 180 degrees about the footprint centre — a
rectangle is symmetric under that, so nothing geometric separates them.
The remaining bit is settled three ways, all on public data:
patb_georef_url. Regress the camera's imagex-axis azimuth against the flight heading, and use sum-versus-difference as the
control — a rigid mount holds the difference constant, a ground frame read with its
axes swapped holds the sum constant, and the two are indistinguishable on a project
that flies one axis.
correct rotation their common ground agrees; a 180-degree error reflects each frame
about its own centre. Needs no reference imagery — the frames check each other.
footprint centre so the test can discriminate.
Then remove the exclusion in
fly_georef(), and pin an invariant that needs no referenceimagery so nothing here recurs.
Value
If we do it: the whole post-2010 catalogue becomes georeferenceable, not just
sizeable.
If we never do: digital frames get footprints, coverage and selection but no
georeferenced output — visibly excluded with a warning rather than silently wrong, which
is the important half.
Follows #32