Форум программистов, компьютерный форум, киберфорум
Программирование Android
Войти
Регистрация
Восстановить пароль
Карта форума Темы раздела Блоги Сообщество Поиск Заказать работу  
 
Рейтинг 4.75/8: Рейтинг темы: голосов - 8, средняя оценка - 4.75
7 / 7 / 0
Регистрация: 14.03.2013
Сообщений: 231
1

Некорректно определяются размеры TextureView в экране предпросмотра камеры

20.07.2018, 11:30. Показов 1594. Ответов 14

Author24 — интернет-сервис помощи студентам
Всем привет.
Прошу подскажите как можно решить следующую проблему:

Имеется приложение камера, в которой при запуске некорректно определяются размеры TextureView (AutoFitTextureView ). Данный view элемент используется для отображения потока изображения на экране с камеры. Т.е. предпросмотр.
Соответственно в связи с некорректным определением размеров, неверно рассчитывается параметер AspectRatio и как следствие искажается экран предпросмотра.
! Но все исправляется если выполнить отключение-включение экрана.

скриншет №1 при первом включении. Видно как изображение растянуто по горизонтали.

скриншет №2 после отключения / включения экрана. Видно что было восстановлена пропорция отношения сторон.

Долго не мог разобраться, грешил на ошибку в коде, но пришел к следующиму выводу.
Причина в некорректных параметрах события onMeasure из класса TextureView (AutoFitTextureView).
Данное событие срабатывает для определения измененной ширины и высоты у элемента TextureView (AutoFitTextureView).

Само устройство у меня имеет размеры экрана 1920 x 1080. Но в связи с тем что на экране у меня еще присутствует view элемент для отображения кнопки затвора, кнопки "о приложении" (на скриншете видно). То размер TextureView (AutoFitTextureView) в высоту у меня выходит 1440 пикселей. Эту величину я узнал при отладке, смотрел какие параметры передаются в onMeasure() после отключения-включения экрана.

Соответственно в метод onMeasure() должно низначально передаватся параметры 1440 x 1080.
Но почему то этого не происходит и размеры TextureView (AutoFitTextureView) передаются как 1920 x 1080.

Если принудительно внутри метода onMeasure() жестко задать высоту как 1440 то при первом запуске все корректно.

Не знаю, может ошибка в layout XML файле? Т.к. элемент AutoFitTextureView у меня привязан только к верхней границе родителя. Нижняя граница определяется по размерам нижнего view элемента с кнопками управления.

класс TextureView (AutoFitTextureView):
Кликните здесь для просмотра всего текста
Java
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
import android.content.Context;
import android.util.AttributeSet;
import android.util.Log; // для записи в лог
import android.view.TextureView;
import java.util.Locale; // для String.format
 
// класс наследник от TextureView, просмотр потока с определенным соотношением сторон 
public class AutoFitTextureView extends TextureView {
 
    private int mRatioWidth = 0;
    private int mRatioHeight = 0;
 
    private static final String TAG = "CameraActivity"; // тег для лога Log
 
    public AutoFitTextureView(Context context) {
        this(context, null);
    }
 
    public AutoFitTextureView(Context context, AttributeSet attrs) {
        this(context, attrs, 0);
    }
 
    public AutoFitTextureView(Context context, AttributeSet attrs, int defStyle) {
        super(context, attrs, defStyle);
    }
 
     // устанавливает соотношение сторон для предпросмотра, размеры вычисляются на основании отношения сторон
     // указанные в параметрах величины не имеют значения, важно их пропорции т.е. (width, height) = (2, 3) = (4, 6).
    public void setAspectRatio(int width, int height) {
 
        Log.d(TAG, "метод setAspectRatio" + String.format(Locale.getDefault(), "(%d, %d)", width, height));
        if (width < 0 || height < 0) {
            throw new IllegalArgumentException("setAspectRatio(): размеры не могут быть отрицательными.");
        }
        mRatioWidth = width;
        mRatioHeight = height;
        requestLayout();
    }
 
    // метод событие для определения измененной ширины и высоты TextureView
    @Override
    protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
 
