Skip to content

Size a UAV frame from manufacturer sensor geometry, not a calibration report #70

Description

@NewGraphEnvironment

Problem

fly_footprint() sizes a digital frame through R/fly_camera_format.R, keyed on
camera_calibration_url / calib_file — the calibration reports the BC Data Catalogue links
for its survey aircraft. A UAV frame has no entry in that catalogue, so today it falls to
inferred_format (sized from focal_length) or unknown_format (empty geometry).

But a UAV's sensor geometry is not unknown — it is published by the manufacturer and is more
precise than anything recoverable from a scanned calibration PDF. There is no route that says
"this frame came from a Mini 4 Pro at 48 MP" and sizes it exactly.

This blocks planning UAV coverage over an AOI, which is the sibling work in stac_uav_bc.
fly_coverage() and fly_select() already do what that needs; only the footprint sizing is
missing.

What is known

DJI Mini 4 Pro, from the published specs:
1/1.3" CMOS, 2.4 µm 4-in-1 pixels (so 1.2 µm native), 48 MP = 8064 × 6048,
6.72 mm actual focal length. Derived sensor 9.68 × 7.26 mm, diagonal 12.10 mm against a
1/1.3" nominal ~12.1 mm — consistent.

At 300 m AGL that gives a 432 × 324 m footprint and 5.36 cm/px.

This is validated against real flight plans, not just arithmetic. Five DJI WPML missions
flown over the Morice (MORR) floodplain in 2026 carry measured transect spacing of 86.0 m and
along-track photo spacing of 65.0 m. Against a 432 × 324 m footprint those are 80.1% side
and 79.9% forward overlap — i.e. the published sensor geometry reproduces the spacings an
independent planner computed, to within a tenth of a percent.

Binning is a mode, not a camera. The same sensor at 12 MP binned (4032 × 3024, 2.4 µm)
gives an identical 432 × 324 m footprint and 10.71 cm/px. Footprint is set by field of view and
height; megapixels only move GSD. So the format table needs a resolution mode alongside the
camera, or a single "Mini 4 Pro" row silently halves or doubles the GSD it implies.

Proposed work

  • Add a UAV sizing route to fly_camera_format.R: sensor dimensions and focal length keyed on
    camera and resolution mode, sourced from manufacturer specs rather than calibration PDFs.
    Mini 4 Pro at 48 MP and at 12 MP as the first two entries.
  • Decide where those rows live — extending inst/extdata/camera_formats.csv versus a sibling
    table. The existing file's columns (width_mm, height_mm, px_cross, px_along,
    pitch_um, focal_mm) already carry everything needed, but its key_type and provenance
    columns (report_serial, source_pdf, retrieved) describe a calibration report and do not
    apply. Whichever way, camera_formats_manifest.csv's drift guard should still cover it.
  • Record the route in footprint_basis so a UAV-sized frame is distinguishable from a film or
    calibration-sized one, consistent with the v0.4.0 decision to refuse rather than estimate.
  • Tests from the measured numbers above: footprint dimensions at 300 m, GSD at both resolution
    modes, and the 80/80 spacings the five real missions imply.

Acceptance

  • fly_footprint() on a Mini 4 Pro frame at 300 m AGL returns a 432 × 324 m rectangle
  • GSD resolves to 5.36 cm/px at 48 MP and 10.71 cm/px at 12 MP, from the same footprint
  • footprint_basis names the UAV route explicitly
  • An unknown UAV camera still returns empty geometry rather than a guess

Scope note

This is a remit question as well as a code change. fly is described as a historic airphoto
toolkit — README, acronym and CLAUDE.md all say legacy — and fly_georef/fly_bearing already
handle digital frames, so the digital path is live rather than hypothetical. Sizing a UAV frame
widens that to "aerial image footprints, whatever produced them", which is a small and
defensible step.

What is explicitly out of scope here, and belongs in the stac_uav_bc sibling issue:
battery endurance budgets, launch-point placement, transect ordering, DJI WPML/KMZ writing.
fly carries no notion of a battery, a home point, a waypoint or a gimbal today (measured: zero
files under R/, tests/ or inst/ mention any of them) and this issue does not add one.

Activity

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions