Website | Code

libobscura lets you use your camera

libobscura

libobscura is a set of camera-related libraries, handling the difficult parts of using a Linux camera for you.

Minimal example

Get frames in 8 API calls, access their data in 2 more.

let cameras_list = vidi::actors::camera_list::spawn()?;
let cameras = cameras_list.cameras();
let camera = cameras_list.create(&cameras[0].info.id)
    .expect("No such camera")
    .expect("Failed to create camera");

let mut camera = camera.acquire();
if let Ok(ref mut camera) = camera {
    let configs = camera.get_supported_configs()?;
    let config = configs.query_configs(ConfigRequest {
        width: Some(640),
        height: Some(480),
        ..ConfigRequest::default()
    }).iter().next().expect("No supported configs");

    let mut stream = camera.start(config, 4).unwrap();

    loop {
        let (buf, meta, _next) = stream.next().unwrap();
        let mmap = buf.memory_map_ro().unwrap();
        let data = mmap.as_slice();
    }
}

Demo

cargo run --bin glium_2

Remember to plug in your camera!

Usage

Add libobscura registry to .cargo/config.toml:

[registries.libobscura]
index = "sparse+https://codeberg.org/api/packages/libobscura/cargo/"

and in Cargo.toml:

vidi = { path = "../vidi", version = "0.3", registry = "libobscura" }

Then copy from the examples.

Devices

Try out your USB camera:

cargo run --bin demo

The Librem 5 has support for collecting frames (demo not adapted yet):

LIBOBSCURA_DEVICES_DIR=crates/vidi/config/ cargo run --bin obscura_getframes -- 'imx7-csi:imx-media:776794edba9cf34e:s5k3l6xx 3-002d'

Aspirations

  • It's hard to use it wrong. No segfaults. Errors guide you to the right track.
  • Point-and-shoot. If that's all you need, you get a RGB buffer in ten lines of code.
  • It's easy to add support for new devices. Great documentation and a good internal API are the goals.
  • It's easy to contribute to. Send patches using the web interface, not a mailing list.

A baby placing a missing block. They are stacked in the Bayer pattern.

Figure: Libobscura will never be friendly enough for every audience.

Why should I care?

If you're an application developer, libobscura is for you! It gives you a reasonable amount of control while preventing mistakes, and it frees you from the trouble of implementing image processing yourself.

If you're a hardware manufactuer, libobscura is also for you! The goal is to make adding new devices really simple as soon as the kernel driver is done.

The libraries

Cameras under Linux require a lot of moving pieces, so libobscura is a collection of many libraries. Some of them were created ust for this purpose, some of them were forked, some were revived.

Hardware support:

General purpose:

The code is stored in the libobscura organization on Codeberg, for most crates inside the libobscura repository.

Dependencies

Libobscura uses as few external dependencies as possible, but not any fewer than that. Rather than reimplement the world, libobscura tries to reduce scope to reach that place. Bigger dependencies like OpenGL libraries are optional, so that the user can decide if they are desired.

Special thanks to the logru project for accepting contributions and for being a backbone of libvidi!

Why is libobscura not on crates.io?

Libobscura is published on its own registry, which requires a small modification to Cargo config (.cargo/config.toml):

[registries.libobscura]
index = "sparse+https://codeberg.org/api/packages/libobscura/cargo/"

I [Dorota] will publish on crates.io once it stops requiring a Github login.

This makes a commercial entity the gatekeeper of a large chunk of the Rust community, which is a political bug. I find it simply insane to host Free Software packages but choose a gatekeeper as hostile to Free Software as Microsoft and this is my protest.

I have a small bounty set aside to anyone who fixes that bug. If you want to, please contact me.

License

Libobscura adheres to the REUSE specification to provide information about copyright and licensing information for each file.

vidi-examples are distributed under the terms of the MIT or Apache 2.0 licenses, at your choice. See vidi-examples Those licenses let you copy-paste the code into your application.

[dma-boom is distributed under the terms of MIT.

The rest of libobscura is distributed under the terms of the LGPL2.1 or later, at your choice. See COPYING.md.

  • If you distribute a modified version of those components, you must share your modifications. (The licenses, MPL 2.0 or LGPL 2.1 or LGPL 3.0, require this).
  • If you distribute those components in a Rust project, even as a dependency, in practice your must also include sources to your software and other dependencies (check LGPL 2.1 or LGPL 3.0 for details).

Funding

Many thanks to Prototype Fund and the German Federal Ministry of Education and Research for paying Dorota to take on this crazy project.

BMBF