#ifdef GL_ES
precision highp float;
#else
#define lowp
#define mediump
#define highp
#endif

IN(0) vec2 tex_coord_0;

UNIFORM_BEGIN
  UNIFORM_V(vec2 scale)
  UNIFORM_V(mat4 projection)
  UNIFORM_F(vec2 sky_offset)
  UNIFORM_F(vec3 nebula_color)
UNIFORM_END

FRAG_COLOR_OUT(frag_color)

float random(vec2 p) {
  float sd = sin(dot(p, vec2(54.90898, 18.233)));
  return fract(sd * 2671.6182);
}

float nebula(in vec2 p) {
  vec2 i = floor(p);
  vec2 f = fract(p);

  float a = random(i);
  float b = random(i + vec2(1.0, 0.0));
  float c = random(i + vec2(0.0, 1.0));
  float d = random(i + vec2(1.0, 1.0));

  vec2 u = smoothstep(0.0, 1.0, f);

  return mix(a, b, u.x) +
      (c - a)* u.y * (1.0 - u.x) +
      (d - b) * u.x * u.y;
}

float stars(in vec2 p, float num_cells, float size) {
  vec2 n = p * num_cells;
  vec2 i = floor(n);

  vec2 a = n - i - random(i);
  a /= num_cells * size;
  float e = dot(a, a);

  return smoothstep(0.94, 1.0, (1.0 - e * 35.0));
}

void main() {
  vec2 layer1_coord = tex_coord_0 + PARAM(sky_offset);
  vec2 layer2_coord = tex_coord_0 + PARAM(sky_offset)  * 0.7;
  mediump vec3 result = vec3(0.);

  float c = nebula(layer2_coord * 3.0) * 0.35 - 0.05;
  result += PARAM(nebula_color) * floor(c * 60.0) / 60.0;

  c = stars(layer1_coord, 8.0, 0.05);
  result += vec3(0.97, 0.74, 0.74) * c;

  c = stars(layer2_coord, 16.0, 0.025) * 0.5;
  result += vec3(0.9, 0.9, 0.95) * c;

  FRAG_COLOR(frag_color) = vec4(result, 1.0);
}
