#version 330

layout( triangles ) in;
layout( triangle_strip, max_vertices = 6) out;

uniform mat4 WorldView;
uniform mat4 WorldViewProj;
uniform int ResolutionX;
uniform int ResolutionY;

uniform bool Edge;

in vec3 VSWorldPos[];
in vec4 VSColor[];
in vec3 VSNormal[];
in vec2 VSTexCoord[];

out vec4 GSWorldPos;
out vec4 GSColor;
out vec3 GSNormal;
out vec2 GSTexCoord;

vec4 GetOutlinePos(int id)
{
	float width = 1.0;
	if(Edge && gl_in[id].gl_Position.w != 0.0 && gl_in[id].gl_Position.z/gl_in[id].gl_Position.w > -1.0){
		vec3 axisX = vec3(WorldView[0][0], WorldView[1][0], WorldView[2][0]);
		vec4 pos = WorldViewProj * vec4(VSWorldPos[id] + axisX, 1);
		vec2 p1 = pos.xy / pos.w;
		vec2 p0 = gl_in[id].gl_Position.xy / gl_in[id].gl_Position.w;
		float w = 1.0 / float(ResolutionX) * 2;
		float scale = width * w / length(p1 - p0);
		return WorldViewProj * vec4(VSWorldPos[id] + VSNormal[id] * scale, 1);
	}else{
		return gl_in[id].gl_Position;
	}
}

void main(void)
{
	for(int i=0; i<3; i++){
		GSWorldPos = vec4(VSWorldPos[i],1);
		GSColor = VSColor[i];
		GSNormal = VSNormal[i];
		GSTexCoord = VSTexCoord[i];
		gl_Position = gl_in[i].gl_Position;
		EmitVertex();
	}
	EndPrimitive();

	if(Edge){
		for(int i=2; i>=0; i--){
			GSWorldPos = vec4(VSWorldPos[i],0);
			GSColor = VSColor[i];
			GSNormal = VSNormal[i];
			GSTexCoord = VSTexCoord[i];
			gl_Position = GetOutlinePos(i);
			EmitVertex();
		}
		EndPrimitive();
	}
}

