Войти
ПрограммированиеФорумГрафика

Fresnel и металл как соединить ?

#0
(Правка: 16:33) 16:16, 30 июня 2020

Fresnel имеет спад отражающегося мира в центре сферы на обычном пластике или не металле.
Изображение
Но на металле окружающий мир отражается четко и равномерно.
Как на этой картинке.
Изображение

И вот вопрос как Fresnel сложить с металлом в PBR шейдере ?


#1
18:15, 30 июня 2020

кукиторинз?

#2
18:53, 30 июня 2020

ronniko
нужно для металла задать соответствующий ior (20-100)

#3
(Правка: 19:51) 19:49, 30 июня 2020

Вопрос задан слишком обобщенно.
А. Тебе нужно в готовом шейдере это сделать? Если да, то какой движок?
Б. Тебе нужен пример псевдокода? Если да, давай пример кода своего шейдера, что бы можно было прикинуть что к нему можно добавить, для получения нужного результата.

#4
20:47, 30 июня 2020
trash metal, death metal, frensel metal
#5
(Правка: 22:12) 22:08, 30 июня 2020

Сложить с металлом?

  vec3 F0 = mix(vec3(0.04), diffuse_coeff.rgb, metalness);
  diffuse.rgb = mix(diffuse_coeff.rgb, vec3(0.0), metalness);
  vec3 fresnel = F0 + (vec3(1.0) - F0) * pow(1.0 - clamp(dot(V, N), 0.0, 1.0), 5.0);
  specular.rgb = fresnel;
  diffuse.rgb *= vec3(1.0)-fresnel;

#6
6:00, 1 июля 2020

ronniko
> Fresnel имеет спад отражающегося мира в центре сферы на обычном пластике или не
> металле.
Он же вроде не до нуля падает, а зависит от микрорельефа. Разве нет?

#7
6:34, 1 июля 2020

MrOcelot

vec3 F0 = mix(vec3(0.04), diffuse_coeff.rgb, metalness);

Вот это похоже на то что мне надо.
Это походу IOR.

#8
6:58, 1 июля 2020

  vec3 F0 = mix(vec3(0.04), diffuse.xyz, METALLIC);
  vec3 F = F0 + (max(vec3(1.0 - ROUGHNESS), F0) - F0) * pow(1.0 - dot(n, v), 5.0);

  diffuse.xyz  *= textureLod(sEnvmap, n, MAX_LOD).xyz;
  vec3 specular = textureLod(sEnvmap, r, ROUGHNESS * MAX_LOD).xyz;
  vec2 lut      = texture2D(sLUT, vec2(max(0.0, dot(n, v)), ROUGHNESS)).xy;

  specular = specular * (F * lut.x + lut.y);
  vec3 kd = (vec3(1.0) - F) * (1.0 - METALLIC);
  vec3 color = kd * diffuse.xyz + specular;
  gl_fragColor = vec4(color, diffuse.w);

что-то такое

#9
(Правка: 12:16) 12:13, 1 июля 2020

ronniko
0.04 это константный F0 для диэлектриков
Из IOR считается как-то так:

vec3 F0 = abs((1 - IOR)/(1 + IOR));
F0 *= F0;

С учетом этого код станет таким:

vec3 F0 = vec3(abs((1.0 - IOR)/(1.0 + IOR)));
F0 *= F0;
F0 = mix(F0, diffuse_coeff.rgb, metalness);
diffuse.rgb = mix(diffuse_coeff.rgb, vec3(0.0), metalness);
vec3 fresnel = F0 + (vec3(1.0) - F0) * pow(1.0 - clamp(dot(V, N), 0.0, 1.0), 5.0);
specular.rgb = fresnel;
diffuse.rgb *= vec3(1.0)-fresnel;

Список IOR для различных материалов можно найти здесь:
https://pixelandpoly.com/ior.html

#10
(Правка: 13:01) 13:01, 1 июля 2020

lookid и MrOcelot спасибо за интересную информацию и за помощь.

Misanthrope спасибо за музыку frensel metal :)

ПрограммированиеФорумГрафика