mirror of
				https://github.com/gnif/LookingGlass.git
				synced 2025-11-04 06:31:54 +00:00 
			
		
		
		
	[client] egl: added colorblind support (egl:cbMode=0/1/2/3)
Based on http://www.daltonize.org/search/label/Daltonize 0 = Off 1 = Protanope 2 = Deuteranope 3 = Tritanope
This commit is contained in:
		@@ -20,6 +20,7 @@ Place, Suite 330, Boston, MA 02111-1307 USA
 | 
				
			|||||||
#include "cursor.h"
 | 
					#include "cursor.h"
 | 
				
			||||||
#include "common/debug.h"
 | 
					#include "common/debug.h"
 | 
				
			||||||
#include "common/locking.h"
 | 
					#include "common/locking.h"
 | 
				
			||||||
 | 
					#include "common/option.h"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
#include "texture.h"
 | 
					#include "texture.h"
 | 
				
			||||||
#include "shader.h"
 | 
					#include "shader.h"
 | 
				
			||||||
@@ -47,6 +48,7 @@ struct EGL_Cursor
 | 
				
			|||||||
  // cursor state
 | 
					  // cursor state
 | 
				
			||||||
  bool              visible;
 | 
					  bool              visible;
 | 
				
			||||||
  float             x, y, w, h;
 | 
					  float             x, y, w, h;
 | 
				
			||||||
 | 
					  int               cbMode;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  // textures
 | 
					  // textures
 | 
				
			||||||
  struct EGL_Texture * texture;
 | 
					  struct EGL_Texture * texture;
 | 
				
			||||||
@@ -59,6 +61,7 @@ struct EGL_Cursor
 | 
				
			|||||||
  // uniforms
 | 
					  // uniforms
 | 
				
			||||||
  GLuint uMousePos;
 | 
					  GLuint uMousePos;
 | 
				
			||||||
  GLuint uMousePosMono;
 | 
					  GLuint uMousePosMono;
 | 
				
			||||||
 | 
					  GLuint uCBMode;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  // model
 | 
					  // model
 | 
				
			||||||
  struct EGL_Model   * model;
 | 
					  struct EGL_Model   * model;
 | 
				
			||||||
@@ -119,6 +122,8 @@ bool egl_cursor_init(EGL_Cursor ** cursor)
 | 
				
			|||||||
  }
 | 
					  }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  (*cursor)->uMousePos     = egl_shader_get_uniform_location((*cursor)->shader    , "mouse" );
 | 
					  (*cursor)->uMousePos     = egl_shader_get_uniform_location((*cursor)->shader    , "mouse" );
 | 
				
			||||||
 | 
					  (*cursor)->uCBMode       = egl_shader_get_uniform_location((*cursor)->shader    , "cbMode");
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  (*cursor)->uMousePosMono = egl_shader_get_uniform_location((*cursor)->shaderMono, "mouse" );
 | 
					  (*cursor)->uMousePosMono = egl_shader_get_uniform_location((*cursor)->shaderMono, "mouse" );
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  if (!egl_model_init(&(*cursor)->model))
 | 
					  if (!egl_model_init(&(*cursor)->model))
 | 
				
			||||||
