Skip to content

[camera_web] Re: Support for camera stream on web#7950

Open
TecHaxter wants to merge 73 commits intoflutter:mainfrom
TecHaxter:camera_web_stream
Open

[camera_web] Re: Support for camera stream on web#7950
TecHaxter wants to merge 73 commits intoflutter:mainfrom
TecHaxter:camera_web_stream

Conversation

@TecHaxter
Copy link
Copy Markdown

This PR aims to provide support for strartImageStream and stopImageStream on Web.

#92460

Based on #6944 from the archived plugins repository

Pre-launch Checklist

  • I read the [Contributor Guide] and followed the process outlined there for submitting PRs.
  • I read the [Tree Hygiene] wiki page, which explains my responsibilities.
  • I read and followed the [relevant style guides] and ran the auto-formatter. (Unlike the flutter/flutter repo, the flutter/packages repo does use dart format.)
  • I signed the [CLA].
  • The title of the PR starts with the name of the package surrounded by square brackets, e.g. [shared_preferences]
  • I [linked to at least one issue that this PR fixes] in the description above.
  • I updated pubspec.yaml with an appropriate new version according to the [pub versioning philosophy], or this PR is [exempt from version changes].
  • I updated CHANGELOG.md to add a description of the change, [following repository CHANGELOG style].
  • I updated/added relevant documentation (doc comments with ///).
  • I added new tests to check the change I am making, or this PR is [test-exempt].
  • All existing and new tests are passing.

POV: my first PR on a public repo
Contains required commits from the PR #6443, resolves unnecessary 202 commits

@TecHaxter TecHaxter requested a review from mdebbar September 28, 2025 11:06
@stuartmorgan-g
Copy link
Copy Markdown
Collaborator

From triage: @mdebbar This looks to be ready for re-review.

@stuartmorgan-g
Copy link
Copy Markdown
Collaborator

From triage: @mdebbar, ping on this re-review.

@stuartmorgan-g
Copy link
Copy Markdown
Collaborator

From triage: Still waiting on web team review.

Copy link
Copy Markdown
Contributor

@mdebbar mdebbar left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Overall looks good! Sorry for the long delay.

I only have a few suggestions and nits. After that it should be good to go. Thank you for the contribution!

final bool canUseOffscreenCanvas;

/// The tolerance for the camera streaming frame time.
final int _frameTimeToleranceMs = 8;
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Can this be a getter that changes dynamically based on the fps value?

E.g.

Suggested change
final int _frameTimeToleranceMs = 8;
final get int _frameTimeToleranceMs => 1000 / cameraStreamFPS ~/ 2;

Copy link
Copy Markdown
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Sure. Done👍

///Used in [takeFrame] if `OffscreenCanvas` is supported
web.OffscreenCanvas? _offscreenCanvas;

///Returns frame at a specific time using video element
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
///Returns frame at a specific time using video element
/// Returns frame at a specific time using video element

///Used in [takeFrame] if `OffscreenCanvas` is not supported
web.CanvasElement? _canvasElement;

///Used in [takeFrame] if `OffscreenCanvas` is supported
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
///Used in [takeFrame] if `OffscreenCanvas` is supported
/// Used in [takeFrame] if `OffscreenCanvas` is supported

return jsUtil.hasProperty(window, 'OffscreenCanvas'.toJS);
}

///Used in [takeFrame] if `OffscreenCanvas` is not supported
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
///Used in [takeFrame] if `OffscreenCanvas` is not supported
/// Used in [takeFrame] if `OffscreenCanvas` is not supported

}
}

///Used to check if browser has OffscreenCanvas capability
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
///Used to check if browser has OffscreenCanvas capability
/// Used to check if browser has OffscreenCanvas capability

Comment on lines +387 to +388
_offscreenCanvas!.width != width ||
_offscreenCanvas!.height != height) {
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Can we resize the existing offscreen canvas instead of creating a new one?

Copy link
Copy Markdown
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

That would be a great optimization. Done👍
I have also optimized the offscreen canvas context call by preserving it from the first call.
Please do take a final look at that. Many thanks.

Comment on lines +401 to +402
_canvasElement!.width != width ||
_canvasElement!.height != height) {
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Same here

'Computed dimensions are zero: width=$width, height=$height',
);
}
late web.ImageData imageData;
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think this can be:

Suggested change
late web.ImageData imageData;
final web.ImageData imageData;

Copy link
Copy Markdown
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Sure. Done👍

@TecHaxter
Copy link
Copy Markdown
Author

Demo

Dummy example app source code

2026-04-03.19-47-24.mp4

@mdebbar mdebbar added the CICD Run CI/CD label Apr 3, 2026
@mdebbar mdebbar requested review from ditman and removed request for ditman April 6, 2026 17:13
@mdebbar mdebbar added CICD Run CI/CD and removed CICD Run CI/CD labels Apr 6, 2026
@mdebbar
Copy link
Copy Markdown
Contributor

mdebbar commented Apr 7, 2026

Some lints have been reported here: https://logs.chromium.org/logs/flutter/buildbucket/cr-buildbucket/8685251527310718641/+/u/Run_package_tests/analyze/stdout

@mdebbar mdebbar dismissed ditman’s stale review April 7, 2026 17:29

Many changes have been done since this review.

@github-actions github-actions bot removed the CICD Run CI/CD label Apr 8, 2026
Comment on lines +51 to +53
({int? audioBitrate, int? videoBitrate})? recorderOptions,
}) : recorderOptions =
recorderOptions ?? (audioBitrate: null, videoBitrate: null),
Copy link
Copy Markdown
Author

@TecHaxter TecHaxter Apr 8, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why this change?

  • mockito walks the constructor and inspects parameter defaults.
  • For a const record literal, it goes through source_gen constant revival (reviveInstance).
  • That code path of the current version of the dependency does not handle record constants properly.
  • As a result, it hits a null and throws Null check operator used on a null value.

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

Labels

p: camera platform-web triage-web Should be looked at in web triage

Projects

None yet

Development

Successfully merging this pull request may close these issues.

6 participants