        super.onMeasure(widthMeasureSpec, heightMeasureSpec);
        int width = MeasureSpec.getSize(widthMeasureSpec);
        int height = MeasureSpec.getSize(heightMeasureSpec); // вместо 1440 выдает полную высоту экрана 1920
        //height = 1440; - если принудительно указывать размер то отношениие сторон при первом запуске корректное
 
        Log.d(TAG, "метод onMeasure" + String.format(Locale.getDefault(), "(%d, %d)", width, height));
 
        if (0 == mRatioWidth || 0 == mRatioHeight) {
            setMeasuredDimension(width, height);
        } else {
            if (width < height * mRatioWidth / mRatioHeight) {
                setMeasuredDimension(width, width * mRatioHeight / mRatioWidth);
            } else {
                setMeasuredDimension(height * mRatioWidth / mRatioHeight, height);
            }
        }
    }
}


activity_camera.xml:
Кликните здесь для просмотра всего текста
XML
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
<?xml version="1.0" encoding="utf-8"?>
 
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent">
 
    <com.example.android.camerafilter.AutoFitTextureView
        android:id="@+id/texture"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_alignParentTop="true" />
 
    <FrameLayout
        android:id="@+id/control"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:layout_below="@id/texture"
        android:layout_alignParentBottom="true"
        android:background="@color/control_background">
 
        <Button
            android:id="@+id/picture"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:layout_gravity="center"
            android:text="@string/picture" />
 
        <ImageButton
            android:id="@+id/info"
            style="@android:style/Widget.Material.Light.Button.Borderless"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:layout_gravity="center_vertical|right"
            android:contentDescription="@string/description_info"
            android:src="@drawable/ic_action_info" />
 
    </FrameLayout>
 
</RelativeLayout>


Такое некорректное определение размеров возвращается снова при повороте экрана. И опять же помогает исправить отключение-включение экрана.

Добавлено через 14 часов 33 минуты
Добавлю, что складывается такое ощущение что приложение при первом запуске как бы не успевает изменить размеры AutoFitTextureView на 1440 x 1080 в layout файле. Т.к. если посмотреть layout файл видно что у меня указана и высота и ширина как wrap_content. И в design режиме у меня элемент AutoFitTextureView занимает все окно экрана - т.е. 1920 x 1080.
0
Programming
Эксперт
94731 / 64177 / 26122
Регистрация: 12.04.2006
Сообщений: 116,782
20.07.2018, 11:30
Ответы с готовыми решениями:

Запись видео с камеры с выводом на textureview
Всем привет! Есть у кого исходники по теме? Поделитесь, пожалуйста. вариант с surfaceview не...

Некорректно определяются совпадения if
Доброго времени суток! Заноза в следующем: Есть массив float чисел объявленный следующим...

Реальные размеры svg на экране
Скажите пожалуйста, как получить реальные размеры svg на экране? Делаю так var el =...

Напишите приложение, которое в заголовке формы выводит ее размеры и координаты на экране
Напишите приложение, которое в заголовке формы выводит ее размеры и координаты на экране, а по...

14
129 / 126 / 22
Регистрация: 23.06.2009
Сообщений: 700
20.07.2018, 11:35 2
Java
1
2
3
4
5
<com.example.android.camerafilter.AutoFitTextureView
        android:id="@+id/texture"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_alignParentTop="true" />
попробуй тут добавить "android:above="@+id/control". Вроде как по разметке (и где-то в коде) используется просто весь дисплей экрана. А кнопка налаживается сверху камеры (FrameLayout with id control)
p.s. но это так.. пальцем в небо
0
7 / 7 / 0
Регистрация: 14.03.2013
Сообщений: 231
20.07.2018, 11:45  [ТС] 3
Добавлено через 8 минут
Спасибо за идею. Проверю как доберусь до студии.

Просто этот баг мне ясно видется так, что система как будто не успевает подкорректировать размеры AutoFitTextureView (согласно разметки XML) и сперва выдает 1920 x 1080. А потом при отключении-включении экрана скорректирует AutoFitTextureView на 1440 x 1080, освобождая место для FrameLayout который приклеен четко ниже AutoFitTextureView.

