Софтверный рендеринг
Модератор: Модераторы разделов
-
- Сообщения: 3408
- Статус: аватар-невидимка
- ОС: openSUSE Tumbleweed x86_64
Re: Софтверный рендеринг
Так, прима версию сделал.
Что изменил:
1. Вычисление длины вектора (куда корень пропал?)
2. Сделал нормальное векторное (crossProduct) и скалярное (dotProduct) произведения.
3. Забыл упомянуть, алгоритм отсекает треугольники по часовой стрелке и рисует только против часовой (положительный поворот). Так что изменил треугольники, направление в отрицательном направлении оси Z сделал. Чтобы были оба направления (правда это не стоит делать), то надо отсекать не альфа<=0 и бета<=0, а альфа==0 и (бета/альфа)<=0.
4. Учёт в расчёте угла превышение 1 (из-за проблем с точностью и округлением) и крайние точки.
Вот изменённый renderer.cpp (7z с расширением rar):
Только Вы не учли последнюю мою мысль. Не надо так делать. Лучше делать преобразование мира, а затем просто работать с 2 координатами. Завтра, если будет время сделаю болванку.
Что изменил:
1. Вычисление длины вектора (куда корень пропал?)
2. Сделал нормальное векторное (crossProduct) и скалярное (dotProduct) произведения.
3. Забыл упомянуть, алгоритм отсекает треугольники по часовой стрелке и рисует только против часовой (положительный поворот). Так что изменил треугольники, направление в отрицательном направлении оси Z сделал. Чтобы были оба направления (правда это не стоит делать), то надо отсекать не альфа<=0 и бета<=0, а альфа==0 и (бета/альфа)<=0.
4. Учёт в расчёте угла превышение 1 (из-за проблем с точностью и округлением) и крайние точки.
Вот изменённый renderer.cpp (7z с расширением rar):
Только Вы не учли последнюю мою мысль. Не надо так делать. Лучше делать преобразование мира, а затем просто работать с 2 координатами. Завтра, если будет время сделаю болванку.
У вас нет необходимых прав для просмотра вложений в этом сообщении.
Спасибо сказали:
-
- Сообщения: 3408
- Статус: аватар-невидимка
- ОС: openSUSE Tumbleweed x86_64
Re: Софтверный рендеринг
Ох, Вы меня заразили
Сделал уже болванку. Выкладывать? А то я тут уже думаю освещение прикручивать 


-
- Сообщения: 1445
- ОС: Debian Squeeze
Re: Софтверный рендеринг
У меня проблема с перспективным преобразованием - не могу нормально разобраться что оно делает, как оно делает и зачем оно делает. Короче, начал разбираться и еще больше запутался. Книжку Энджела не прочитал пока от начала до конца.
Выкладывать.
Выкладывать.
-
- Сообщения: 3408
- Статус: аватар-невидимка
- ОС: openSUSE Tumbleweed x86_64
Re: Софтверный рендеринг
Кидаю как оно сейчас есть. Там есть лишние телодвижения. Освещение не прикручивал - времени не было. Нормали там, кстати, не надо менять, освещение до преобразования надо обработать и сохранить коэффициенты, которые учитывать и корректировать цвет.
(Архив 7z с расширением rar)
(Архив 7z с расширением rar)
У вас нет необходимых прав для просмотра вложений в этом сообщении.
-
- Сообщения: 1445
- ОС: Debian Squeeze
Re: Софтверный рендеринг
Насчет освещения - какое затенение проще и еффективнее сделать? Всмысле затенение Гуро или затенение Фонга? Какие между ними существенные различия(о том что при затенении Гуро не нужно вручную задавать нормали и так знаю)? И какой смысл из ручного задания нормалей при затенении Фонга?
Помойму сейчас лучше перейти на какой-нибудь более подходящий для real-time 2d-движок. Тем более что Qt весит очень много, а в большинстве его функций я не нуждаюсь. Существует ли среди 2d-движков еще что-то хорошее, быстрое и нежрущее видеокарту кроме SDL?
PS. Насчет перспективного преобразования - понял (кстати, оригинальное решение делать перспективное деление прямо в функции умножения матрицы на вектор).
-
- Сообщения: 3408
- Статус: аватар-невидимка
- ОС: openSUSE Tumbleweed x86_64
Re: Софтверный рендеринг
frp писал(а): ↑28.01.2010 17:50Насчет освещения - какое затенение проще и еффективнее сделать? Всмысле затенение Гуро или затенение Фонга? Какие между ними существенные различия(о том что при затенении Гуро не нужно вручную задавать нормали и так знаю)? И какой смысл из ручного задания нормалей при затенении Фонга?
Да вот, собственно: http://www.compgraphics.info/3D/lighting/shading_model.php
Наглядно и с картинками

