Доступ к камере устройства Android через элемент HTML5 <video>через мобильное приложение CodeName One - PullRequest
0 голосов
/ 03 сентября 2018

Мы создаем мобильное приложение для Android с использованием CodeName One. Как часть нашего требования, у нас уже есть страница HTML5, которая содержит элемент видео, чтобы использовать камеру устройства для захвата фотографий. Нам нужно вызвать эту страницу HTML5 из ​​нашего приложения CodeName One. Но этот код не работает в соответствии с ожиданиями, однако URL-адрес HTML-файла работает отлично, когда вызывается напрямую из браузера Chrome. При просмотре в браузере Chrome появляется запрос на разрешение камеры, где, как и в приложении CodeName One, запрос разрешения не отображается.

Я видел похожий вопрос, опубликованный недавно Не работает управление видео html в приложении коденамона для Android

Я попробовал приведенные там рекомендации, но у меня это не сработало. Может, что-то не так, что я здесь делаю?

В моем CodeName один класс, у меня есть следующий код. Код в основном создает новый BrowserComponent и устанавливает URL-адрес camera1.html в этом компоненте. Camera1.html содержит код HTML5, который отображает элемент видео для фотосъемки. `

private Form current;
private Resources theme;

public void init(Object context) {
    theme = UIManager.initFirstTheme("/theme");

    // Enable Toolbar on all Forms by default
    Toolbar.setGlobalToolbar(true);    
}

public void start(){
    if(current != null) {
        current.show();
        return;
    }

    Form f = new Form("Camera", new BorderLayout());
    try {
        CN1NativeCameraInterface cnci = NativeLookup.create(CN1NativeCameraInterface.class);
        if (cnci != null && cnci.isSupported()) {

            boolean cameraPerm = cnci.promptCameraPermission();
            if (cameraPerm) {
               f.setTitle("Camera Permission true");
            }              
        }

        BrowserComponent browser = new BrowserComponent();

        browser.setURL("https://8c10ec77.ngrok.io/app/camera1.html");
        f.add(BorderLayout.CENTER, browser);
    }
    catch (Exception ex) {
        ex.printStackTrace();
    }
    finally {
        f.show();
    }
}

public void stop(){
    current = Display.getInstance().getCurrent();
}

public void destroy(){
}

` Я определил собственный интерфейс, который выглядит следующим образом

public interface CN1NativeCameraInterface extends NativeInterface {
    public boolean promptCameraPermission();
}

Сгенерировал собственный код доступа для этого интерфейса в CodeName One, а реализация для Android выглядит следующим образом

import com.codename1.impl.android.AndroidImplementation;
import android.Manifest;

public class CN1NativeCameraInterfaceImpl {
    public boolean promptCameraPermission() {
        return AndroidImplementation.checkForPermission(Manifest.permission.CAMERA, "This is required to take a picture");
    }

    public boolean isSupported() {
        return true;
    }

}

Когда я запускаю это на устройстве Android, я вижу, как загружается HTML-страница, но элемент video не загружается, все, что я вижу, является заполнителем для элемента video. Приложение также не запрашивает разрешение камеры, что было предложено в другом связанном вопросе.

Что я здесь не так делаю?

Обновление 1:

Я вижу следующие ошибки в журнале, полученном от устройства с помощью Команда adb "logcat --pid = $ (pidof -s com.codename1)":

Ошибка1 -

