На главную
ПРАВИЛА FAQ Помощь Участники Календарь Избранное RSS
msm.ru
! Правила раздела "Программирование графики"
1) Данный раздел предназначен для обсуждения проблем, возникающих при программировании задач, связанных с чтением, сохранением, обработкой, созданием, отрисовкой графической информации (в том числе - 3D [OpenGL, Direct3D] и анимации [в т.ч. VFW, DirectShow, OpenDML]).
Флэш обсуждают здесь!.

2) Если вы хотите получить совет для конкретной платформы/языка программирования, обязательно укажите их в вопросе.

3) Уважаемые новички! Мы приветствуем Ваше желание научить всех посетителей раздела правильному программированию. Но огромная просьба, перед тем, как писать поучения в старых (последний ответ - "старее" месяца, а особенно, если вопрошавший не появляется на форуме уже не первый месяц, в чем можно убедиться в его профиле) темах, хорошо подумать, будет ли кому-нибудь, кроме Вас cамих, это интересно.



Ваше мнение о модераторах: user posted imageBarazuk, user posted imageOpenGL, user posted imageMikle
Модераторы: OpenGL, Mikle
  
> WebGL/OpenGL проекция и глубина, Вопрос по теории
    Здравствуйте.

    Сколько не смотрел материалы в интернете, все делают проекцию в clipspace матрицей, например такой.
    Но проблема в том, что при увеличении расстояния от камеры, глубина очень быстро приближается к значению 0,99... и весьма вероятны погрешности в тесте глубины. Но почему бы не использовать линейное преобразование координаты z?

    Пусть у нас есть система координат камеры, и камера находится в начале координат и смотрит вдоль оси z. Ближайшая плоскость отсечения на расстоянии n от камеры, дальняя на расстоянии f. Не будем использовать матрицу проекции, а передадим в вершинный шейдер 4 числа (uniform переменные): kx, ky, kz и dz.
    kx и ky - это коэффициенты для проекции x и y, взятые из матрицы по ссылке выше.
    kz - коэффициент для z, что бы сжать расстояние от n до f в отрезок длинной 2.
    dz - величина сдвига, что бы этот отрезок находится по z от -1 до 1.
    Так же вершинный шейдер будет получать координаты точки (attribute переменная) p = [x, y, z, 1].

    После этого в вершинном шейдере можно написать:
    gl_Position.x = kx * p.x;
    gl_Position.y = ky * p.y;
    gl_Position.z = (kz * p.z + dz) * p.z;
    gl_Position.w = p.z;

    Что бы получить координаты в clipspace, библиотека будет делить все компоненты gl_Position на gl_Position.w, после чего в gl_Position.z окажется линейно-преобразованная координата z в отрезке от -1 до 1, причем все точки будут равномерно распределены по отрезку, а не скапливаться в его конце. И точность теста глубины будет гораздо лучше.

    Почему же не используют такой алгоритм? Может я что-то не учел?
      Цитата lzv @
      в gl_Position.z окажется линейно-преобразованная координата z в отрезке от -1 до 1, причем все точки будут равномерно распределены по отрезку
      Пока в плавающих числах используется мантисса да порядок (а это сейчас идёт почти как ГОСТ) - равномерного распределения по отрезку не будет. :no-sad:
        Цитата Славян @
        Пока в плавающих числах используется мантисса да порядок (а это сейчас идёт почти как ГОСТ) - равномерного распределения по отрезку не будет. :no-sad:

        Не понял вашего ответа. Суть вопроса не в том, что распределение обязательно равномерное. А в том, что тест глубины будет проходить с гораздо большей точностью. Но непонятно, почему везде пишут про проекцию матрицей, у которой есть такая проблема с точностью.
          Цитата lzv @
          Суть вопроса не в том, что распределение обязательно равномерное.
          Да, я знал, просто маленькое замечание-поправку к вашему высказыванию добавил. :blush:
            Вон пишут, что в идеале должно быть именно неравномерное распределение, логарифмическое:
            http://outerra.blogspot.ru/2012/11/maximiz...-range-and.html

            Почему по умолчанию используется не самое лучшее в плане точности Z-буфера преобразование - в основном для упрощения расчётов с Z в экранных координатах:
            http://www.humus.name/index.php?ID=255
              Цитата Sapersky @
              Почему по умолчанию используется не самое лучшее в плане точности Z-буфера преобразование - в основном для упрощения расчётов с Z в экранных координатах:
              http://www.humus.name/index.php?ID=255

              Здесь похоже речь идет о другом. Во-первых, там про DX10, а здесь OpenGL. Во-вторых, там автор пишет, что z в пространстве экрана линейно. Но при проекции упомянутой выше матрицей z как раз нелинеен. Так что там видимо речь идет о другом методе проеции, тем более что в статье метод проекции не упоминается. Вопрос остается открытым.
              Хотя возможно больше информации найду в статье по первой ссылке, ее еще не читал.
                Видимо, Хумус имел в виду линейность 1/z.
                http://dev.theomader.com/linear-depth/
                DX или OGL - это не так важно, проекционная матрица может несколько отличаться из-за использования разных диапазонов Z, но принцип одинаковый.
                Здесь вообще описывается теория без привязки к API, но вывод в итоге делается тот же:
                http://www.scratchapixel.com/lessons/3d-ba...h-interpolation
                  Вообще-то имеет значение только монотонность Z от дальности. Матрица преобразования эту монотонность обеспечивает. Нарушение монотонности происходит не от матрицы, а от того, что Z имеет дискретное представление
                  Всё написанное выше это всего лишь моё мнение, возможно ошибочное.
                  1 пользователей читают эту тему (1 гостей и 0 скрытых пользователей)
                  0 пользователей:


                  Рейтинг@Mail.ru
                  [ Script Execution time: 0,0878 ]   [ 14 queries used ]   [ Generated: 15.12.19, 15:01 GMT ]