Добавлю что иногда, редко приложение запускалось с корректным отношение сторон, т.е. похоже AutoFitTextureView был размерами с 1440 x 1080. Т.е. ошибка плавающая. И непонятно отчего она зависела.
На другом устройстве не проверял. Только на одном.
0
129 / 126 / 22
Регистрация: 23.06.2009
Сообщений: 700
20.07.2018, 12:03 4


пробуй убрать эту строку. Добавь то что я писал выше в текстуру.

п.с. нашел я этот проект. Либо ты менял что-то в основном файле . Либо какой-то косячок где-то спрятал. Но у меня нормально отображается после смены двух строк.

Добавлено через 16 минут
Проверил размеры. Сделай как я сказал. Будет норм. в frame убери below , в texture добавь above
0
7 / 7 / 0
Регистрация: 14.03.2013
Сообщений: 231
20.07.2018, 14:56  [ТС] 5
Сделал как ты сказал.

Кликните здесь для просмотра всего текста
XML
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
<?xml version="1.0" encoding="utf-8"?>
 
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent">
 
    <com.example.android.camerafilter.AutoFitTextureView
        android:id="@+id/texture"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_alignParentTop="true"
        android:layout_above="@+id/control"/>
 
    <FrameLayout
        android:id="@+id/control"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:layout_alignParentBottom="true"
        android:background="@color/control_background">
 
        <Button
            android:id="@+id/picture"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:layout_gravity="center"
            android:text="@string/picture" />
 
        <ImageButton
            android:id="@+id/info"
            style="@android:style/Widget.Material.Light.Button.Borderless"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:layout_gravity="center_vertical|right"
            android:contentDescription="@string/description_info"
            android:src="@drawable/ic_action_info" />
 
    </FrameLayout>
 
</RelativeLayout>


Но нарушилось отношение сторон.

Некорректно определяются размеры TextureView в экране предпросмотра камеры


Сделал фотку под наклоном что бы было видно что отношение сторон нарушилось.
1
129 / 126 / 22
Регистрация: 23.06.2009
Сообщений: 700
20.07.2018, 15:02 6
Цитата Сообщение от oleggy Посмотреть сообщение
Сделал как ты сказал.
и ? помогло не?
0
7 / 7 / 0
Регистрация: 14.03.2013
Сообщений: 231
20.07.2018, 15:24  [ТС] 7
В посте выше написал.

Добавлено через 1 минуту
Вообщем сейчас для теста качаю проект с гитхаба и установлю на устройство что бы проверить.

Просто видишь что, этот проект у меня изначально шел с такой ошибкой.
Эта ошибка проявлялась если повернуть несколько раз экран из горизонтального в вертикальный.

Добавлено через 12 минут
Вообщем как и в прошлый раз. Cкачал проект, ни-че-го в нем не менял.
Запустил, и прямо сразу же - искажение.
Повернул в горизонтальную ориентацию - дичайшие искажения.

Причем опять же, ошибка проявляется случайно. Но нормальное отношение, то дичайшие искажения.
Но ведь стоковая программа корректно отрабатывает!

Для примера выдаю скрины:
https://preview.ibb.co/b8ULZJ/... _13_06.png
https://preview.ibb.co/iqym8d/... _13_21.png

Добавлено через 2 минуты
Это при то что в проекте существует совсем некорректная XML разметка для FrameLayout:

Кликните здесь для просмотра всего текста
XML
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent">
 
    <com.example.android.camera2basic.AutoFitTextureView
        android:id="@+id/texture"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:layout_alignParentStart="true"
        android:layout_alignParentTop="true" />
 
    <FrameLayout
        android:id="@+id/control"
        android:layout_width="match_parent"
        android:layout_height="112dp"
        android:layout_alignParentBottom="true"
        android:layout_alignParentStart="true"
        android:background="@color/control_background">
 
        <Button
            android:id="@+id/picture"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:layout_gravity="center"
            android:text="@string/picture" />
 
        <ImageButton
            android:id="@+id/info"
            android:contentDescription="@string/description_info"
            style="@android:style/Widget.Material.Light.Button.Borderless"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:layout_gravity="center_vertical|right"
            android:padding="20dp"
            android:src="@drawable/ic_action_info" />
 
    </FrameLayout>
 
