![]() |
| ||
|
|
Новости |
Поиск |
FAQ |
Статьи |
Книги |
Новости VCL
| | Форумы ЧАТ |
Орешник |
|
| |||
| |||
« предыдущая ветвь | форум | следующая ветвь »
блендинг текстур по маске
korvin88 © (2006-07-19 19:30:00)Всем привет!
Вопрос практический - как совместить две текстуры на одном полигоне, имея битовую маску их совмещения? Т.е. там, где маска белая, должна быть одна текстура, а там, где черная - другая. API - OpenGL.
DeadMeat (2006-07-23 13:05:00) [21]Собсна говоря это не просто Covarage factor.
Там ведь число в пределах 0..255. Это не так, что вот 0 это трава, а 255 это земля и ничего более. Между ними как раз и идет градация. 127 - это будет среднее между травой и землей. Да и там просто показан пример. Принцип можно из него понять и сделать как надо. Маска ведь черно белая, как ни крути. В начале (к примеру) кладется трава. И там, где на маске, скажем 255 - идет трава. Но если маску сгладить и сделать не сразу 255, а к примеру градиентом от 0 до 255, плавным, то и на полике будет плавный переход. Это и есть блендинг по вашей маске. И как раз используя расширения. А точнее комбайнер. Есть и ограничение, на 4 текстуры одновременно, но что мешает подставлять нужные текстуры в нужный момент?
Хотя конечно я могу и ошибаться, пускай спецы меня поправят. Я давно уже OGLом не занимался. Времени нет.
korvin88 (2006-07-23 04:27:00) [22]OSokin
Нет, мне нужен именно OpenGL. Если antonn что-нибудь знает, то пусть отпишется :).
DeadMeat
Может я, конечно, чего-то не понимаю, но там у них маскирование не используется. Маска - это не те данные, которые указывают, где на карте располагается трава, а где земля. Маска - это те данные, которые указывают на то, как в каждом конкретном тайле смешиваются эти текстуры.
Вот маска (приблизительно):
0000000000000000
0000000000000000
0000000000000000
0000000100000000
0011001101111000
1111111111111111
1111111111111111
1111111111111111
Единицы - белый цвет, нули - черный. Каждый тайл должен рисоваться с 3 параметрами - текстура для белого цвета, текстура для черного и маска. Если цвет маски серый (0.5), то должна получится смесь соответствующих текстур. В примере из статьи они для каждого вертекса указывают "coverage factor", т.е (насколько я понял), с какой прозрачностью нужно нарисовать там ту, или иную текстуру. Я пытаюсь реализовать совсем другой метод.
A22
Спасибо, попробую разобраться :).
A22 (2006-07-22 22:29:00) [23]sampler2D TexBase0 : register(s0);
sampler2D TexBase1 : register(s1);
sampler2D TexMask : register(s2);
void ps_main(in float2 iTex0 : TEXCOORD0, out float4 output : COLOR)
{
float4 c0 = tex2D(TexBase0, iTex0);
float4 c1 = tex2D(TexBase1, iTex0);
output = (c1 - c0)*tex2D(TexMask, iTex0).r + c0;
}
это на HLSL, я работал только с DirectX. но думаю, разницы особой нет. Шейдер берет 3 текстуры и смешивает две первые по маске (третья текстура). ничего особо умного, по сути то же, что предлагали считать на процессоре, но переписанное для видюхи.
2 tButton
насчет текстур и памяти - где они будут лежать от пула зависит :)
DeadMeat (2006-07-22 22:06:00) [24]Так я и не понял, почему способ из ссылки не подходит.
OSokin (2006-07-22 21:01:00) [25]Я знаю, как это делается с GDI! RTFM MaskBlt и юзай с обоими рисунками! Как еще - спрашивай у antonn'а :)
korvin88 (2006-07-22 13:35:00) [26]All
Up! Ну что? У кого-нить есть идеи? Может все-таки операцию, которую предложил tButton можно провернуть и без шейдеров, только с помощью расширений? У меня пока не получается :(. Ну хоть смысл простого блендинга понял - и то польза :).
В общем тут получается, что при обычном блендинге нельзя смешать одновременно 3 текстуры (ну, 2 типа земли и маску). Сначала нужно смешать 2 (одну землю и маску). Потом добавить еще одну (вторую землю). Так вот последняя добавленная влияет на уже готовую и правильно затекстуренную часть результирующего тайла :((. И никак от этого не избавишься :(. В голову лезет пока только использовать дополнительный буффер цвета и потом обьединять его с основным. Но нутром чую, что идея -бред :))).
korvin88 (2006-07-21 17:41:00) [27]tButton
Вот тут ты не прав. Что значит, "только те, которые используются"? Теоретически, использоваться могут все комбинации. А следовательно, их общее число будет около 400 (навскидку). Забиндинные текстуры, насколько я знаю, действительно хранятся в видеопамяти. Нагрузка на нее будет определятся размерами тайлов. Их можно сделать небольшим, так что первая проблема не так важна, разве что если только в видеокарте не стоит ограничение на кол-во используемых текстур :))). Гораздо больше меня смущает этап загрузки всего этого дела - 100-процентно получится медленно и печально :((.
В общем, резюмирую: такие варианты для тайлинга, как
1)заготовить хренову тучу текстур заранее.
2)сгенерить эту самую тучу на этапе инициализации.
и т.п., я буду использовать только тогда, когда израсходую все остальные методы. А следовательно, с нетерпением жду ответа от a22 по поводу того шейдера в 3 строки (уж больно заманчиво звучит :))).
tButton (2006-07-21 14:25:00) [28]
> сгенерировать все возможные комбинации совмещения этих текстур
> и забить все это в оперативу, чтобы потом рисовать по мере
> надобности???
не все, а только те которые используются
и получится у тебя 16*5 80 текстур
не так уж много для современного железа
> во многих играх тайлы были заранее нарисованы.
угум-с
> оперативка дешевле новой видеокарты
однако или я чего не понимаю или текстуры - таки лежат в видеопамяти
a22 (2006-07-21 12:10:00) [29]во многих играх тайлы были заранее нарисованы. оперативка дешевле новой видеокарты
korvin88 (2006-07-21 11:45:00) [30]tButton
Обьясняю подробно:
У меня есть ландшафт, нужно его затайлить. То место, где, например, трава граничит с камнем, нужно затекстурить по определенной маске - часть травой, а часть - камнем. Масок у меня много (16 штук). Текстур тоже (минимум - 5). Мне нужно, чтобы ландшафт рисовался, а следовательно, и текстуры блендились по маске в реальном времени (желательно с приемлимым FPS :))). Ты, насколько я понимаю, предлагаешь мне еще на этапе инициализации из базовых 16 черно-белых масок и 5 текстур сгенерировать всевозможные комбинации совмещения этих текстур и забить все это в оперативу, чтобы потом рисовать по мере надобности???
Я, конечно, не спец в этом деле, но, imho, очень сильно пострадает время загрузки, а также на все это потребуется много памяти.
tButton (2006-07-21 08:44:00) [31]
> Делать это в realtime?!?!
а сделать это один раз в начале никак?
korvin88 (2006-07-20 18:05:00) [32]a22
Я шейдеры раньше вообще не изучал. Но раз так, то видимо, придется. Если не трудно, то подкинь сам шейдер, чтобы я мог в нем разобраться, а также какую-нить простую доку для начинающих по использованию шейдеров в Delphi/OpenGL.
a22 (2006-07-20 17:34:00) [33]если собираешься менять маску - делай шейдером. шейдер в 3 строки, не такой уж тяжелый, а быстрее все равно никак не сделаешь
korvin88 (2006-07-20 15:24:00) [34]Trimp
Гы... це я (как ты, наверное, уже понял) :))). В общем, ты мне это уже советовал :))). Просто тогда на геймдеве я рано порадовался - в реализацию закрался глюк (см. пост выше) и я решил уточнить вопрос здесь.
Мне действительно интересно, можно ли отладить вариант с блендингом.
Trimp (2006-07-20 14:12:00) [35]
> Делать это в realtime?!?! Тогда уж лучше каждый раз приделывать
> к текстуре нужную альфу :)). Предложенный тобой способ,
> может, конечно, и правильный, теоретически... Но блин, меня
> ведь в первую очередь интересует практическая реализация
> такого эффекта. То, что их цвета нужно смешать по подобному
> закону, я уже давно понял. Но как именно это сделать???
Это можно сделать через расширение ARB_texture_env_combine.
Описание тут http://steps3d.narod.ru/tutorials/tutorial-4.html
korvin88 (2006-07-20 13:38:00) [36]tButton
Делать этов realtime?!?! Тогда уж лучше каждый раз приделывать к текстуре нужную альфу :)). Предложенный тобой способ, может, конечно, и правильный, теоретически... Но блин, меня ведь в первую очередь интересует практическая реализация такого эффекта. То, что их цвета нужно смешать по подобному закону, я уже давно понял. Но как именноэто сделать??? Только шейдеры, или можно обойтись расширениями? Какими? И как?
Именно для этого я и указываю, что юзаю OpenGL. Тут, по идее, нужен блендинг, но у меня не получается его правильно настроить. Я вывожу маску - отлично. Вывожу поверх нее полигон с текстурой травы и glBlendFunc(GL_DST_COLOR,GL_ZERO) - вроде пока нормально (там где маска белая - появляется трава). Но затем пытаюсь вывести еще один полигон, с текстурой камня и glBlendFunc(GL_SRC_COLOR,GL_ONE ) - и все, уже облом (трава и камень резко меняют цвет, накладываясь друг на друга). Если юзать не битовую маску, а с альфой, то можно добиться, что камень выводится еще нормально, но трава, что ни делай, смешана с текстурой камня :((. Уже задолбался с этим :(. Я явно что-то делаю не так и почти наверняка существуют правила, как делать подобные вещи верным образом. Я вот и хочу узнать у вас, как это делается, т.к. по логике вещей, я явно не первый, кто с этим сталкивается. Искренне надеюсь на вашу помощь.
tButton (2006-07-20 12:44:00) [37]а что не понятно?
проходишься по пикселям
result.R = sprite1.R * mask + sprite2.R * (mask - 1);
result.G = sprite1.G * mask + sprite2.G * (mask - 1);
result.B = sprite1.B * mask + sprite2.B * (mask - 1);
где
sprite#.R - красная составляющая цвета пикселя
sprite#.G - зелёная составляющая цвета пикселя
sprite#.B - синяя составляющая цвета пикселя
mask - значение маски для данного пикселя выраженое в значении 0..1
и так для каждого пикселя.
korvin88 (2006-07-20 10:03:00) [38]tButton
Второй вариант пока отпадает - работать, конечно, будет, только медленно. Мне же маски нужно будет часто менять.
Степень подробности первого варианта поражает :))). Самое интересное место - мешаешь обе текстуры по маске. Хотелось бы узнать, как именно это сделать? То, что потом результат нужно будет вывести на экран, можно было не говорить :).
tButton (2006-07-20 08:48:00) [39]1 вариант.
есть: текстура 1, текстура 2, маска для смешивания
мешаешь обе текстуры по маске результат кладёшь в третью текстуру
эту третью текстуру кладёшь на полигон
2 вариант
есть: текстура 1, текстура 2, маска для смешивания
кладёшь на полигон текстуру 1
делаешь маску альфа-каналом для второй текстуры (или её дубликата)
кладёшь вторую текстуру на полигон поверх первой
DeadMeat (2006-07-20 08:47:00) [40]
> Нет, не то. Там они не используют маску, а просто блендят
> текстуры. Мне же нужно именно по маске.
Вообщето они не просто блендят текстуры, а именно блендят их по маске. Я по этому примеру делал текстурирование своего терраина. Правда есть конечно и ограничение на количество. Зато шустро.
Если надо много, то gr32 и ей подобные в помощь. Но это уже не аппаратно.
Либо как в ссылке, но многопроходным рендерингом.
Больше не знаю...
Есть конечно еще и шейдеры. Там тоже просто реализуется, но насчет быстродействия, судя по моим экспериментам, при количестве текстур больше 4-5 на один полик, тормоза выше чем через комбайнер. Хотя шейдер простой как пятка.. Пришлось оптимизировать по дальности отрисовки.