blob: 19f43cd8a7e2c8d5563623a1a0e7dcf4285cdece [file] [log] [blame]
Marius Renn65953da2012-03-27 10:44:45 -07001/*
2 * Copyright (C) 2011 The Android Open Source Project
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16
17#include <string>
18#include <vector>
19
20#include "jni/jni_shader_program.h"
21#include "jni/jni_util.h"
22
23#include "native/base/logging.h"
24#include "native/core/geometry.h"
25#include "native/core/gl_env.h"
26#include "native/core/gl_frame.h"
27#include "native/core/shader_program.h"
28#include "native/core/vertex_frame.h"
29
30using android::filterfw::GLEnv;
31using android::filterfw::GLFrame;
32using android::filterfw::Point;
33using android::filterfw::ProgramVar;
34using android::filterfw::Quad;
35using android::filterfw::ShaderProgram;
36using android::filterfw::VertexFrame;
37
38jboolean Java_android_filterfw_core_ShaderProgram_allocate(JNIEnv* env,
39 jobject thiz,
40 jobject gl_env,
41 jstring vertex_shader,
42 jstring fragment_shader) {
43 // Get the GLEnv pointer
44 GLEnv* gl_env_ptr = ConvertFromJava<GLEnv>(env, gl_env);
45
46 // Create the shader
47 if (!fragment_shader || !gl_env_ptr)
48 return false;
49 else if (!vertex_shader)
50 return ToJBool(WrapObjectInJava(new ShaderProgram(
51 gl_env_ptr,
52 ToCppString(env, fragment_shader)),
53 env,
54 thiz,
55 true));
56 else
57 return ToJBool(WrapObjectInJava(new ShaderProgram(
58 gl_env_ptr,
59 ToCppString(env, vertex_shader),
60 ToCppString(env, fragment_shader)),
61 env,
62 thiz,
63 true));
64}
65
66jboolean Java_android_filterfw_core_ShaderProgram_deallocate(JNIEnv* env, jobject thiz) {
67 return ToJBool(DeleteNativeObject<ShaderProgram>(env, thiz));
68}
69
70jboolean Java_android_filterfw_core_ShaderProgram_compileAndLink(JNIEnv* env, jobject thiz) {
71 ShaderProgram* program = ConvertFromJava<ShaderProgram>(env, thiz);
72 return program ? ToJBool(program->CompileAndLink()) : JNI_FALSE;
73}
74
75jboolean Java_android_filterfw_core_ShaderProgram_setUniformValue(JNIEnv* env,
76 jobject thiz,
77 jstring key,
78 jobject value) {
79 ShaderProgram* program = ConvertFromJava<ShaderProgram>(env, thiz);
80 const Value c_value = ToCValue(env, value);
81 const std::string c_key = ToCppString(env, key);
82 if (c_value.value) {
83 return ToJBool(program && program->SetUniformValue(c_key, c_value));
84 } else {
85 ALOGE("ShaderProgram: Could not convert java object value passed for key '%s'!", c_key.c_str());
86 return JNI_FALSE;
87 }
88}
89
90jobject Java_android_filterfw_core_ShaderProgram_getUniformValue(JNIEnv* env,
91 jobject thiz,
92 jstring key) {
93 ShaderProgram* program = ConvertFromJava<ShaderProgram>(env, thiz);
94 const std::string c_key = ToCppString(env, key);
95 return program ? ToJObject(env, program->GetUniformValue(c_key)) : JNI_NULL;
96}
97
98jboolean Java_android_filterfw_core_ShaderProgram_shaderProcess(JNIEnv* env,
99 jobject thiz,
100 jobjectArray inputs,
101 jobject output) {
102 ShaderProgram* program = ConvertFromJava<ShaderProgram>(env, thiz);
103 std::vector<const GLFrame*> input_frames;
104 if (program && inputs && output) {
105 // Get the input frames
106 const int input_count = env->GetArrayLength(inputs);
107 for (int i = 0; i < input_count; ++i) {
108 jobject input = env->GetObjectArrayElement(inputs, i);
109 const GLFrame* input_frame = ConvertFromJava<GLFrame>(env, input);
110 if (!input || !input_frame) {
111 ALOGE("ShaderProgram: invalid input frame %d!", i);
112 return JNI_FALSE;
113 }
114 input_frames.push_back(input_frame);
115 }
116
117 // Get the output frame
118 GLFrame* output_frame = ConvertFromJava<GLFrame>(env, output);
119 if (!output_frame) {
120 ALOGE("ShaderProgram: no output frame found!");
121 return JNI_FALSE;
122 }
123
124 // Process the frames!
125 if (!program->Process(input_frames, output_frame)) {
126 ALOGE("ShaderProgram: error processing shader!");
127 return JNI_FALSE;
128 }
129
130 return JNI_TRUE;
131 }
132 return JNI_FALSE;
133}
134
135jobject Java_android_filterfw_core_ShaderProgram_nativeCreateIdentity(JNIEnv* env,
136 jclass,
137 jobject gl_env) {
138 GLEnv* gl_env_ptr = ConvertFromJava<GLEnv>(env, gl_env);
139 ShaderProgram* program = gl_env_ptr ? ShaderProgram::CreateIdentity(gl_env_ptr) : NULL;
140 return program ? WrapNewObjectInJava(program, env, false) : NULL;
141}
142
143jboolean Java_android_filterfw_core_ShaderProgram_setSourceRegion(JNIEnv* env,
144 jobject thiz,
145 jfloat x0,
146 jfloat y0,
147 jfloat x1,
148 jfloat y1,
149 jfloat x2,
150 jfloat y2,
151 jfloat x3,
152 jfloat y3) {
153 ShaderProgram* program = ConvertFromJava<ShaderProgram>(env, thiz);
154 if (program) {
155 program->SetSourceRegion(Quad(Point(x0, y0), Point(x1, y1), Point(x2, y2), Point(x3, y3)));
156 return JNI_TRUE;
157 }
158 return JNI_FALSE;
159}
160
161jboolean Java_android_filterfw_core_ShaderProgram_setTargetRegion(JNIEnv* env,
162 jobject thiz,
163 jfloat x0,
164 jfloat y0,
165 jfloat x1,
166 jfloat y1,
167 jfloat x2,
168 jfloat y2,
169 jfloat x3,
170 jfloat y3) {
171 ShaderProgram* program = ConvertFromJava<ShaderProgram>(env, thiz);
172 if (program) {
173 program->SetTargetRegion(Quad(Point(x0, y0), Point(x1, y1), Point(x2, y2), Point(x3, y3)));
174 return JNI_TRUE;
175 }
176 return JNI_FALSE;
177}
178
179jboolean Java_android_filterfw_core_ShaderProgram_setShaderClearsOutput(JNIEnv* env,
180 jobject thiz,
181 jboolean clears) {
182 ShaderProgram* program = ConvertFromJava<ShaderProgram>(env, thiz);
183 if (program) {
184 program->SetClearsOutput(ToCppBool(clears));
185 return JNI_TRUE;
186 }
187 return JNI_FALSE;
188}
189
190jboolean Java_android_filterfw_core_ShaderProgram_setShaderBlendEnabled(JNIEnv* env,
191 jobject thiz,
192 jboolean enable) {
193 ShaderProgram* program = ConvertFromJava<ShaderProgram>(env, thiz);
194 if (program) {
195 program->SetBlendEnabled(ToCppBool(enable));
196 return JNI_TRUE;
197 }
198 return JNI_FALSE;
199}
200
201jboolean Java_android_filterfw_core_ShaderProgram_setShaderBlendFunc(JNIEnv* env,
202 jobject thiz,
203 jint sfactor,
204 jint dfactor) {
205 ShaderProgram* program = ConvertFromJava<ShaderProgram>(env, thiz);
206 if (program) {
207 program->SetBlendFunc(sfactor, dfactor);
208 return JNI_TRUE;
209 }
210 return JNI_FALSE;
211}
212
213jboolean Java_android_filterfw_core_ShaderProgram_setShaderClearColor(JNIEnv* env,
214 jobject thiz,
215 jfloat r,
216 jfloat g,
217 jfloat b) {
218 ShaderProgram* program = ConvertFromJava<ShaderProgram>(env, thiz);
219 if (program) {
220 program->SetClearColor(r, g, b, 1.0f);
221 return JNI_TRUE;
222 }
223 return JNI_FALSE;
224}
225
226jboolean Java_android_filterfw_core_ShaderProgram_setShaderDrawMode(JNIEnv* env,
227 jobject thiz,
228 jint draw_mode) {
229 ShaderProgram* program = ConvertFromJava<ShaderProgram>(env, thiz);
230 if (program) {
231 program->SetDrawMode(draw_mode);
232 return JNI_TRUE;
233 }
234 return JNI_FALSE;
235}
236
237jboolean Java_android_filterfw_core_ShaderProgram_setShaderTileCounts(JNIEnv* env,
238 jobject thiz,
239 jint x_count,
240 jint y_count) {
241 ShaderProgram* program = ConvertFromJava<ShaderProgram>(env, thiz);
242 if (program) {
243 program->SetTileCounts(x_count, y_count);
244 return JNI_TRUE;
245 }
246 return JNI_FALSE;
247}
248
249jboolean Java_android_filterfw_core_ShaderProgram_setShaderVertexCount(JNIEnv* env,
250 jobject thiz,
251 jint vertex_count) {
252 ShaderProgram* program = ConvertFromJava<ShaderProgram>(env, thiz);
253 if (program) {
254 program->SetVertexCount(vertex_count);
255 return JNI_TRUE;
256 }
257 return JNI_FALSE;
258}
259
260jboolean Java_android_filterfw_core_ShaderProgram_beginShaderDrawing(JNIEnv* env, jobject thiz) {
261 ShaderProgram* program = ConvertFromJava<ShaderProgram>(env, thiz);
262 return ToJBool(program && program->BeginDraw());
263}
264
265jboolean Java_android_filterfw_core_ShaderProgram_setShaderAttributeValues(
266 JNIEnv* env,
267 jobject thiz,
268 jstring attr_name,
269 jfloatArray values,
270 jint component_count) {
271 ShaderProgram* program = ConvertFromJava<ShaderProgram>(env, thiz);
272 if (program) {
273 // Get the floats to set
274 jfloat* float_ptr = env->GetFloatArrayElements(values, NULL);
275 const int length = env->GetArrayLength(values);
276
277 // Get the program variable to set
278 const std::string attr_string = ToCppString(env, attr_name);
279 ProgramVar program_var = program->GetAttribute(attr_string);
280
281 // Set the variable
282 if (float_ptr && ShaderProgram::IsVarValid(program_var)) {
283 const bool success = program->SetAttributeValues(program_var,
284 reinterpret_cast<float*>(float_ptr),
285 length,
286 component_count);
287 env->ReleaseFloatArrayElements(values, float_ptr, JNI_ABORT);
288 return ToJBool(success);
289 }
290 }
291 return JNI_FALSE;
292}
293
294jboolean Java_android_filterfw_core_ShaderProgram_setShaderAttributeVertexFrame(
295 JNIEnv* env,
296 jobject thiz,
297 jstring attr_name,
298 jobject vertex_frame,
299 jint type,
300 jint component_count,
301 jint stride,
302 jint offset,
303 jboolean normalize) {
304 ShaderProgram* program = ConvertFromJava<ShaderProgram>(env, thiz);
305 if (program) {
306 // Get the vertex frame
307 VertexFrame* v_frame = ConvertFromJava<VertexFrame>(env, vertex_frame);
308
309 // Get the program variable to set
310 const std::string attr_string = ToCppString(env, attr_name);
311 ProgramVar program_var = program->GetAttribute(attr_string);
312
313 // Set the variable
314 if (v_frame && ShaderProgram::IsVarValid(program_var)) {
315 const bool success = program->SetAttributeValues(program_var,
316 v_frame,
317 type,
318 component_count,
319 stride,
320 offset,
321 ToCppBool(normalize));
322 return ToJBool(success);
323 }
324 }
325 return JNI_FALSE;
326}