</RelativeLayout>
0
129 / 126 / 22
Регистрация: 23.06.2009
Сообщений: 700
20.07.2018, 16:01 8
ну это понятно. Нада поковырятся. Там при повороте остаются теже размеры экраны и поэтому картинка ростянутая.

Добавлено через 26 минут
пробуй это фигню

Кликните здесь для просмотра всего текста
XML
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent">
 
    <com.example.android.camera2video.AutoFitTextureView
        android:id="@+id/texture"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:layout_above="@+id/container" />
 
    <FrameLayout
        android:id="@+id/container"
        android:layout_width="match_parent"
        android:layout_height="wrap_content"
        android:layout_alignParentBottom="true"
        android:background="#4285f4">
 
        <Button
            android:id="@+id/video"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:layout_gravity="center"
            android:text="@string/record" />
 
        <ImageButton
            android:id="@+id/info"
            style="@android:style/Widget.Material.Light.Button.Borderless"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:layout_gravity="center_vertical|right"
            android:contentDescription="@string/description_info"
            android:padding="20dp"
            android:src="@drawable/ic_action_info" />
 
    </FrameLayout>
 
</RelativeLayout>
0
7 / 7 / 0
Регистрация: 14.03.2013
Сообщений: 231
20.07.2018, 16:03  [ТС] 9
Ты мне скажи, у тебя на устройстве все отношения корректные?
0
129 / 126 / 22
Регистрация: 23.06.2009
Сообщений: 700
20.07.2018, 16:04 10
да, стакан не растягивается при повороте.
0
7 / 7 / 0
Регистрация: 14.03.2013
Сообщений: 231
20.07.2018, 16:10  [ТС] 11
Погоди, ты какой то другой проект скачал.
Вот этот посмотри:
https://github.com/googlesampl... mera2Basic
0
129 / 126 / 22
Регистрация: 23.06.2009
Сообщений: 700
20.07.2018, 16:12 12
смысл. тут теже грабли. Что у тебя не получается?

правь разметку :
Кликните здесь для просмотра всего текста

Java
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent">
 
    <com.example.android.camera2basic.AutoFitTextureView
        android:id="@+id/texture"
        android:layout_width="match_parent"
        android:layout_height="match_parent"
        android:layout_above="@+id/control" />
 
    <FrameLayout
        android:id="@+id/control"
        android:layout_width="match_parent"
        android:layout_height="112dp"
        android:layout_alignParentBottom="true"
        android:background="@color/control_background">
 
        <Button
            android:id="@+id/picture"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:layout_gravity="center"
            android:text="@string/picture" />
 
        <ImageButton
            android:id="@+id/info"
            style="@android:style/Widget.Material.Light.Button.Borderless"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:layout_gravity="center_vertical|right"
            android:contentDescription="@string/description_info"
            android:padding="20dp"
            android:src="@drawable/ic_action_info" />
 
    </FrameLayout>
 
</RelativeLayout>


что с видео что с фото у них одинаково идет. :\
0
7 / 7 / 0
Регистрация: 14.03.2013
Сообщений: 231
20.07.2018, 18:13  [ТС] 13
Так и не могу одолеть.

А может нужно переделать представление?
Может сделать отображение AutoFitTextureView на весь экран а кнопки установить поверх?
0
129 / 126 / 22
Регистрация: 23.06.2009
Сообщений: 700
23.07.2018, 12:02 14
Выложи свой проект архивом. Скачаю посмотрю с твоей стороны. Может действительно я не те качал.
0
7 / 7 / 0
Регистрация: 14.03.2013
Сообщений: 231
24.07.2018, 09:40  [ТС] 15
Посмотри личное сообщение.
0
24.07.2018, 09:40
IT_Exp
Эксперт
87844 / 49110 / 22898
Регистрация: 17.06.2006
Сообщений: 92,604
24.07.2018, 09:40
Помогаю со студенческими работами здесь

В заголовке формы нужно выводить положение формы на экране и ее размеры
Здравствуйте, Нужна помощь. Имеется задача: 1) в заголовке формы нужно выводить положение формы...


Искать еще темы с ответами

Или воспользуйтесь поиском по форуму:
15
Ответ Создать тему
КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin
Copyright ©2000 - 2024, CyberForum.ru