09-06 11: 48: 42.530 10172 10202 I WebViewFactory: загрузка com.android.chrome версии 69.0.3497.76 (код 349707652) 09-06 11: 48: 42.595 10172 10202 I zygote64: Отклонение повторного инициирования для ранее неудачного класса java.lang.Class: java.lang.NoClassDefFoundError: Неудачное разрешение: Landroid / webkit / TracingController; 09-06 11: 48: 42.595 10172 10202 Я zygote64: at java.lang.Class java.lang.Class.classForName (java.lang.String, boolean, java.lang.ClassLoader) (Class.java:-2) 09-06 11: 48: 42.595 10172 10202 I zygote64: at java.lang.Class java.lang.Class.forName (java.lang.String, boolean, java.lang.ClassLoader) (Class.java:453) 09-06 11: 48: 42.595 10172 10202 Я zygote64: at java.lang.Class android.webkit.WebViewFactory.getWebViewProviderClass (java.lang.ClassLoader) (WebViewFactory.java:151) 09-06 11: 48: 42.595 10172 10202 Я zygote64: at java.lang.Class android.webkit.WebViewFactory.getProviderClass () (WebViewFactory.java:472) 09-06 11: 48: 42.595 10172 10202 Я zygote64: at android.webkit.WebViewFactoryProvider android.webkit.WebViewFactory.getProvider () (WebViewFactory.java:212) 09-06 11: 48: 42.595 10172 10202 Я zygote64: at android.webkit.CookieManager android.webkit.CookieManager.getInstance () (CookieManager.java:39) 09-06 11: 48: 42.595 10172 10202 Я zygote64: at android.webkit.CookieManager com.codename1.impl.android.AndroidImplementation.getCookieManager () (AndroidImplementation.java:4511) 09-06 11: 48: 42.595 10172 10202 Я zygote64: at java.util.Vector com.codename1.impl.android.AndroidImplementation.getCookiesForURL (java.lang.String) (AndroidImplementation.java:4528) 09-06 11: 48: 42.595 10172 10202 I zygote64: at void com.codename1.io.ConnectionRequest.performOperation () (ConnectionRequest.java:633) 09-06 11: 48: 42.595 10172 10202 I zygote64: at void com.codename1.io.NetworkManager $ NetworkThread.run () (NetworkManager.java:282) 09-06 11: 48: 42.595 10172 10202 I zygote64: at void com.codename1.impl.CodenameOneThread $ 1.run () (CodenameOneThread.java:60) 09-06 11: 48: 42.595 10172 10202 I zygote64: at void java.lang.Thread.run () (Thread.java:764)09-06 11: 48: 42.595 10172 10202 I zygote64: Причина: java.lang.ClassNotFoundException: не найден класс «android.webkit.TracingController» по пути: DexPathList [[zip-файл »/ data / app / com. android.chrome-fq476TNc_btk-Vb0sBbuyw == / base.apk "], nativeLibraryDirectories = [/ data / app / com.android.chrome-fq476TNc_btk-Vb0sBbuyw == / lib / arm64, /data/appchrome.and -fq476TNc_btk-Vb0sBbuyw == / base.apk! / lib / arm64-v8a, / system / lib64, / system / vendor / lib64]] 09-06 11: 48: 42.595 10172 10202 Я zygote64: at java.lang.Class dalvik.system.BaseDexClassLoader.findClass (java.lang.String) (BaseDexClassLoader.java:93) 09-06 11: 48: 42.595 10172 10202 Я zygote64: at java.lang.Class java.lang.ClassLoader.loadClass (java.lang.String, boolean) (ClassLoader.java:379) 09-06 11: 48: 42.595 10172 10202 Я zygote64: at java.lang.Class java.lang.ClassLoader.loadClass (java.lang.String) (ClassLoader.java:312) 09-06 11: 48: 42.595 10172 10202 Я zygote64: at java.lang.Class java.lang.Class.classForName (java.lang.String, boolean, java.lang.ClassLoader) (Class.java:-2) 09-06 11: 48: 42.595 10172 10202 I zygote64: at java.lang.Class java.lang.Class.forName (java.lang.String, boolean, java.lang.ClassLoader) (Class.java:453) 09-06 11: 48: 42.595 10172 10202 Я zygote64: at java.lang.Class android.webkit.WebViewFactory.getWebViewProviderClass (java.lang.ClassLoader) (WebViewFactory.java:151) 09-06 11: 48: 42.595 10172 10202 Я zygote64: at java.lang.Class android.webkit.WebViewFactory.getProviderClass () (WebViewFactory.java:472) 09-06 11: 48: 42.595 10172 10202 Я zygote64: at android.webkit.WebViewFactoryProvider android.webkit.WebViewFactory.getProvider () (WebViewFactory.java:212) 09-06 11: 48: 42.595 10172 10202 Я zygote64: at android.webkit.CookieManager android.webkit.CookieManager.getInstance () (CookieManager.java:39) 09-06 11: 48: 42.595 10172 10202 Я zygote64: at android.webkit.CookieManager com.codename1.impl.android.AndroidImplementation.getCookieManager () (AndroidImplementation.java:4511) 09-06 11: 48: 42.595 10172 10202 Я zygote64: at java.util.Vector com.codename1.impl.android.AndroidImplementation.getCookiesForURL (java.lang.String) (AndroidImplementation.java:4528) 09-06 11: 48: 42.595 10172 10202 I zygote64: at void com.codename1.io.ConnectionRequest.performOperation () (ConnectionRequest.java:633)

Ошибка 2 -

09-06 11: 48: 44.506 10172 10266 Вт VideoCapabilities: Нераспознанный профиль 2130706433 для видео / avc 09-06 11: 48: 44.506 10172 10266 Вт VideoCapabilities: Нераспознанный профиль 2130706434 для видео / avc 09-06 11: 48: 44.536 10172 10266 Вт VideoCapabilities: Нераспознанный профиль 2130706433 для видео / avc 09-06 11: 48: 44.536 10172 10266 Вт VideoCapabilities: Нераспознанный профиль 2130706434 для видео / avc 09-06 11: 48: 44.542 10172 10266 Вт VideoCapabilities: Нераспознанный профиль 2130706433 для видео / avc 09-06 11: 48: 44.542 10172 10266 Вт VideoCapabilities: Нераспознанный профиль 2130706434 для видео / avc 09-06 11: 48: 44.551 10172 10266 Вт VideoCapabilities: Нераспознанный профиль / уровень 0/3 для видео / mpeg2 09-06 11: 48: 44.555 10172 10266 Вт VideoCapabilities: Нераспознанный профиль / уровень 0/3 для видео / mpeg2 09-06 11: 48: 44.564 10172 10266 Вт VideoCapabilities: Неподдерживаемое mime video / x-ms-wmv 09-06 11: 48: 44.568 10172 10266 Вт VideoCapabilities: Неподдерживаемое mime-видео / x-ms-wmv 09-06 11: 48: 44.574 10172 10266 Вт VideoCapabilities: Неподдерживаемое mime video / divx 09-06 11: 48: 44.577 10172 10177 I zygote64: Выполнить сбор кеша частичного кода, код = 55 КБ, данные = 56 КБ 09-06 11: 48: 44.580 10172 10266 Вт VideoCapabilities: Неподдерживаемое mime video / divx311 09-06 11: 48: 44.584 10172 10266 Вт VideoCapabilities: Неподдерживаемое mime video / divx4 09-06 11: 48: 44.585 10172 10177 I zygote64: После сбора кэша кода код = 55 КБ, данные = 56 КБ 09-06 11: 48: 44.585 10172 10177 I zygote64: Увеличение емкости кэша кода до 256 КБ 09-06 11: 48: 44.605 10172 10266 Вт VideoCapabilities: Неподдерживаемое mime video / mp4v-esdp 09-06 11: 48: 44.633 10172 10266 I VideoCapabilities: Неподдерживаемый профиль 4 для видео / mp4v-es09-06 11: 48: 44.867 10172 10282 W cr_CrashFileManager: /data/user/0/com.codename1/cache/WebView/Crash Отчеты не существуют или не являются каталогом

Ошибка 3 -

09-06 11: 48: 47.715 10172 10253 I CameraManagerGlobal: подключение к сервису камеры 09-06 11: 48: 47.799 10172 10172 D Кодовое имя один: onPermissionRequest 09-06 11: 48: 50.952 10172 10172 E AndroidВыполнение: ноль 09-06 11: 48: 50.952 10172 10172 E AndroidImplementation: java.io.FileNotFoundException: /data/user/0/com.codename1/files/CN1$AndroidServiceProperties (такого файла или каталога нет) 09-06 11: 48: 50.952 10172 10172 E AndroidImplementation: at java.io.FileInputStream.open0 (собственный метод) 09-06 11: 48: 50.952 10172 10172 E Реализация Android: в java.io.FileInputStream.open (FileInputStream.java:200) 09-06 11: 48: 50.952 10172 10172 E Реализация Android: в java.io.FileInputStream. (FileInputStream.java:150) 09-06 11: 48: 50.952 10172 10172 E AndroidImplementation: at android.app.ContextImpl.openFileInput (ContextImpl.java:515) 09-06 11: 48: 50.952 10172 10172 E AndroidImplementation: at android.content.ContextWrapper.openFileInput (ContextWrapper.java:190) 09-06 11: 48: 50.952 10172 10172 E Осуществление Android: на com.codename1.impl.android.AndroidImplementation.getServiceProperties (AndroidImplementation.java:6081) 09-06 11: 48: 50.952 10172 10172 E Реализация Android: по адресу com.codename1.impl.android.AndroidImplementation.writeServiceProperties (AndroidImplementation.java:6107) 09-06 11: 48: 50.952 10172 10172 E Реализация Android: по адресу com.codename1.CameraDemoStub.onStop (CameraDemoStub.java:166) 09-06 11: 48: 50.952 10172 10172 E AndroidImplementation: at android.app.Instrumentation.callActivityOnStop (Instrumentation.java:1486) 09-06 11: 48: 50.952 10172 10172 E AndroidImplementation: at android.app.Activity.performStop (Activity.java:7178) 09-06 11: 48: 50.952 10172 10172 E Реализация Android: на android.app.ActivityThread.performStopActivityInner (ActivityThread.java:4274) 09-06 11: 48: 50.952 10172 10172 E Осуществление Android: в android.app.ActivityThread.handleStopActivity (ActivityThread.java:4333) 09-06 11: 48: 50.952 10172 10172 E AndroidImplementation: at android.app.ActivityThread.-wrap24 (Неизвестно Источник: 0) 09-06 11: 48: 50.952 10172 10172 E Осуществление Android: на android.app.ActivityThread $ H.handleMessage (ActivityThread.java:1722) 09-06 11: 48: 50.952 10172 10172 E AndroidImplementation: at android.os.Handler.dispatchMessage (Handler.java:105) 09-06 11: 48: 50.952 10172 10172 E AndroidImplementation: at android.os.Looper.loop (Looper.java:164) 09-06 11: 48: 50.952 10172 10172 E AndroidImplementation: at android.app.ActivityThread.main (ActivityThread.java:6798) 09-06 11: 48: 50.952 10172 10172 E AndroidImplementation: at java.lang.reflect.Method.invoke (собственный метод) 09-06 11: 48: 50.952 10172 10172 E Реализация Android: на com.android.internal.os.Zygote $ MethodAndArgsCaller.run (Zygote.java:240) 09-06 11: 48: 50.952 10172 10172 E Реализация Android: на com.android.internal.os.ZygoteInit.main (ZygoteInit.java:767)

Ошибка 4 -

09-06 11: 48: 51.005 10172 10172 D CameraDemo: [main] 0: 0: 0,3 - [LOG] Произошла следующая ошибка: NotAllowedError: В доступе запрещено 55 https://8319bf05.ngrok.io/ventasys/venta/code/camera1.html

Эта ошибка выше (Ошибка 4) исходит из .html, который вызывается из CodeName One. Вот код для HTML:

<!DOCTYPE HTML>
<html>
  <head>
    <script>
        function copyPhoto() {
            var imgName;
            imgName = getParamValues("imgNm");        
            window.opener.document.getElementById(imgName).src = document.getElementById("theimage1").src;
            window.close();
        }

        function getParamValues(paramNm) {
            var qstring = window.location.href.slice(window.location.href.indexOf('?') + 1).split('&');
            for (var i = 0; i < qstring.length; i++) {
                var urlparam = qstring[i].split('='); 
                if (urlparam[0] == paramNm) {                        
                    return urlparam[1];
                }
            }
        }

        function snapshot() {

            var canvas = document.getElementById("thecanvas");

            var ctx = canvas.getContext("2d");

            //var constraints = { video: { facingMode: "user" }, audio: false };
            //var constraints = {
            //    video: {
            //        width: { min: 640, ideal: 1920 },
            //        height: { min: 400, ideal: 1080 },
            //        aspectRatio: { ideal: 1.7777777778 },
            //        facingMode: "environment"
            //    },
            //    audio: false
            //};

            var constraints = {
                video: { facingMode: "user" },
                audio: false
            };

            try {

                navigator.mediaDevices.getUserMedia(constraints).then(                        
                    // successCallback
                    function (localMediaStream) {
                        document.getElementById("mylog").innerHTML = document.getElementById("mylog").innerHTML + '1.3 ';
                        video = document.querySelector('video');
                        video.srcObject = localMediaStream;
                    })
                    .catch(function (err) {
                        console.log("The following error occured: " + err);
                        document.getElementById("mylog").innerHTML = document.getElementById("mylog").innerHTML + ' <br> 5 Err' + err;
                    });

            }
            catch (e)
            {
                document.getElementById("mylog").innerHTML = document.getElementById("mylog").innerHTML + ' 6 catch ##** ' + e;
            }
            document.getElementById("mylog").innerHTML = document.getElementById("mylog").innerHTML + '10 ';
            canvas.width = 640;
            canvas.height = video.videoHeight / (video.videoWidth / canvas.width);

            // Draws current image from the video element into the canvas               
            //ctx.drawImage(video, 0,0, video.videoWidth, video.videoHeight);
            ctx.drawImage(video, 0, 0, canvas.width, canvas.height);

            var canvas = document.getElementById("thecanvas");
            var dataUrl = canvas.toDataURL('image/jpeg', 0.6);
        }
    </script>
</head>
<body onload="snapshot();">
    <div id='mylog'></div>
    <p><video id="video" controls autoplay></video></p>
    <p><button onclick="snapshot();">Take Snapshot</button></p>
    <div id='item' hidden>
        <p><canvas id="thecanvas"></canvas></p>
    </div>        
    <p><image id="theimage1"></image></p>
    <p><button onclick="copyPhoto()">Done</button></p>
    <p><button onclick="copyPhoto()">Reload</button></p>
</body>
</html>

1 Ответ

0 голосов
/ 07 сентября 2018

Попробуйте добавить это к вашему init(Object) методу:

Display.getInstance().setProperty("android.WebView.grantPermissionsFrom", url_of_your_video_page);

Вы можете добавить несколько URL через пробел. Если это не сработает, нам может понадобиться что-то еще.

...