rsScriptC_LibGL.cpp revision a04e30dbb5ab11592b03666bb3d102070759c58e
1/*
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 "rsContext.h"
18#include "rsScriptC.h"
19#include "rsMatrix4x4.h"
20#include "rsMatrix3x3.h"
21#include "rsMatrix2x2.h"
22
23#include "utils/Timers.h"
24#include "driver/rsdVertexArray.h"
25#include "driver/rsdShaderCache.h"
26#include "driver/rsdCore.h"
27
28#define GL_GLEXT_PROTOTYPES
29
30#include <GLES/gl.h>
31#include <GLES/glext.h>
32#include <GLES2/gl2.h>
33#include <GLES2/gl2ext.h>
34
35#include <time.h>
36
37using namespace android;
38using namespace android::renderscript;
39
40namespace android {
41namespace renderscript {
42
43//////////////////////////////////////////////////////////////////////////////
44// Context
45//////////////////////////////////////////////////////////////////////////////
46
47void rsrBindTexture(Context *rsc, Script *sc, ProgramFragment *pf, uint32_t slot, Allocation *a) {
48    CHECK_OBJ_OR_NULL(a);
49    CHECK_OBJ(pf);
50    pf->bindTexture(rsc, slot, a);
51}
52
53void rsrBindSampler(Context *rsc, Script *sc, ProgramFragment *pf, uint32_t slot, Sampler *s) {
54    CHECK_OBJ_OR_NULL(vs);
55    CHECK_OBJ(vpf);
56    pf->bindSampler(rsc, slot, s);
57}
58
59void rsrBindProgramStore(Context *rsc, Script *sc, ProgramStore *ps) {
60    CHECK_OBJ_OR_NULL(ps);
61    rsc->setProgramStore(ps);
62}
63
64void rsrBindProgramFragment(Context *rsc, Script *sc, ProgramFragment *pf) {
65    CHECK_OBJ_OR_NULL(pf);
66    rsc->setProgramFragment(pf);
67}
68
69void rsrBindProgramVertex(Context *rsc, Script *sc, ProgramVertex *pv) {
70    CHECK_OBJ_OR_NULL(pv);
71    rsc->setProgramVertex(pv);
72}
73
74void rsrBindProgramRaster(Context *rsc, Script *sc, ProgramRaster *pr) {
75    CHECK_OBJ_OR_NULL(pr);
76    rsc->setProgramRaster(pr);
77}
78
79void rsrBindFrameBufferObjectColorTarget(Context *rsc, Script *sc, Allocation *a, uint32_t slot) {
80    CHECK_OBJ(va);
81    rsc->mFBOCache.bindColorTarget(rsc, a, slot);
82}
83
84void rsrBindFrameBufferObjectDepthTarget(Context *rsc, Script *sc, Allocation *a) {
85    CHECK_OBJ(va);
86    rsc->mFBOCache.bindDepthTarget(rsc, a);
87}
88
89void rsrClearFrameBufferObjectColorTarget(Context *rsc, Script *sc, uint32_t slot) {
90    rsc->mFBOCache.bindColorTarget(rsc, NULL, slot);
91}
92
93void rsrClearFrameBufferObjectDepthTarget(Context *rsc, Script *sc) {
94    rsc->mFBOCache.bindDepthTarget(rsc, NULL);
95}
96
97void rsrClearFrameBufferObjectTargets(Context *rsc, Script *sc) {
98    rsc->mFBOCache.resetAll(rsc);
99}
100
101//////////////////////////////////////////////////////////////////////////////
102// VP
103//////////////////////////////////////////////////////////////////////////////
104
105void rsrVpLoadProjectionMatrix(Context *rsc, Script *sc, const rsc_Matrix *m) {
106    rsc->getProgramVertex()->setProjectionMatrix(rsc, m);
107}
108
109void rsrVpLoadModelMatrix(Context *rsc, Script *sc, const rsc_Matrix *m) {
110    rsc->getProgramVertex()->setModelviewMatrix(rsc, m);
111}
112
113void rsrVpLoadTextureMatrix(Context *rsc, Script *sc, const rsc_Matrix *m) {
114    rsc->getProgramVertex()->setTextureMatrix(rsc, m);
115}
116
117void rsrPfConstantColor(Context *rsc, Script *sc, ProgramFragment *pf,
118                        float r, float g, float b, float a) {
119    CHECK_OBJ(pf);
120    pf->setConstantColor(rsc, r, g, b, a);
121}
122
123void rsrVpGetProjectionMatrix(Context *rsc, Script *sc, rsc_Matrix *m) {
124    rsc->getProgramVertex()->getProjectionMatrix(rsc, m);
125}
126
127//////////////////////////////////////////////////////////////////////////////
128// Drawing
129//////////////////////////////////////////////////////////////////////////////
130
131void rsrDrawQuadTexCoords(Context *rsc, Script *sc,
132                          float x1, float y1, float z1, float u1, float v1,
133                          float x2, float y2, float z2, float u2, float v2,
134                          float x3, float y3, float z3, float u3, float v3,
135                          float x4, float y4, float z4, float u4, float v4) {
136    if (!rsc->setupCheck()) {
137        return;
138    }
139
140    RsdHal *dc = (RsdHal *)rsc->mHal.drv;
141    if (!dc->gl.shaderCache->setup(rsc)) {
142        return;
143    }
144
145    //LOGE("Quad");
146    //LOGE("%4.2f, %4.2f, %4.2f", x1, y1, z1);
147    //LOGE("%4.2f, %4.2f, %4.2f", x2, y2, z2);
148    //LOGE("%4.2f, %4.2f, %4.2f", x3, y3, z3);
149    //LOGE("%4.2f, %4.2f, %4.2f", x4, y4, z4);
150
151    float vtx[] = {x1,y1,z1, x2,y2,z2, x3,y3,z3, x4,y4,z4};
152    const float tex[] = {u1,v1, u2,v2, u3,v3, u4,v4};
153
154    RsdVertexArray::Attrib attribs[2];
155    attribs[0].set(GL_FLOAT, 3, 12, false, (uint32_t)vtx, "ATTRIB_position");
156    attribs[1].set(GL_FLOAT, 2, 8, false, (uint32_t)tex, "ATTRIB_texture0");
157
158    RsdVertexArray va(attribs, 2);
159    va.setupGL2(rsc);
160
161    glDrawArrays(GL_TRIANGLE_FAN, 0, 4);
162}
163
164void rsrDrawQuad(Context *rsc, Script *sc,
165                 float x1, float y1, float z1,
166                 float x2, float y2, float z2,
167                 float x3, float y3, float z3,
168                 float x4, float y4, float z4) {
169    rsrDrawQuadTexCoords(rsc, sc, x1, y1, z1, 0, 1,
170                                  x2, y2, z2, 1, 1,
171                                  x3, y3, z3, 1, 0,
172                                  x4, y4, z4, 0, 0);
173}
174
175void rsrDrawSpriteScreenspace(Context *rsc, Script *sc,
176                              float x, float y, float z, float w, float h) {
177    ObjectBaseRef<const ProgramVertex> tmp(rsc->getProgramVertex());
178    rsc->setProgramVertex(rsc->getDefaultProgramVertex());
179    //rsc->setupCheck();
180
181    //GLint crop[4] = {0, h, w, -h};
182
183    float sh = rsc->getHeight();
184
185    rsrDrawQuad(rsc, sc,
186                x,   sh - y,     z,
187                x+w, sh - y,     z,
188                x+w, sh - (y+h), z,
189                x,   sh - (y+h), z);
190    rsc->setProgramVertex((ProgramVertex *)tmp.get());
191}
192
193void rsrDrawRect(Context *rsc, Script *sc, float x1, float y1, float x2, float y2, float z) {
194    //LOGE("SC_drawRect %f,%f  %f,%f  %f", x1, y1, x2, y2, z);
195    rsrDrawQuad(rsc, sc, x1, y2, z, x2, y2, z, x2, y1, z, x1, y1, z);
196}
197
198void rsrDrawMesh(Context *rsc, Script *sc, Mesh *sm) {
199    CHECK_OBJ(sm);
200    if (!rsc->setupCheck()) {
201        return;
202    }
203    sm->render(rsc);
204}
205
206void rsrDrawMeshPrimitive(Context *rsc, Script *sc, Mesh *sm, uint32_t primIndex) {
207    CHECK_OBJ(sm);
208    if (!rsc->setupCheck()) {
209        return;
210    }
211    sm->renderPrimitive(rsc, primIndex);
212}
213
214void rsrDrawMeshPrimitiveRange(Context *rsc, Script *sc, Mesh *sm, uint32_t primIndex,
215                               uint32_t start, uint32_t len) {
216    CHECK_OBJ(sm);
217    if (!rsc->setupCheck()) {
218        return;
219    }
220    sm->renderPrimitiveRange(rsc, primIndex, start, len);
221}
222
223void rsrMeshComputeBoundingBox(Context *rsc, Script *sc, Mesh *sm,
224                               float *minX, float *minY, float *minZ,
225                               float *maxX, float *maxY, float *maxZ) {
226    CHECK_OBJ(sm);
227    sm->computeBBox();
228    *minX = sm->mBBoxMin[0];
229    *minY = sm->mBBoxMin[1];
230    *minZ = sm->mBBoxMin[2];
231    *maxX = sm->mBBoxMax[0];
232    *maxY = sm->mBBoxMax[1];
233    *maxZ = sm->mBBoxMax[2];
234}
235
236
237//////////////////////////////////////////////////////////////////////////////
238//
239//////////////////////////////////////////////////////////////////////////////
240
241
242void rsrColor(Context *rsc, Script *sc, float r, float g, float b, float a) {
243    ProgramFragment *pf = rsc->getProgramFragment();
244    pf->setConstantColor(rsc, r, g, b, a);
245}
246
247void rsrFinish(Context *rsc, Script *sc) {
248    glFinish();
249}
250
251
252void rsrClearColor(Context *rsc, Script *sc, float r, float g, float b, float a) {
253    rsc->mFBOCache.setupGL2(rsc);
254    rsc->setupProgramStore();
255
256    glClearColor(r, g, b, a);
257    glClear(GL_COLOR_BUFFER_BIT);
258}
259
260void rsrClearDepth(Context *rsc, Script *sc, float v) {
261    rsc->mFBOCache.setupGL2(rsc);
262    rsc->setupProgramStore();
263
264    glClearDepthf(v);
265    glClear(GL_DEPTH_BUFFER_BIT);
266}
267
268uint32_t rsrGetWidth(Context *rsc, Script *sc) {
269    return rsc->getWidth();
270}
271
272uint32_t rsrGetHeight(Context *rsc, Script *sc) {
273    return rsc->getHeight();
274}
275
276void rsrDrawTextAlloc(Context *rsc, Script *sc, Allocation *a, int x, int y) {
277    const char *text = (const char *)a->getPtr();
278    size_t allocSize = a->getType()->getSizeBytes();
279    rsc->mStateFont.renderText(text, allocSize, x, y);
280}
281
282void rsrDrawText(Context *rsc, Script *sc, const char *text, int x, int y) {
283    size_t textLen = strlen(text);
284    rsc->mStateFont.renderText(text, textLen, x, y);
285}
286
287static void SetMetrics(Font::Rect *metrics,
288                       int32_t *left, int32_t *right, int32_t *top, int32_t *bottom) {
289    if (left) {
290        *left = metrics->left;
291    }
292    if (right) {
293        *right = metrics->right;
294    }
295    if (top) {
296        *top = metrics->top;
297    }
298    if (bottom) {
299        *bottom = metrics->bottom;
300    }
301}
302
303void rsrMeasureTextAlloc(Context *rsc, Script *sc, Allocation *a,
304                         int32_t *left, int32_t *right, int32_t *top, int32_t *bottom) {
305    CHECK_OBJ(a);
306    const char *text = (const char *)a->getPtr();
307    size_t textLen = a->getType()->getSizeBytes();
308    Font::Rect metrics;
309    rsc->mStateFont.measureText(text, textLen, &metrics);
310    SetMetrics(&metrics, left, right, top, bottom);
311}
312
313void rsrMeasureText(Context *rsc, Script *sc, const char *text,
314                    int32_t *left, int32_t *right, int32_t *top, int32_t *bottom) {
315    size_t textLen = strlen(text);
316    Font::Rect metrics;
317    rsc->mStateFont.measureText(text, textLen, &metrics);
318    SetMetrics(&metrics, left, right, top, bottom);
319}
320
321void rsrBindFont(Context *rsc, Script *sc, Font *font) {
322    CHECK_OBJ(font);
323    rsi_ContextBindFont(rsc, font);
324}
325
326void rsrFontColor(Context *rsc, Script *sc, float r, float g, float b, float a) {
327    rsc->mStateFont.setFontColor(r, g, b, a);
328}
329
330}
331}
332