Files
DarkRoom/ui/dr-ui/Cargo.toml
T
dtourolle 6507593715 Hand the drag ghost to the renderer through a file, so it draws
The bitmap under the cursor was a solid red rectangle. Slint's drag
overlay uploads the image as a texture, draws it and drops the texture in
one call; with the wgpu FemtoVG renderer the drop is immediate and the
draw is deferred to the flush, so the frame binds femtovg's placeholder —
which is red. An image with a cache key survives in the texture cache
until after the flush, and only a path gives one. So the composite goes
to the data directory's scratch as a PNG and comes back through
load_from_path; one file per drag, removed when the drag ends. A
workaround for Slint 1.17.1, written up as one beside the code.
2026-09-20 15:58:44 +02:00

156 lines
7.6 KiB
TOML

[package]
name = "dr-ui"
version.workspace = true
edition.workspace = true
rust-version.workspace = true
license.workspace = true
[dependencies]
dr-types.workspace = true
# TRACES: FR-DEV-6
# Reading Lightroom `.xmp` presets. Its own crate because the translation names
# operations, which the interface may not — see `ui_names_no_operation.rs`.
dr-preset-xmp.workspace = true
# No `readback`. S1 wired Slint's texture import, so the develop view hands
# the compositor the texture itself and there is no display round-trip left to
# gate (ARCH §6.1, AC-8). The export path reads pixels back through
# `export_pixels`, which is ungated and always was.
#
# `segment-readback` *is* on, and it is not a contradiction of the above. It
# gates the region-graph transfer that local masking is built on: once per
# image, on a worker, off the frame path. The display round-trip AC-8 forbids
# stays behind its own switch, which remains off. See `dr-gpu/src/segment.rs`.
dr-gpu = { workspace = true, features = ["segment-readback"] }
# The semantic arm and its weights, for local adjustments (FR-DEV-3, D14).
dr-segment = { workspace = true, features = ["semantic", "embedded-model"] }
dr-decode.workspace = true
serde_json.workspace = true
tokio.workspace = true
reqwest.workspace = true
dr-plat.workspace = true
dr-sync.workspace = true
dr-xmp.workspace = true
dr-sync-folder.workspace = true
dr-sync-nextcloud.workspace = true
dr-export.workspace = true
# The panorama's geometry and its keypoint detector (§3.11). The detector's
# runtime is the same tract the faces and masks already carry.
dr-pano = { workspace = true, features = ["xfeat", "embedded-model"] }
dr-ingest.workspace = true
dr-film.workspace = true
# The lens profile database, here for the same reason dr-film is: dr-pipeline
# knows the maths of lens correction and deliberately has no dependency with
# which to find out which coefficients belong to which lens. The conversion
# between the two crates' mirrored coefficient types happens in `develop.rs`,
# because it is the only place that can see both.
dr-lens.workspace = true
dr-pipeline.workspace = true
dr-catalog.workspace = true
# The face pipeline, with the ONNX runtime: this is the layer that actually
# runs the models over the library (docs/faces.md).
dr-face = { workspace = true, features = ["inference"] }
# The engine behind both. `native` here means the *app* may look for a
# runtime file; the build stays C-free either way (docs/inference.md §3).
dr-inference-engine = { workspace = true, features = ["native"] }
dr-thumbs.workspace = true
# For the drag ghost only: the composite under the cursor has to reach the
# renderer through a file, and the fan of thumbnails needs alpha, which the
# thumbnail store's JPEG cannot carry. See `collections_ui::drag_image_via_file`.
png = "0.18"
# The library module writes scan results straight into the catalog, so it
# needs the same SQLite types dr-catalog exposes.
rusqlite.workspace = true
# The renderer is shared, but the backend is not: winit on desktop,
# android-activity on Android, and enabling both makes the backend selector
# pick at random. So the backend features live on the target-specific
# dependencies below rather than here.
#
# `renderer-femtovg-wgpu` rather than `renderer-femtovg`: the latter is
# FemtoVG over OpenGL, and a compositor drawing through GL cannot be handed a
# `wgpu::Texture`. Importing one requires Slint itself to be rendering with
# wgpu, and this is the FemtoVG backend that does (ARCH §6.1, spike S1).
#
# `unstable-wgpu-29` is the other half: the renderer feature makes Slint draw
# with wgpu, and this one exposes the API to say so — `BackendSelector::
# require_wgpu_29` and `Image::try_from(wgpu::Texture)`. Unstable is Slint's
# word for it; the surface is small and the alternative is the 7 ms round-trip.
#
# `renderer-femtovg` is *not* kept alongside as a fallback, though it would
# still compile. Slint's winit backend prefers the wgpu FemtoVG renderer
# whenever both are built, so the GL one would only ever be reached by someone
# setting `SLINT_BACKEND=winit-femtovg` — and on that path an imported texture
# is not drawn at all. FemtoVG-over-GL has no branch for a `wgpu::Texture`, so
# it falls through to "render this image to a buffer", gets nothing back, and
# draws nothing. A blank canvas with no error is a far worse failure than the
# one below, so the fallback is removed rather than left as a trap.
#
# Consequence worth stating plainly: the desktop app now needs a working wgpu
# adapter to open a window at all. Slint refuses a CPU adapter for this
# renderer unless `SLINT_WGPU_CPU` is set in the environment.
# TEST BUILD: the wgpu renderer features have moved to the desktop-only
# dependency below. On Android they made `AndroidWindowAdapter` choose
# `SkiaRenderer::default_wgpu_29`, and so put the app on wgpu's Vulkan
# swapchain — which hardcodes `preTransform = IDENTITY` (gfx-rs/wgpu#3345).
# Without them the Android backend uses `SkiaRenderer::default`, which on
# Android resolves to Skia over OpenGL, where the driver owns the display
# rotation and there is no transform to get wrong.
slint = { workspace = true, features = ["compat-1-2"] }
wgpu.workspace = true
anyhow.workspace = true
# `SettingsError` distinguishes an io failure from a malformed file, which the
# settings page reports differently; anyhow would flatten both to a string.
thiserror.workspace = true
log.workspace = true
pollster.workspace = true
# Runtime YAML only for `live-style`; release builds read the tokens the
# Slint compiler folded in at build time and never touch style.yaml.
serde_norway = { workspace = true, optional = true }
# Backend per platform. Slint already declares its android-activity backend
# under `cfg(target_os = "android")`, so this only has to name the feature;
# cargo resolves it away entirely on desktop.
[target.'cfg(not(target_os = "android"))'.dependencies]
slint = { workspace = true, features = [
"backend-winit",
"renderer-femtovg-wgpu",
"unstable-wgpu-29",
] }
[target.'cfg(target_os = "android")'.dependencies]
slint = { workspace = true, features = ["backend-android-activity-06"] }
# Opening the sign-in URL needs an ACTION_VIEW Intent — Android has no
# xdg-open. Version-matched to Slint's Android backend so both halves of the
# process agree on the JavaVM types; ndk-context supplies the VM and activity
# that android-activity's glue already stashed.
jni = "0.22"
ndk-context = "0.1"
[build-dependencies]
slint-build.workspace = true
# build.rs generates theme.slint from style.yaml (S2).
serde_norway.workspace = true
[features]
# Compile the scene model into the binary.
#
# On by default for the desktop app and *off* for Android, which unpacks the
# same graph from APK assets instead — 24 MB of constant is worth avoiding in a
# mobile install and not worth the plumbing to avoid on a desktop one. Without
# it `segmentation::scene_categories` falls back to the installed-file lookup,
# which is what a packaged desktop build uses too.
scene-model = ["dr-segment/embedded-scene-model"]
default = []
# Debug convenience: re-read style.yaml at startup so a palette can be tuned
# without rebuilding. Costs the constant-folding of every token, so it stays
# off by default and has no business in a release build.
live-style = ["dep:serde_norway"]
[dev-dependencies]
# The face_index batch job wants a log level from the environment; the library
# itself only ever calls `log`, and picks up whatever the application installs.
env_logger.workspace = true
# Standing in a test backend behind `dyn RemoteBackend`, which is an
# `#[async_trait]` trait — implementing one needs the same attribute.
async-trait.workspace = true