А нормали для интерполирования нужны. Чтобы гладкие поверхности имитировать. В методе Фонга просто расчёт нормали вынесен за пределы алгоритма. Благодаря этому он не требует знания о всей поверхности, работает с отдельными треугольниками. А нормали считаются уровнем выше. Обычно автоматически, но иногда бывает надо что-то "замутить".
Тут не помогу, к сожалению Не в курсе

Спасибо сказали:
-
- Сообщения: 1445
- ОС: Debian Squeeze
Re: Софтверный рендеринг
Сегодня за полчаса "портировал" "движок" на SDL. Выложу когда код файла main.cpp приведу к человеческому виду.
В самом файле renderer.cpp поменял несколько строк в функции Renderer::render()
Заметил одну странную вещь - FPS не превышает 20. Так что в будущем точно придется сильно оптимизировать. И о затенении Фонга скорее всего придется забыть. Или для всех статических объектов использовать лайтмапы.
Спасибо.
В самом файле renderer.cpp поменял несколько строк в функции Renderer::render()
Заметил одну странную вещь - FPS не превышает 20. Так что в будущем точно придется сильно оптимизировать. И о затенении Фонга скорее всего придется забыть. Или для всех статических объектов использовать лайтмапы.
NickLion писал(а): ↑28.01.2010 21:10Да вот, собственно: http://www.compgraphics.info/3D/lighting/shading_model.php
Наглядно и с картинками
Спасибо.
-
- Сообщения: 1445
- ОС: Debian Squeeze
Re: Софтверный рендеринг
Придал коду более-менее человеческий вид. Немного оптимизировал (теперь fps 27-30). Выкладываю (архив не rar, а 7z).
Как правильно наложить текстуру на треугольник если для каждой вершины заданы текстурные координаты?
Как правильно наложить текстуру на треугольник если для каждой вершины заданы текстурные координаты?
У вас нет необходимых прав для просмотра вложений в этом сообщении.
-
- Сообщения: 3408
- Статус: аватар-невидимка
- ОС: openSUSE Tumbleweed x86_64
Re: Софтверный рендеринг
У меня 200-280 fps

В Renderer::renderPixel расчитываются e1, e2 - их можно понимать как координаты в треугольнике. Если, к примеру, заданы текстурные координаты: t->tx[i], t->ty[i] (i=0,1,2), тогда координата текущей точки по интерполяции:
tx=t->tx[0] * e0 + t->tx[1] * e1 + t->tx[2] * e2;
ty=t->ty[0] * e0 + t->ty[1] * e1 + t->ty[2] * e2;
А далее стоит задача расчёта цвета пикселя из текстуры. По расстоянию можно выбирать мипмап (если таковые будут). Расчет цвета - отдельная песТня. Для начала сделайте округление до ближайшего пикселя, а потом будет видно. Можно и билинейную интерполяцию прикрутить.
-
- Сообщения: 1445
- ОС: Debian Squeeze
Re: Софтверный рендеринг
Сделал текстурирование. Вроде работает (самая большая текстура, с которой тестировалось - 3х3
). Какие есть свободные удобные библиотеки для работы с изображениями? SDL_Image не интересует.

-
- Сообщения: 3408
- Статус: аватар-невидимка
- ОС: openSUSE Tumbleweed x86_64
Re: Софтверный рендеринг
libjpeg, libpng

