uniform variable causing problems in fragment shader - java

This is my fragment shader code. Its an implementation of Gradient Map function.
varying vec2 v_TextureCoord;
uniform samplerExternalOES sTexture;
uniform sampler2D u_GradientTexture;
uniform float u_FilParOne;
const highp vec3 W = vec3(0.2989, 0.5870, 0.1140);
void main() {
lowp vec4 textureColor = texture2D(sTexture, v_TextureCoord);
float gray = dot(textureColor.rgb, W);
float samplePoint = (0.2 + ((1.0 - 0.2) * gray));
vec4 map = texture2D(u_GradientTexture, vec2(samplePoint, 5.0));
gl_FragColor = vec4(vec3(map), textureColor.a);
}
Note the line
float samplePoint = (0.2 + ((1.0 - 0.2) * gray));
the 0.2 there is something I would like to replace with a parameter. so I used the uniform u_FilParOne. But when I replace the 0.2 with that variable like this:
float samplePoint = (u_FilParOne + ((1.0 - u_FilParOne) * gray));
my program runs but the Screen just keeps cycling through random colors.
when I replace all the code in the main function with
gl_FragColor = vec4(u_FilParOne, u_FilParOne, u_FilParOne, 1.0);
My screen turns gray and when i change the value of the uniform from my java code with the lines :
filterParameterOne=0.2f;
glUniform1f(mUniformFilterParameterOneHandle, filterParameterOne);
I can control the lightness and darkness of the gray, Which means that the value is being sent correctly from Java to OpenGL.
Is there something I am missing here? Why can't I use the uniform in the original program itself?

Related

Why are my uniform locations showing incorrectly?

I'm attempting to get the uniform locations of variables in my shader.
#Override
public void getAllUniformLocations(){
location_transformationMatrix = super.getUniformLocation("transformationMatrix");
location_lightPosition = super.getUniformLocation("lightPosition");
location_lightColour = super.getUniformLocation("lightColour");
System.out.println(location_transformationMatrix + " | "
+ location_lightPosition + " | " + location_lightColour);
}
public int getUniformLocation(String name){
return GL20.glGetUniformLocation(programID, name);
}
However, when it prints out, it prints completely incorrectly:
0 | -1 | -1
0 is for the fixed-function pipeline, so having something bound there is going to completely crash the program, and the other two are simply returning -1, which is a null value.
Here is my shader loading code:
public ShaderProgram(String vertexFile,String fragmentFile){
System.out.println("Comiling shader!");
vertexShaderID = loadShader(vertexFile,GL20.GL_VERTEX_SHADER);
fragmentShaderID = loadShader(fragmentFile,GL20.GL_FRAGMENT_SHADER);
programID = GL20.glCreateProgram();
GL20.glAttachShader(programID, vertexShaderID);
GL20.glAttachShader(programID, fragmentShaderID);
bindAttributes();
getAllUniformLocations();
GL20.glLinkProgram(programID);
GL20.glValidateProgram(programID);
start();
System.out.println(GL11.glGetError());
System.out.println("Comiled shader!");
}
The shaders bind, attach, validate, compile, etc, completely successfully, and the game does successfully run at this point. However, the uniform locations are missing and so I am unable to achieve things like lighting.
Here is my vertex shader:
#version 130
in vec3 position;
in vec2 textureCoords;
in vec3 normal;
out vec2 pass_textureCoords;
out vec3 surfaceNormal;
out vec3 toLightVector;
uniform mat4 transformationMatrix;
uniform vec3 lightPosition;
void main(void){
gl_Position = ftransform();
pass_textureCoords = textureCoords;
surfaceNormal = (transformationMatrix * vec4(normal, 0.0)).xyz;
toLightVector = (vec3(0, 20000, 0)) - (transformationMatrix * vec4(position, 1.0)).xyz;
}
Variables 0, 1, 2, and 3 are all bound to attributes, so I would expect the numbers to return something along the lines of "4 | 5 | 6".
Here is my fragment shader:
#version 130
in vec2 pass_textureCoords;
in vec3 surfaceNormal;
in vec3 toLightVector;
out vec4 out_Color;
uniform sampler2D textureSampler;
uniform vec3 lightColour;
void main(void){
vec3 unitNormal = normalize(surfaceNormal);
vec3 unitLightVector = normalize(toLightVector);
float nDot1 = dot(unitNormal, unitLightVector);
float brightness = max(nDot1, 0.5);
brightness = brightness * 1.5;
vec3 diffuse = brightness * vec3(1, 1, 1);
vec4 text = texture(textureSampler, pass_textureCoords);
vec4 textureColor = vec4(diffuse, 1.0) * text;
if(textureColor.a<0.01){
discard;
}
out_Color = vec4(textureColor.r, textureColor.g, textureColor.b, textureColor.a);
}
The results you are getting are absoutely correct, your interpretations of them are not:
0 is for the fixed-function pipeline, so having something bound there
is going to completely crash the program,
No. 0 is a perfectly valid uniform location, which has nothing to do the fixed function pipeline. You somehow seem to confuse the program object 0 (which represents the fixed-function pipeline in legacy GL and compatibility profiles) with the per-program uniform locations.
and the other two are simply
returning -1, which is a null value.
Well, more or less. -1 means that there is no acivte uniform of that name. Note that calling glUniform*() functions with location -1 is explicitely defined to be no error - such calls just have no effect.
The shader code you have pasted simply does not use the lightPosition and lightColour uniforms, so they are not there. You might intend to use them in the fragment shader, but I'd bet my life on it that you don't do it there in the correct way - i.e. even if you declare and use them in the code, they might still have no effect on the shader outputs, so are still not active.