@@ -128,6 +133,9 @@ bool egl_cursor_init(EGL_Cursor ** cursor)
 | 
				
			|||||||
  }
 | 
					  }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  egl_model_set_default((*cursor)->model);
 | 
					  egl_model_set_default((*cursor)->model);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					  (*cursor)->cbMode = option_get_int("egl", "cbMode");
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  return true;
 | 
					  return true;
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
@@ -255,6 +263,7 @@ void egl_cursor_render(EGL_Cursor * cursor)
 | 
				
			|||||||
    {
 | 
					    {
 | 
				
			||||||
      egl_shader_use(cursor->shader);
 | 
					      egl_shader_use(cursor->shader);
 | 
				
			||||||
      glUniform4f(cursor->uMousePos, cursor->x, cursor->y, cursor->w, cursor->h / 2);
 | 
					      glUniform4f(cursor->uMousePos, cursor->x, cursor->y, cursor->w, cursor->h / 2);
 | 
				
			||||||
 | 
					      glUniform1i(cursor->uCBMode  , cursor->cbMode);
 | 
				
			||||||
      glBlendFunc(GL_ZERO, GL_SRC_COLOR);
 | 
					      glBlendFunc(GL_ZERO, GL_SRC_COLOR);
 | 
				
			||||||
      egl_model_set_texture(cursor->model, cursor->texture);
 | 
					      egl_model_set_texture(cursor->model, cursor->texture);
 | 
				
			||||||
      egl_model_render(cursor->model);
 | 
					      egl_model_render(cursor->model);
 | 
				
			||||||
@@ -271,6 +280,7 @@ void egl_cursor_render(EGL_Cursor * cursor)
 | 
				
			|||||||
    {
 | 
					    {
 | 
				
			||||||
      egl_shader_use(cursor->shader);
 | 
					      egl_shader_use(cursor->shader);
 | 
				
			||||||
      glUniform4f(cursor->uMousePos, cursor->x, cursor->y, cursor->w, cursor->h);
 | 
					      glUniform4f(cursor->uMousePos, cursor->x, cursor->y, cursor->w, cursor->h);
 | 
				
			||||||
 | 
					      glUniform1i(cursor->uCBMode  , cursor->cbMode);
 | 
				
			||||||
      glBlendFunc(GL_ONE, GL_ONE_MINUS_SRC_ALPHA);
 | 
					      glBlendFunc(GL_ONE, GL_ONE_MINUS_SRC_ALPHA);
 | 
				
			||||||
      egl_model_render(cursor->model);
 | 
					      egl_model_render(cursor->model);
 | 
				
			||||||
      break;
 | 
					      break;
 | 
				
			||||||
 
 | 
				
			|||||||
@@ -43,6 +43,7 @@ struct DesktopShader
 | 
				
			|||||||
  GLint uDesktopSize;
 | 
					  GLint uDesktopSize;
 | 
				
			||||||
  GLint uNearest;
 | 
					  GLint uNearest;
 | 
				
			||||||
  GLint uNV, uNVGain;
 | 
					  GLint uNV, uNVGain;
 | 
				
			||||||
 | 
					  GLint uCBMode;
 | 
				
			||||||
};
 | 
					};
 | 
				
			||||||
 | 
					
 | 
				
			||||||
struct EGL_Desktop
 | 
					struct EGL_Desktop
 | 
				
			||||||
@@ -64,6 +65,9 @@ struct EGL_Desktop
 | 
				
			|||||||
  KeybindHandle kbNV;
 | 
					  KeybindHandle kbNV;
 | 
				
			||||||
  int   nvMax;
 | 
					  int   nvMax;
 | 
				
			||||||
  int   nvGain;
 | 
					  int   nvGain;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					  // colorblind mode
 | 
				
			||||||
 | 
					  int   cbMode;
 | 
				
			||||||
};
 | 
					};
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// forwards
 | 
					// forwards
 | 
				
			||||||
@@ -90,6 +94,7 @@ static bool egl_init_desktop_shader(
 | 
				
			|||||||
  shader->uNearest     = egl_shader_get_uniform_location(shader->shader, "nearest" );
 | 
					  shader->uNearest     = egl_shader_get_uniform_location(shader->shader, "nearest" );
 | 
				
			||||||
  shader->uNV          = egl_shader_get_uniform_location(shader->shader, "nv"      );
 | 
					  shader->uNV          = egl_shader_get_uniform_location(shader->shader, "nv"      );
 | 
				
			||||||
  shader->uNVGain      = egl_shader_get_uniform_location(shader->shader, "nvGain"  );
 | 
					  shader->uNVGain      = egl_shader_get_uniform_location(shader->shader, "nvGain"  );
 | 
				
			||||||
 | 
					  shader->uCBMode      = egl_shader_get_uniform_location(shader->shader, "cbMode"  );
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  return true;
 | 
					  return true;
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
@@ -143,6 +148,7 @@ bool egl_desktop_init(EGL_Desktop ** desktop, EGLDisplay * display)
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
  (*desktop)->nvMax  = option_get_int("egl", "nvGainMax");
 | 
					  (*desktop)->nvMax  = option_get_int("egl", "nvGainMax");
 | 
				
			||||||
  (*desktop)->nvGain = option_get_int("egl", "nvGain"   );
 | 
					  (*desktop)->nvGain = option_get_int("egl", "nvGain"   );
 | 
				
			||||||
 | 
					  (*desktop)->cbMode = option_get_int("egl", "cbMode"   );
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  return true;
 | 
					  return true;
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
@@ -272,6 +278,7 @@ bool egl_desktop_render(EGL_Desktop * desktop, const float x, const float y, con
 | 
				
			|||||||
  else
 | 
					  else
 | 
				
			||||||
    glUniform1i(shader->uNV, 0);
 | 
					    glUniform1i(shader->uNV, 0);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					  glUniform1i(shader->uCBMode, desktop->cbMode);
 | 
				
			||||||
  egl_model_render(desktop->model);
 | 
					  egl_model_render(desktop->model);
 | 
				
			||||||
  return true;
 | 
					  return true;
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 
 | 
				
			|||||||
@@ -134,6 +134,13 @@ static struct Option egl_options[] =
 | 
				
			|||||||
    .type         = OPTION_TYPE_INT,
 | 
					    .type         = OPTION_TYPE_INT,
 | 
				
			||||||
    .value.x_int  = 0
 | 
					    .value.x_int  = 0
 | 
				
			||||||
  },
 | 
					  },
 | 
				
			||||||
 | 
					  {
 | 
				
			||||||
 | 
					    .module       = "egl",
 | 
				
			||||||
 | 
					    .name         = "cbMode",
 | 
				
			||||||
 | 
					    .description  = "Colorblind Mode (0 = Off, 1 = Protanope, 2 = Deuteranope, 3 = Tritanope)",
 | 
				
			||||||
 | 
					    .type         = OPTION_TYPE_INT,
 | 
				
			||||||
 | 
					    .value.x_int  = 0
 | 
				
			||||||
 | 
					  },
 | 
				
			||||||
  {0}
 | 
					  {0}
 | 
				
			||||||
};
 | 
					};
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 
 | 
				
			|||||||