А если серьёзно, то про удобство даже не в курсе. Qt в основном при работе с изображениями использовал - там не требуется чего-то дополнительного.
ИМХО, стоит сделать загрузку-обёртку через libjpeg и libpng в несжатый вид, и с ним работать - это по-любому. Скорость важнее расходов на память (тем более у Вас же не мегатекстуры будут

PS вру, под виндой libjpeg использовал давно. Там достаточно просто было. Не очень красиво, но работало.
-
- Сообщения: 1445
- ОС: Debian Squeeze
Re: Софтверный рендеринг
Короче посмотрел немного на libjpg, libpng. Сложно. Пошел в гугл. Нагуглил DevIL и FreeImage. DevIL отпал из-за мягко говоря странноватой архитектуры с закосом под OpenGL. Сделал загрузку через FreeImage.
Появился doom-эффект (если смотреть на объект с большого расстояния, то текстура выглядит очень нереалистично и при любом движении кажется что текстура дергается). Насколько я понимаю для решения этой проблемы нужно применить либо мип-мапы, либо анизотропную фильтрацию (судя по гуглу второй метод лучше, но вызывает огромное снижение производительности). Как правильно выбрать нужный мип-мап?
PS. Поменял конфигурацию сборки на release. FPS вырос до 55-60.
На каком железе вы это запускали? Я запускал на Celeron 1.8 Ghz с 1280 Мб RAM.
Появился doom-эффект (если смотреть на объект с большого расстояния, то текстура выглядит очень нереалистично и при любом движении кажется что текстура дергается). Насколько я понимаю для решения этой проблемы нужно применить либо мип-мапы, либо анизотропную фильтрацию (судя по гуглу второй метод лучше, но вызывает огромное снижение производительности). Как правильно выбрать нужный мип-мап?
PS. Поменял конфигурацию сборки на release. FPS вырос до 55-60.
На каком железе вы это запускали? Я запускал на Celeron 1.8 Ghz с 1280 Мб RAM.
У вас нет необходимых прав для просмотра вложений в этом сообщении.
-
- Сообщения: 3408
- Статус: аватар-невидимка
- ОС: openSUSE Tumbleweed x86_64
Re: Софтверный рендеринг
frp писал(а): ↑05.02.2010 22:20Появился doom-эффект (если смотреть на объект с большого расстояния, то текстура выглядит очень нереалистично и при любом движении кажется что текстура дергается). Насколько я понимаю для решения этой проблемы нужно применить либо мип-мапы, либо анизотропную фильтрацию (судя по гуглу второй метод лучше, но вызывает огромное снижение производительности). Как правильно выбрать нужный мип-мап?
Нужно выбрать уровень мипмапа с наиболее близким размером текселя к пикселю. Для улучшения ещё можно брать наиболее близкие снизу и сверху и считать среднее. Для дальних объектов (размер текселя меньше пикселя) можно считать интегральное значение. Это немного увеличивает время, но даёт нормальное качество без необходимости мипмапов.
Core2Quad 6600 2,4 GHz, 6 GB RAM.
PS с текстурой 250-300 FPS

-
- Сообщения: 1445
- ОС: Debian Squeeze
Re: Софтверный рендеринг
Нашел на википедии формулу miplevel=log2(dist/(texelsize*resolution))+mipbias. Возник вопрос - а что есть texelsize? На википедии написано, что texelsize - размер текселя в единицах 3d-мира. А если тексели не квадратные и даже не прямоугольные?
PS. Пока реализовал билинейную фильтрацию - теперь дум-эффект заметен только на больших расстояниях. Выкладываю.
PPS. Заметил еще одну странную вещь - полигоны, которые находятся сзади камеры, тоже рендерятся. Как определить, спереди или сзади камеры находиться полигон.
PS. Пока реализовал билинейную фильтрацию - теперь дум-эффект заметен только на больших расстояниях. Выкладываю.
PPS. Заметил еще одну странную вещь - полигоны, которые находятся сзади камеры, тоже рендерятся. Как определить, спереди или сзади камеры находиться полигон.
У вас нет необходимых прав для просмотра вложений в этом сообщении.
-
- Сообщения: 3408
- Статус: аватар-невидимка
- ОС: openSUSE Tumbleweed x86_64
Re: Софтверный рендеринг
Эм... Как бы это определить... Если по физике, то мгновенный размер текселя в данной точке

А если серьёзно, то конечно есть заморочки, но обычно текстура сильно не искажается - а если искажается - проблема того, кто так пишет

Код: Выделить всё
double lng = e0 * t->p[0].z + e1 * t->p[1].z + e2 * t->p[2].z;
Вот расстояние же

-
- Сообщения: 1445
- ОС: Debian Squeeze
Re: Софтверный рендеринг
Что это такое и как это вычислить?
Сделал проверку. Рисую только если lng>=0. Рисуется спереди камеры (z>=0) и сзади камеры, но сзади рисуется только z<=-19.
-
- Сообщения: 3408
- Статус: аватар-невидимка
- ОС: openSUSE Tumbleweed x86_64
Re: Софтверный рендеринг
Что это такое - не заморачивайтесь, оно всё-равно не надо, это физика на башку давит

Как вычислить - зависит в общем от текстурных координат и координат треугольника - расстояние в координатах делим на расстояние в текселях - получаем размер текселя в координатах

В общем случае тут ещё текстурная матрица необходима, если она у Вас появится.
Странно... Посмотрю...
-
- Сообщения: 1445
- ОС: Debian Squeeze
Re: Софтверный рендеринг
lng там точно вычисляется неправильно если объект находится сзади камеры (z<0). Если спереди, то вроде правильно. В чем суть алгоритма? И почему он работает неправильно если объект находится сзади камеры?
-
- Сообщения: 3408
- Статус: аватар-невидимка
- ОС: openSUSE Tumbleweed x86_64
Re: Софтверный рендеринг
Ой, всё никак не посмотрю.
В общем, по хорошему, должно получиться так, что объекты в ближней отсекающей плоскости получат Z равный "+1", а в дальней отсекающей - "-1". Всё, что ближе (читай больше) "+1" нужно отсекать, а всё что дальше (меньше) "-1" - по хорошему тоже, хотя это уже спорный вопрос.
В общем, по хорошему, должно получиться так, что объекты в ближней отсекающей плоскости получат Z равный "+1", а в дальней отсекающей - "-1". Всё, что ближе (читай больше) "+1" нужно отсекать, а всё что дальше (меньше) "-1" - по хорошему тоже, хотя это уже спорный вопрос.
-
- Сообщения: 1445
- ОС: Debian Squeeze
Re: Софтверный рендеринг
NickLion писал(а): ↑17.02.2010 21:58В общем, по хорошему, должно получиться так, что объекты в ближней отсекающей плоскости получат Z равный "+1", а в дальней отсекающей - "-1". Всё, что ближе (читай больше) "+1" нужно отсекать, а всё что дальше (меньше) "-1" - по хорошему тоже, хотя это уже спорный вопрос.
Разобрался. Алгоритм таки правильный, просто я не умел его использоват

И еще - как посчитать количество пикселей, которое будет в объекте размером в 1 ед., расположенном в 1 ед. от камеры?
-
- Сообщения: 3408
- Статус: аватар-невидимка
- ОС: openSUSE Tumbleweed x86_64
Re: Софтверный рендеринг
А это точно нужно? Зачем?
Можно двумя способами получить координаты точки в исходном мире:
1) координаты точки через обратную матрицу
2) координаты исходного треугольника и используя e0/1/2 посчитать повторно
а затем просто расстояние между точками считать.
Очень просто, эта величина зависит только от угла обзора камеры: viewport_width*znear/(right-left)
-
- Сообщения: 1445
- ОС: Debian Squeeze
Re: Софтверный рендеринг
(ru.wikipedia.org) писал(а):..., texelsize — размер текселя в единицах трёхмерного мира, dist — расстояние до объекта в тех же единицах, ...
dist ведь нужно как-то вычислить.
-
- Сообщения: 3408
- Статус: аватар-невидимка
- ОС: openSUSE Tumbleweed x86_64
Re: Софтверный рендеринг
Можно рассуждать в терминах нового мира. С новыми координатами. у Вас расстояние идет дважды - в dist и texelsize. Т.е. единица мира уходит остается только отношение - поэтому не важно, вроде.
-
- Сообщения: 1445
- ОС: Debian Squeeze
Re: Софтверный рендеринг
Можно рассуждать в терминах нового мира. С новыми координатами. у Вас расстояние идет дважды - в dist и texelsize. Т.е. единица мира уходит остается только отношение - поэтому не важно, вроде.
Т.е. Не нужно dist и texelsize переводить в единицы трехмерного мира.
Нужно только чтобы они были в одних и тех же единицах.
Но как сие реализовать (к каким общим единицам привести dist и texelsize)?
-
- Сообщения: 3408
- Статус: аватар-невидимка
- ОС: openSUSE Tumbleweed x86_64
Re: Софтверный рендеринг
Посмотрел подробнее. В общем, смотрите, после перспективного преобразования мы разделили на расстояние до объекта, т.о. из нашей формулы расстояние просто уходит. Формула преобразуется в:
mip_level=log2(1/(texel_size*resolution))+mip_bias
resolution=viewport_width/2 (потому что от -1 до +1 - 2 единицы нового мира)
texel_size=расстояние_в_координатах_нового_мира/(расстояние_в_текстурных_координатах*количество_текселей_в_0_уровне)
в этой величине наибольшая сложность. Нужно считать по горизонтали (потому что разрешение по горизонтали брали, ну и плюс анизотропность возможная....)
UPD (1.03.2010)
в величине "расстояние_в_координатах_нового_мира" нужно читывать только x, y, но не z. т.е. составляющую перпендикулярную лучу зрения....
mip_level=log2(1/(texel_size*resolution))+mip_bias
resolution=viewport_width/2 (потому что от -1 до +1 - 2 единицы нового мира)
texel_size=расстояние_в_координатах_нового_мира/(расстояние_в_текстурных_координатах*количество_текселей_в_0_уровне)
в этой величине наибольшая сложность. Нужно считать по горизонтали (потому что разрешение по горизонтали брали, ну и плюс анизотропность возможная....)
UPD (1.03.2010)
в величине "расстояние_в_координатах_нового_мира" нужно читывать только x, y, но не z. т.е. составляющую перпендикулярную лучу зрения....