Phone unable to compile shader

I have a project I'm working on in libGDX. I'm running tests on a distance field font and I've run into issues while compiling the shader on my Android phone (Galaxy Core 2 4.4.2). When deployed on my phone I get errors while the desktop app works fine (mostly - I'll get to that).
I'll take you through what I've been trying.
I want to be able to enable and disable having a font border during run time, and I can do this fine on the desktop app using the following shader and methods.
.frag:
#ifdef GL_ES
precision mediump float;
#else
#define LOWP
#endif
uniform sampler2D u_texture;
uniform float u_lower;
uniform float u_upper;
varying vec4 v_color;
uniform vec4 u_outlineColor;
uniform float u_enableOutline;
varying vec2 v_texCoord;
const float smoothing = 1.0/12.0;
const float outlineWidth = 3.0/12.0; //will need to be tweaked
const float outerEdgeCenter = 0.5 - outlineWidth; //for optimizing below calculation
void main() {
float distance = texture2D(u_texture, v_texCoord).a;
if (u_enableOutline > 0){
float alpha = smoothstep(outerEdgeCenter - smoothing, outerEdgeCenter + smoothing, distance);//Bigger to accomodate outline
float border = smoothstep(0.45 - smoothing, 0.55 + smoothing, distance);
gl_FragColor = vec4( mix(u_outlineColor.rgb, v_color.rgb, border), alpha );
}
else{
float alpha = smoothstep(0.5 - smoothing, 0.5 + smoothing, distance);
gl_FragColor = vec4(v_color.rgb, alpha);
}
}
.vert:
uniform mat4 u_projTrans;
attribute vec4 a_position;
attribute vec2 a_texCoord0;
attribute vec4 a_color;
varying vec4 v_color;
varying vec2 v_texCoord;
void main() {
gl_Position = u_projTrans * a_position;
v_texCoord = a_texCoord0;
v_color = a_color;
}
With the distance font method to enable / disable the outline being:
public void enableOutline(float enable) {
ENABLE_OUTLINE = enable;
}
Where ENABLE_OUTLINE is passed to the shader by
distanceFieldShader.setUniformf("u_enableOutline", ENABLE_OUTLINE);
In this set up, running on my phone gives the following error:
"cannot compare float to int"
referencing this line in the .frag
if (u_enableOutline > 0){
Fair enough I say, so I change the data type like so:
uniform int u_enableOutline;
And the method to pass through an int:
public void enableOutline(int enable) {
ENABLE_OUTLINE = enable;
}
BUT there is no way to pass an int to the shader (which is why I chose to use floats, see this image: http://imgur.com/nVTN12i) and because of this my method to enable the outline doesn't work due to mixing up data types.
So my question is: can I get around this somehow so that I can enable and disable a border on my phone given these constraints?
It sounds like the API you are using does not offer you the possibility to use bool and int as Uniforms. The solution of using floats to circumvent this seems to be a good idea.
In your example, the problem you are having is because, unlike C and java, the GLSL compiler does not implicitly convert ints to floats.
what you need to do, is tell the compiler the type of your "0".
By using the syntax, 0.0, the compiler knows that your constant is a float and not an integer.
if (u_enableOutline > 0.0){
should fix your problem

Getting world position for deferred rendering light pass

I have recently began to build some kind of deferred rendering pipeline for the engine I am working on but I'm stuck at reconstructing the world position from depth. I have looked at quite a few examples where the explain that you need either a world position texture or a depth texture to then use for the correct distance and direction calculation of the light.
My problem is that the so called position texture which assumably is the world position doesn't seem to give me correct data. Therefore I tried to find alternative ways of getting a world position and some have suggested that I should use a depth texture instead but then what?
To make it all more clear this picture shows the textures that I currently have stored:
Position(Top left), Normal(Top right), Diffuse(Bottom left) and Depth(Bottom right).
For the light pass I am trying to use a method which works fine if used in the first pass. When I try the same method for the light pass with the exact same variables it stops working.
Here's my Geometry Vertex Shader:
#version 150
uniform mat4 projectionMatrix;
uniform mat4 viewMatrix;
uniform mat4 modelMatrix;
in vec4 in_Position;
in vec3 in_Normal;
in vec2 in_TextureCoord;
out vec3 pass_Normals;
out vec4 pass_Position;
out vec2 pass_TextureCoord;
out vec4 pass_Diffuse;
void main(void) {
pass_Position = viewMatrix * modelMatrix * in_Position;
pass_Normals = (viewMatrix * modelMatrix * vec4(in_Normal, 0.0)).xyz;
pass_Diffuse = vec4(1,1,1,1);
gl_Position = projectionMatrix * pass_Position;
}
Geometry Fragment shader:
#version 150 core
uniform sampler2D texture_diffuse;
uniform mat4 projectionMatrix;
uniform mat4 viewMatrix;
uniform mat4 modelMatrix;
in vec4 pass_Position;
in vec3 pass_Normals;
in vec2 pass_TextureCoord;
in vec4 pass_Diffuse;
out vec4 out_Diffuse;
out vec4 out_Position;
out vec4 out_Normals;
void main(void) {
out_Position = pass_Position;
out_Normals = vec4(pass_Normals, 1.0);
out_Diffuse = pass_Diffuse;
}
Light Vertex Shader:
#version 150
in vec4 in_Position;
in vec2 in_TextureCoord;
out vec2 pass_TextureCoord;
void main( void )
{
gl_Position = in_Position;
pass_TextureCoord = in_TextureCoord;
}
Light Fragment Shader:
#version 150 core
uniform sampler2D texture_Diffuse;
uniform sampler2D texture_Normals;
uniform sampler2D texture_Position;
uniform vec3 cameraPosition;
uniform mat4 viewMatrix;
in vec2 pass_TextureCoord;
out vec4 frag_Color;
void main( void )
{
frag_Color = vec4(1,1,1,1);
vec4 image = texture(texture_Diffuse,pass_TextureCoord);
vec3 position = texture( texture_Position, pass_TextureCoord).rgb;
vec3 normal = texture( texture_Normals, pass_TextureCoord).rgb;
frag_Color = image;
vec3 LightPosition_worldspace = vec3(0,2,0);
vec3 vertexPosition_cameraspace = position;
vec3 EyeDirection_cameraspace = vec3(0,0,0) - vertexPosition_cameraspace;
vec3 LightPosition_cameraspace = ( viewMatrix * vec4(LightPosition_worldspace,1)).xyz;
vec3 LightDirection_cameraspace = LightPosition_cameraspace + EyeDirection_cameraspace;
vec3 n = normal;
vec3 l = normalize( LightDirection_cameraspace );
float cosTheta = max( dot( n,l ), 0);
float distance = distance(LightPosition_cameraspace, vertexPosition_cameraspace);
frag_Color = vec4((vec3(10,10,10) * cosTheta)/(distance*distance)), 1);
}
And finally, here's the current result:
So My question is if anyone please can explain the result or how I should do to get a correct result. I would also appreciate good resources on the area.
Yes, using the depth buffer to reconstruct position is your best bet. This will significantly cut down on memory bandwidth / storage requirements. Modern hardware is biased towards doing shader calculations rather than memory fetches (this was not always the case), and the instructions necessary to reconstruct position per-fragment will always finish quicker than if you were to fetch the position from a texture with adequate precision. Now, you just have to realize what the hardware depth buffer stores (understand how depth range and perspective distribution work) and you will be good to go.
I do not see any attempt at reconstruction of world/view space position from the depth buffer in the code your question lists. You are just sampling from a buffer that stores the position in view-space. Since you are not performing reconstruction in this example, the problem has to do with sampling the view-space position... can you update your question to include the internal formats of the G-Buffer textures. In particular, are you using a format that can represent negative values (this is necessary to express position, otherwise negative values are clamped to 0).
On a final note, your position is also view-space and not world-space, a trained eye can tell this immediately by the way the colors in your position buffer are black in the lower-left corner. If you want to debug your position/normal, you should bias/scale the sampled colors into the visible range:
([-1.0, 1.0] -> [0.0, 1.0]) // Vec = Vec * 0.5 + 0.5
You may need to do this when you output some of the buffers if you want to store the normal G-Buffer more efficiently (e.g. in an 8-bit fixed-point texture instead of floating-point).

LibGdx shader "no uniform with name..." in phong shader

I'm very new to OpenGL and LibGdx. I started with these tutorials but wanted to apply a phong texture. I've tried to merge a number of examples but am having issues.
I've got a sphere and spinning cube on the center of the screen. I've still got hundreds of things to work out but for the moment, I don't understand why LibGdx is reporting that my uniform material can't be found...
Exception in thread "LWJGL Application" com.badlogic.gdx.utils.GdxRuntimeException: java.lang.IllegalArgumentException: no uniform with name 'uMvpMatrix' in shader
Pixel Shader
I don't believe the Fragment shader is relevant but it's at the bottom in case.
#version 120
uniform mat4 uMvpMatrix;
varying vec3 diffuseColor;
// the diffuse Phong lighting computed in the vertex shader
varying vec3 specularColor;
// the specular Phong lighting computed in the vertex shader
varying vec4 texCoords; // the texture coordinates
void main()
{
vec3 normalDirection =
normalize(gl_NormalMatrix * gl_Normal);
vec3 viewDirection =
-normalize(vec3(gl_ModelViewMatrix * gl_Vertex));
vec3 lightDirection;
float attenuation;
if (0.0 == gl_LightSource[0].position.w)
// directional light?
{
attenuation = 1.0; // no attenuation
lightDirection =
normalize(vec3(gl_LightSource[0].position));
}
else // point light or spotlight (or other kind of light)
{
vec3 vertexToLightSource =
vec3(gl_LightSource[0].position
- gl_ModelViewMatrix * gl_Vertex);
float distance = length(vertexToLightSource);
attenuation = 1.0 / distance; // linear attenuation
lightDirection = normalize(vertexToLightSource);
if (gl_LightSource[0].spotCutoff <= 90.0) // spotlight?
{
float clampedCosine = max(0.0, dot(-lightDirection,
gl_LightSource[0].spotDirection));
if (clampedCosine < gl_LightSource[0].spotCosCutoff)
// outside of spotlight cone?
{
attenuation = 0.0;
}
else
{
attenuation = attenuation * pow(clampedCosine,
gl_LightSource[0].spotExponent);
}
}
}
vec3 ambientLighting = vec3(gl_LightModel.ambient);
// without material color!
vec3 diffuseReflection = attenuation
* vec3(gl_LightSource[0].diffuse)
* max(0.0, dot(normalDirection, lightDirection));
// without material color!
vec3 specularReflection;
if (dot(normalDirection, lightDirection) < 0.0)
// light source on the wrong side?
{
specularReflection = vec3(0.0, 0.0, 0.0);
// no specular reflection
}
else // light source on the right side
{
specularReflection = attenuation
* vec3(gl_LightSource[0].specular)
* vec3(gl_FrontMaterial.specular)
* pow(max(0.0, dot(reflect(-lightDirection,
normalDirection), viewDirection)),
gl_FrontMaterial.shininess);
}
diffuseColor = ambientLighting + diffuseReflection;
specularColor = specularReflection;
texCoords = gl_MultiTexCoord0;
gl_Position = gl_ModelViewProjectionMatrix * gl_Vertex;
}
Setup
shader = new ShaderProgram(vertexShader, fragmentShader);
mesh = Shapes.genCube();
mesh.getVertexAttribute(Usage.Position).alias = "a_position";
Render
...
float aspect = Gdx.graphics.getWidth() / (float) Gdx.graphics.getHeight();
projection.setToProjection(1.0f, 20.0f, 60.0f, aspect);
view.idt().trn(0, 0, -2.0f);
model.setToRotation(axis, angle);
combined.set(projection).mul(view).mul(model);
Gdx.gl20.glViewport(0, 0, Gdx.graphics.getWidth(), Gdx.graphics.getHeight());
shader.begin();
shader.setUniformMatrix("uMvpMatrix", combined);
mesh.render(shader, GL20.GL_TRIANGLES);
shader.end();
Stack Trace
at com.badlogic.gdx.backends.lwjgl.LwjglApplication$1.run(LwjglApplication.java:113)
Caused by: java.lang.IllegalArgumentException: no uniform with name 'uMvpMatrix' in shader
at com.badlogic.gdx.graphics.glutils.ShaderProgram.fetchUniformLocation(ShaderProgram.java:283)
at com.badlogic.gdx.graphics.glutils.ShaderProgram.setUniformMatrix(ShaderProgram.java:539)
at com.badlogic.gdx.graphics.glutils.ShaderProgram.setUniformMatrix(ShaderProgram.java:527)
at com.overshare.document.Views.Test.onRender(Test.java:150)
...
Fragment Shader
#ifdef GL_ES
precision mediump float;
#endif
precision mediump float;
varying vec4 v_Color;
void main()
{
gl_FragColor = v_Color;
}
Can someone please tell me what I'm missing?
I ran into something similar. I think because your shader doesn't use the "uMvpMatrix" uniform, it declaration gets optimized out, and so its "not there" when you go to set it. If you change your shader to reference the matrix in some way, you should get farther.
See (indirectly)
Do (Unused) GLSL uniforms/in/out Contribute to Register Pressure?
I believe there are ways of developing and compiling shaders offline, so for a complex shader it may make sense to develop it outside of Libgdx (hopefully you'd get better error messages). Libgdx is just passing the giant string on to the lower layers, it doesn't do much with the shader itself, so there shouldn't be compatibility issues.
Also, problem could be in precision specifier. On device(Nexus S) the next uniform defining will throw the same error:
uniform float yShift;
Using precision specifier solves the problem:
uniform lowp float yShift;
LibGDX allows to check shader compilation and get error log:
if(!shader.isCompiled()){
String log = shader.getLog();
}
Finally, there's flag to ignore shader errors:
ShaderProgram.pedantic = false;

Invalid fragment shader. Link cannot proceed

At the beginning of my project, I used simple Strings for filling my both Shaders with code. This looked like this:
public final static String chunkDefaultVertexInit = ""
+constantParameters
+"precision mediump float;"
+"uniform mat4 mPMatrix;"
+"uniform mat4 mVMatrix;"
+"uniform mat4 mMMatrix;"
+"uniform mat4 mMVMatrix;"
+"attribute vec4 Vertex;"
+"attribute vec3 Normal;"
+"attribute vec2 TexCoord;"
+"varying vec3 normal;"
+"varying vec2 uv;"
+"varying vec4 positionM;"
+"varying vec4 positionMV;";
etc....
This worked for me, but it was not really clearly. So I thought about how I could make my code a little bit more clean and clearly for everybody. My idea was, to put my whole bunch of code in a real .cc - file and move it into the res/raw folder. No sooner said than done.
I wanted to read out my code via Inputstreams and save it into a String. That also worked fine, and so I fed the shader the String source.
So... now there happend to be a problem, and as I said, I didn't get it yet. I even made me a little bit angry about myself, because I thought about an easy way of fix it and I don't see it.
I even did show my source code I put in... but it looks correct! o.O
Log.i("Llama3D Shader",shaderCode);
(Don't worry about the weird "Debug ID," it's the projects name)
Here's the source code for the shaders:
Vertexshader:
//vertexshader
precision mediump float;
uniform mat4 mPMatrix;
uniform mat4 mVMatrix;
uniform mat4 mMMatrix;
uniform mat4 mMVMatrix;
attribute vec4 aVertex;
attribute vec3 aNormal;
attribute vec2 aTexCoord;
varying vec2 vecTexCoord;
varying vec3 vecNormal;
varying vec4 vecVertex[2];
void main() {
gl_Position = mPMatrix * mMVMatrix * aVertex;
vecVertex[0] = mMMatrix * aVertex;
vecVertex[1] = mMVMatrix * aVertex;
vecTexCoord = aTexCoord;
vecNormal = normalize(vec3(mMMatrix * -vec4(aNormal,0.0)));
}
Fragmentshader:
#define MAX_POINT_LIGHTS 4
precision mediump float;
varying vec2 vecTexCoord;
varying vec3 vecNormal;
varying vec4 vecVertex[2];
uniform vec3 uVecEye;
uniform vec3 uPointLightPosition[MAX_POINT_LIGHTS];
uniform vec3 uPointLightColor[MAX_POINT_LIGHTS];
uniform sampler2D textureHandle;
vec3 V = normalize(uVecEye.xyz-vecVertex[1].xyz);
vec3 N = vNormal;
vec3 vecLight[MAX_POINT_LIGHTS];
vec4 pointDiffuse = vec4(0.0);
vec4 pointSpecular = vec4(0.0);
vec4 ambient = vec4(0.2,0.2,0.2,1.0);
vec4 color = vec4(1.0,1.0,1.0,1.0);
vec4 matSpec = vec4(1.0,1.0,1.0,1.0);
vec4 lightSpec = vec4(1.0,1.0,1.0,1.0);
vec4 spec = matSpec * lightSpec;
float shininess = 20.0;
void main() {
for (int i=0;i<MAX_POINT_LIGHTS;i++) {
vecLight[i].xyz = vecVertex[0].xyz - uPointLightPosition[i].xyz;
float vecDistance = length(vecLight[i].xyz);
if (vecDistance<=25.0) {
vecDistance = 1.0 - max(0.0,vecDistance)/25.0;
vec3 L = normalize(vecLight[i]);
vec3 R = normalize(reflect(L,N));
float LND = max(0.0,dot(N,L)) * vecDistance;
pointDiffuse += color * vec4(uPointLightColor[i].xyz,0.0) * LND;
if (shininess!=0.0 && spec!=0.0) {
pointSpecular += spec * pow(max(0.0,dot(R,V)),shininess) * LND;
} else {
pointSpecular += vec4(0.0,0.0,0.0,0.0);
}
}
}
vec4 colorTexture = texture2D(textureHandle,vec2(+vTexCoord.x,-vTexCoord.y));
gl_FragColor = ambient + colorTexture * pointDiffuse + pointSpecular;
}
Every time I try to run the program, the ShaderlogInfo and ProgramlogInfo say to me:
Invalid fragment shader. Link cannot proceed.*
Am I crazy or just blind?!
I hope you know an answer... I really don't know any... please help me!
The log you got is from the Program linking stage, glGetProgramInfoLog.
What you need to debug is the Fragment Shader log, glGetShaderInfoLog.
Something along these lines:
def _compile(self, source):
ptr = cast(c_char_p(source), POINTER(c_char))
glShaderSource(self.id, 1, byref(ptr), None)
glCompileShader(self.id)
status = c_int(0)
glGetShaderiv(self.id, GL_COMPILE_STATUS, byref(status))
log = self.check()
print(log),
if not status.value:
raise Exception(log)
def check(self):
length = c_int(0)
glGetShaderiv(self.id, GL_INFO_LOG_LENGTH, byref(length))
log = create_string_buffer(length.value)
glGetShaderInfoLog(self.id, length.value, None, log)
return log.value
Though this is not in java but in python, it should give you an idea of how to get your shader compile log.
Compiling your shaders in my environment gives me this log which may or may not be useful to you:
Vertex shader was successfully compiled to run on hardware.
WARNING: 0:2: warning(#260) Keyword 'precision' is supported in GLSL 1.3
Fragment shader failed to compile with the following errors:
WARNING: 0:2: warning(#260) Keyword 'precision' is supported in GLSL 1.3
ERROR: 0:14: error(#143) Undeclared identifier vNormal
WARNING: 0:14: warning(#402) Implicit truncation of vector from size 1 to size 3.
ERROR: 0:50: error(#143) Undeclared identifier vTexCoord
ERROR: 0:50: error(#216) Vector field selection out of range 'y'
ERROR: error(#273) 4 compilation errors. No code generated

Categories

Resources