Sec-ant / user-media-stream

A streamlined JavaScript library designed for web applications to easily handle camera streams.
https://www.npmjs.com/package/user-media-stream/v/latest
MIT License
2 stars 0 forks source link

Request for comments #2

Closed Sec-ant closed 8 months ago

Sec-ant commented 8 months ago

Hi @gruhn,

I've always wanted to decouple the logic of the camera operations, which has been battle-tested by a large amount of real world devices/browsers, out of the repo vue-qrcode-reader, so it can be used in other projects adopting react, svelte, web components, etc., or some other projects which just want to interact with web cameras.

So I created this repo and published the package. While the name is not very obvious, my resistance to use a scoped name is even greater :D

Like I said above, this package is mainly just an extraction of the original code to make it reusable. But I also did some modifications to make it more versatile and universal for various use cases, not just for barcode detections. One of them is that it supports full customization of all kinds of media constraints/capabilities. Another is that it keeps tracks of all video and audio tracks. I also simplified the task queue implementation and did some other tweaks like reducing the capability acquiring time, a better chunk splitting for webrtc-adapter...

And I'd love to hear your inputs on this, including but not restricted to: Does the code look good to you? Are there any traps or quirks unnoticed? Will you consider maybe switching out the original code in favor of this (when this is stable of course)? Do you want to be credited in some particular manner? Or anything you can think of. Your inputs will be much appreciated.

Thanks in advance!

Sec-ant commented 8 months ago

Actually I'm a little hesitated now. An object oriented API seems more intuitive and fits here better.

const userMediaStream = createUserMediaStream(...);

userMediaStream.start();
userMediaStream.stop();
userMediaStream.setConstraints(...);
gruhn commented 8 months ago

Damn, thanks for the effort. I would prefer to avoid too much decoupling though and camera.ts is still fairly small file. If the "camera handling" is in its own package, making changes to it that effect vue-qrcode-reader are a bit more cumbersome. One needs to publish a new version and then install the update in vue-qrcode-reader. Also you don't directly see how changes affect the demo page in PRs.

so it can be used in other projects adopting react, svelte, web components, etc.,

That's a good point. In the past I considered rewriting the whole library in vanilla JS, so frameworks can integrate it with minimal wrapper components. But never got to it. Either way, that would probably be a complete fork project.

Sec-ant commented 8 months ago

If the "camera handling" is in its own package, making changes to it that effect vue-qrcode-reader are a bit more cumbersome. One needs to publish a new version and then install the update in vue-qrcode-reader. Also you don't directly see how changes affect the demo page in PRs.

You make a fair point. However, I anticipate minimal changes to this package in the future once it's stable. The main maintenance work would likely only involve addressing cross-platform compatibility issues.

In the past I considered rewriting the whole library in vanilla JS, so frameworks can integrate it with minimal wrapper components.

Actually, that’s exactly what I’m working on with my videoScanner.ts in zxing-wasm. Currently, vue-qrcode-reader employs barcode-detector, a package primarily aimed at providing an API consistent with web spec standards for polyfill purposes. This results in numerous unnecessary exception checks and some performance drawbacks, such as creating a new canvas for each scan. Thus, I plan to build a scanning feature directly based on zxing-wasm, which not only improves performance but also allows for more customization compared to barcode-detector.

From my perspective, there are two main tasks: attaching the camera feed to a video element, as done in this repository, and performing continuous detection on video frames, which is what videoScanner.ts accomplishes. This latter is also largely inspired by the code in vue-qrcode-reader’s scanner.ts. The scanner's core logic will be exported in vanilla JS for users to call. Additionally, I plan to encapsulate this core logic with framework-specific APIs and further wrap it into ready-to-use components. The hierarchy would be

core logic in vanilla JS -> react hooks/vue composables/... -> react/vue/... components

Users then would be able to utilize various functionalities in the following manner:

import { createUserMediaStream } from "user-media-stream";
import { videoScanner } from "zxing-wasm/scanner";
import { useVideoScanner, VideoScanner } from "zxing-wasm/react";

Since much of the code references vue-qrcode-reader, I felt it necessary to inform you. I also believe that making significant changes to vue-qrcode-reader isn't very feasible, so most of the work will likely be focused on the zxing-wasm repository. I would warmly welcome your involvement. If you choose to continue focusing on vue-qrcode-reader, I am also willing to contribute back any issues I identify and resolve during development, considering many of the core logics are similar.