2012-07-02 28 views
7

estoy luchando para obtener el siguiente algoritmo sencillo trabajar en el Samsung Galaxy SIIIruido algoritmo falla en el Samsung Galaxy SIII (GLES)

float rand(vec2 co) 
{ 
    return fract(sin(dot(co.xy ,vec2(12.9898,78.233))) * 43758.5453); 
} 

.... 
vec3 color = texture2D(u_texture, v_texcoord); 
gl_FragColor.rgb = color + vec3(rand(gl_FragCoord.xy + time/1000.0)); 
.... 

El código genera perfectamente el ruido esperado en Samsung Galaxy S1 y Google Nexus S . Pero falla completamente en el nuevo teléfono inteligente que usa Mali-400/MP4 de ARM.

¿Alguien puede detectar algo incorrecto con este algoritmo? O tal vez entender por qué podría fallar?

+2

¿Cómo funciona? ¿Está revisando los infólogos para detectar errores/advertencias? – Tim

+0

Sin errores, simplemente no muestra ningún pixel de ruido. La imagen general está bien, pero sin ningún ruido. – PerracoLabs

+2

Hmm, no estoy seguro entonces. Solo recomendaría pelarlo una capa por vez hasta que puedas entender por qué. P.ej. funciona fract()? funciona fract (sin()), funciona fract (sin (punto (())? etc. – Tim

Respuesta

9

Su problema probablemente proviene de tomar el sin de un número grande. El resultado de esto depende de la implementación exacta de sin, que no está disponible. Obviamente, la función sin utilizada por el chip Mali tiene resultados más predecibles con grandes números que los demás.

Me parece que deberías usar an actual noise function, no es esto. Al menos tendrá resultados predecibles en todo el hardware.

+1

He intentado esta opción porque pensé que sería la mejor y obtuve resultados muy extraños. líneas en todas partes en lugar de ruido. He utilizado el siguiente de la biblioteca: https://github.com/ashima/webgl-noise/blob/master/src/noise2D.glsl – PerracoLabs

3

Un poco de discusión sobre este tema en los foros de ARM: http://forums.arm.com/index.php?/topic/16364-random-number-with-mali-400-mp/.

El problema se debe a la precisión del FP16 en sombreadores de fragmentos en la GPU de Mali. Básicamente, no hay bits fraccionarios restantes para el momento en que se invoca fract (porque los multiplicadores son tan grandes), por lo que no se recupera ningún "ruido". Si reduce las constantes, comenzará a recuperar valores que no sean cero, pero no serán ruidosos. (No estoy del todo seguro de cómo se escogieron los valores, y es not clear where this algorithm came from).

Técnicamente, este algoritmo de ruido se basa en operaciones de punto flotante de precisión superior (medio? Alto?), Que son opcionales en los sombreadores de fragmentos. De acuerdo con this other post, puede verificar la precisión admitida de la plataforma en sombreadores de fragmentos al buscar la extensión "OES_fragment_precision_high" en glGetString(GL_EXTENSIONS).

El proyecto webgl-noise en la respuesta de Nicol no parece ser susceptible a problemas de truncamiento de punto flotante (parece mantener las cosas en un límite más estricto). Sin embargo, tiene un período de alrededor de 300, y genera más ruido "estructurado" que el ruido "blanco" (o "rosa") que recibe actualmente. Sin embargo, es una biblioteca excelente, por lo que vale la pena trabajar en su código, incluso si no es un reemplazo directo.

+0

Terminé usando la biblioteca webgl-noise , aunque aún estoy tratando de encontrar una alternativa, ya que el algoritmo es demasiado grande y, además, a veces (más de lo que quería) produce ruido que no se ve del todo como ruido, especialmente cuando se mezcla con colores oscuros. además del proyecto webgl-noise, no he encontrado ninguna alternativa. – PerracoLabs

Cuestiones relacionadas