Доступ к внешней USB-камере из веб-просмотра в Android
У меня есть веб-просмотр в моем приложении для Android. Из веб-просмотра я могу получить доступ к камере по умолчанию на телефоне. Следующий код работает нормально.
webview.setWebChromeClient(new WebChromeClient(){
// Need to accept permissions to use the camera
@Override
public void onPermissionRequest(final PermissionRequest request) {
L.d("onPermissionRequest");
request.grant(request.getResources());
}
});
Моя проблема заключается в том, чтобы получить доступ к внешней камере USB из этого веб-просмотра. Выше разрешения открывает камеру по умолчанию в веб-представлении.
Я не смог найти никакой документации, которая даже говорит, что это возможно. Это из-за проблем с безопасностью?
1 ответ
У вас могут быть проблемы с драйвером USB-камеры и выбором камеры, а не с разрешениями.
- USB-драйверы для камер
Первый шаг - убедиться, что ваша USB-камера обнаружена и работает на вашем устройстве. Вы не указали, подтвердили ли вы это или нет. Насколько я понимаю, поддержка android.hardware.camera2 для USB-камер все еще довольно слабая. Если ваша камера поддерживается, то, надеюсь, она будет перечислять вместе с остальными камерами. В моем тесте с Android 8.1.0 USB-камера, которую я подключил, не была перечислена с CameraManager, в то время как это было с библиотекой ниже.
Библиотека USB-камеры https://github.com/saki4510t/UVCCamera часто используется для обеспечения более широкой поддержки USB-камер, но из моего ограниченного опыта работы с библиотекой она пишет в TextureView и поэтому, вероятно, не будет хорошо работать с WebRTC в WebView. В очень беглом исследовании я не видел хуков WebView, которые бы поддерживали подключение внешнего источника видео.
- Выбор камеры
Вы упомянули, что в вашем тесте всегда использовалась камера по умолчанию, поэтому похоже, что вы не будете активно перечислять и выбирать целевую камеру. Выбор камеры WebRTC может быть выполнен в Javascript, используя navigator.mediaDevices
интерфейс. Например,
function chooseDevice(videoInDevices) {
// return selected device
}
// Filter devices so we only consider video sources
function filterForVideoInputs(devices) {
return devices.filter(d => d.kind === 'videoinput');
}
// Simply pull out deviceId from selected device struct
function getDeviceId(deviceInfo) {
return deviceInfo.deviceId;
}
// Request video stream from selected deviceId
function requestDevice(deviceId) {
return navigator.mediaDevices.getUserMedia({
video: {
deviceId: {
exact: deviceId
}
}
});
}
// Connect stream from getUserMedia to HTML5 video element
function startStream(stream) {
let video = document.querySelector('video');
video.srcObject = stream;
video.onloadedmetadata = function () {
video.play();
}
}
navigator.mediaDevices.enumerateDevices()
.then(filterForVideoInputs)
.then(chooseDevice)
.then(getDeviceId)
.then(requestDevice)
.then(startStream)
.catch(err => console.log(err));
Поскольку ваши разрешения были достаточны для внутренней камеры, они, насколько я понимаю, должны быть достаточными и для камеры USB.
Обратите внимание, что, как вы, возможно, знаете, в документации есть предупреждение о не ослеплении при предоставлении разрешения Webkit. Когда вы движетесь к производству, не забудьте заменить
request.grant(request.getResources())
возможно, с чем-то вроде этого
if (isRequestOriginOrWhateverApproved(request)) {
request.grant(new String[]{PermissionRequest.RESOURCE_VIDEO_CAPTURE});
}