@@ -5,7 +5,46 @@ out highp vec4 color;
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
uniform sampler2D sampler1;
 | 
					uniform sampler2D sampler1;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					uniform int cbMode;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
void main()
 | 
					void main()
 | 
				
			||||||
{
 | 
					{
 | 
				
			||||||
  color = texture(sampler1, uv);
 | 
					  color = texture(sampler1, uv);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					  if (cbMode > 0)
 | 
				
			||||||
 | 
					  {
 | 
				
			||||||
 | 
					    highp float L = (17.8824000 * color.r) + (43.516100 * color.g) + (4.11935 * color.b);
 | 
				
			||||||
 | 
					    highp float M = (03.4556500 * color.r) + (27.155400 * color.g) + (3.86714 * color.b);
 | 
				
			||||||
 | 
					    highp float S = (00.0299566 * color.r) + (00.184309 * color.g) + (1.46709 * color.b);
 | 
				
			||||||
 | 
					    highp float l, m, s;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    if (cbMode == 1) // Protanope
 | 
				
			||||||
 | 
					    {
 | 
				
			||||||
 | 
					      l = 0.0f * L + 2.02344f * M + -2.52581f * S;
 | 
				
			||||||
 | 
					      m = 0.0f * L + 1.0f * M + 0.0f * S;
 | 
				
			||||||
 | 
					      s = 0.0f * L + 0.0f * M + 1.0f * S;
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					    else if (cbMode == 2) // Deuteranope
 | 
				
			||||||
 | 
					    {
 | 
				
			||||||
 | 
					      l = 1.000000 * L + 0.0f * M + 0.00000 * S;
 | 
				
			||||||
 | 
					      m = 0.494207 * L + 0.0f * M + 1.24827 * S;
 | 
				
			||||||
 | 
					      s = 0.000000 * L + 0.0f * M + 1.00000 * S;
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					    else if (cbMode == 3) // Tritanope
 | 
				
			||||||
 | 
					    {
 | 
				
			||||||
 | 
					      l =  1.000000 * L + 0.000000 * M + 0.0 * S;
 | 
				
			||||||
 | 
					      m =  0.000000 * L + 1.000000 * M + 0.0 * S;
 | 
				
			||||||
 | 
					      s = -0.395913 * L + 0.801109 * M + 0.0 * S;
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    highp vec4 error;
 | 
				
			||||||
 | 
					    error.r = ( 0.080944447900 * l) + (-0.13050440900 * m) + ( 0.116721066 * s);
 | 
				
			||||||
 | 
					    error.g = (-0.010248533500 * l) + ( 0.05401932660 * m) + (-0.113614708 * s);
 | 
				
			||||||
 | 
					    error.b = (-0.000365296938 * l) + (-0.00412161469 * m) + ( 0.693511405 * s);
 | 
				
			||||||
 | 
					    error.a = 0.0;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    error = color - error;
 | 
				
			||||||
 | 
					    color.g += (error.r * 0.7) + (error.g * 1.0);
 | 
				
			||||||
 | 
					    color.b += (error.r * 0.7) + (error.b * 1.0);
 | 
				
			||||||
 | 
					  }
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 
 | 
				
			|||||||
@@ -10,6 +10,7 @@ uniform highp vec2  size;
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
uniform       int   nv;
 | 
					uniform       int   nv;
 | 
				
			||||||
uniform highp float nvGain;
 | 
					uniform highp float nvGain;
 | 
				
			||||||
 | 
					uniform       int   cbMode;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
void main()
 | 
					void main()
 | 
				
			||||||
{
 | 
					{
 | 
				
			||||||
@@ -18,6 +19,43 @@ void main()
 | 
				
			|||||||
  else
 | 
					  else
 | 
				
			||||||
    color = texelFetch(sampler1, ivec2(uv * size), 0);
 | 
					    color = texelFetch(sampler1, ivec2(uv * size), 0);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					  if (cbMode > 0)
 | 
				
			||||||
 | 
					  {
 | 
				
			||||||
 | 
					    highp float L = (17.8824000 * color.r) + (43.516100 * color.g) + (4.11935 * color.b);
 | 
				
			||||||
 | 
					    highp float M = (03.4556500 * color.r) + (27.155400 * color.g) + (3.86714 * color.b);
 | 
				
			||||||
 | 
					    highp float S = (00.0299566 * color.r) + (00.184309 * color.g) + (1.46709 * color.b);
 | 
				
			||||||
 | 
					    highp float l, m, s;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    if (cbMode == 1) // Protanope
 | 
				
			||||||
 | 
					    {
 | 
				
			||||||
 | 
					      l = 0.0f * L + 2.02344f * M + -2.52581f * S;
 | 
				
			||||||
 | 
					      m = 0.0f * L + 1.0f * M + 0.0f * S;
 | 
				
			||||||
 | 
					      s = 0.0f * L + 0.0f * M + 1.0f * S;
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					    else if (cbMode == 2) // Deuteranope
 | 
				
			||||||
 | 
					    {
 | 
				
			||||||
 | 
					      l = 1.000000 * L + 0.0f * M + 0.00000 * S;
 | 
				
			||||||
 | 
					      m = 0.494207 * L + 0.0f * M + 1.24827 * S;
 | 
				
			||||||
 | 
					      s = 0.000000 * L + 0.0f * M + 1.00000 * S;
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					    else if (cbMode == 3) // Tritanope
 | 
				
			||||||
 | 
					    {
 | 
				
			||||||
 | 
					      l =  1.000000 * L + 0.000000 * M + 0.0 * S;
 | 
				
			||||||
 | 
					      m =  0.000000 * L + 1.000000 * M + 0.0 * S;
 | 
				
			||||||
 | 
					      s = -0.395913 * L + 0.801109 * M + 0.0 * S;
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    highp vec4 error;
 | 
				
			||||||
 | 
					    error.r = ( 0.080944447900 * l) + (-0.13050440900 * m) + ( 0.116721066 * s);
 | 
				
			||||||
 | 
					    error.g = (-0.010248533500 * l) + ( 0.05401932660 * m) + (-0.113614708 * s);
 | 
				
			||||||
 | 
					    error.b = (-0.000365296938 * l) + (-0.00412161469 * m) + ( 0.693511405 * s);
 | 
				
			||||||
 | 
					    error.a = 0.0;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    error = color - error;
 | 
				
			||||||
 | 
					    color.g += (error.r * 0.7) + (error.g * 1.0);
 | 
				
			||||||
 | 
					    color.b += (error.r * 0.7) + (error.b * 1.0);
 | 
				
			||||||
 | 
					  }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
  if (nv == 1)
 | 
					  if (nv == 1)
 | 
				
			||||||
  {
 | 
					  {
 | 
				
			||||||
    highp float lumi = 1.0 - (0.2126 * color.r + 0.7152 * color.g + 0.0722 * color.b);
 | 
					    highp float lumi = 1.0 - (0.2126 * color.r + 0.7152 * color.g + 0.0722 * color.b);
 | 
				
			||||||
 
 | 
				
			|||||||
		Reference in New Issue
	
	Block a user