因此,我目前正在开发一款Android应用程序,该应用程序使用可在Android和iOS上运行的OpenGL ES 2.0本机库。目前,我正在测试两款Android设备。我有一个运行Fire OS 4.5.5.1的Kindle Fire HD 2,可以很好地使用我的应用程序。另一台设备是运行Android 4.4.4的Nexus 4,它将正确运行glClear(GL_COLOR_BUFFER_BIT);
命令(使用不同的清晰颜色进行测试),但它根本不会绘制VBO。
的Manifest.xml:
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="com.buildertrend.gantt"
android:versionCode="1"
android:versionName="1.0">
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"/>
<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE"/>
<uses-feature
android:glEsVersion="0x00020000"
android:required="true" />
<application
android:allowBackup="false"
android:fullBackupContent="false"
android:icon="@mipmap/ic_launcher"
android:label="@string/app_name">
<provider
android:name="android.support.v4.content.FileProvider"
android:authorities="com.buildertrend.gantt.fileprovider"
android:exported="false"
android:grantUriPermissions="true">
<meta-data
android:name="android.support.FILE_PROVIDER_PATHS"
android:resource="@xml/my_paths" />
<grant-uri-permission android:pathPattern="/notes/" /> <!-- FOR GRANTING URI-BASED PERMISSIONS TO SPECIFIC SUB-BRANCHES OF THE PROVIDER -->
</provider>
<activity android:name=".GanttActivity"
android:label="@string/app_name"
android:configChanges="orientation|screenSize">
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
</application>
</manifest>
GanttActivity.java exerpt:
public final class GanttActivity extends Activity {
private GLSurfaceView mSurfaceView;
private GestureDetectorCompat detectorCompat;
private ScaleGestureDetector detectorScale;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
requestWindowFeature(Window.FEATURE_NO_TITLE);
getWindow().setFlags(
WindowManager.LayoutParams.FLAG_FULLSCREEN,
WindowManager.LayoutParams.FLAG_FULLSCREEN);
GLSurfaceView mGLView = new GanttGLSurfaceView(this);
mGLView.setPreserveEGLContextOnPause(true);
setContentView(mGLView);
mSurfaceView = mGLView;
...
}
...
}
GanttGLSurfaceView.java:
final class GanttGLSurfaceView extends GLSurfaceView {
private final GanttRenderer mRenderer;
public GanttGLSurfaceView(Context context) {
super(context);
mRenderer = new GanttRenderer(context);
setEGLContextClientVersion(2);
setEGLConfigChooser(8, 8, 8, 8, 16, 0);
setRenderer(mRenderer);
}
...
}
GanttRenderer:
final class GanttRenderer implements GLSurfaceView.Renderer {
private final Context appContext;
private boolean initialized;
private String fontPath;
public GanttRenderer(Context context) {
appContext = context;
}
public void onSurfaceCreated(GL10 gl, EGLConfig config) {
File f = new File(appContext.getFilesDir(), "Arial.ttf");
if (!f.exists()) {
AssetManager assets = appContext.getAssets();
try {
copy(assets.open("Arial.ttf"), f);
} catch (IOException e) {
Log.e("FileProvider", "Exception copying from assets", e);
}
}
fontPath = f.getAbsolutePath();
}
public void onSurfaceChanged(GL10 gl, int w, int h) {
nativeResize(w, h);
}
public void onDrawFrame(GL10 gl) {
if (!initialized) {
nativeInit(fontPath, appContext.getResources().getDisplayMetrics().densityDpi,
appContext.getResources().getDisplayMetrics().density);
initialized = true;
}
nativeRender();
}
...
}
Gantt.cpp摘录:
void appInit(char* fontPath, GLfloat ppi, GLfloat scale) {
sWindowPpi = ppi;
sWindowScale = scale;
glClearColor(0.0f, 1.0f, 1.0f, 0.0f);
glEnable(GL_CULL_FACE);
glEnable(GL_BLEND);
glEnable(GL_DEPTH_TEST);
glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
generateProjectionMatrix(sWindowWidth, sWindowHeight);
engine = Engine();
shader = Shader();
viewController = ProjectionController();
polygonRenderer = PolygonRenderer();
textRenderer = TextRenderer(std::string(fontPath));
projectFontLowestBearing = textRenderer.prepareSize(
static_cast<int>(projectFontSizePoints * sWindowPpi / 72));
headerFontLowestBearing = textRenderer.prepareSize(
static_cast<int>(headerFontSizePoints * sWindowPpi / 72));
}
void appRender(int tick, GLfloat width, GLfloat height) {
glClear(GL_COLOR_BUFFER_BIT);
glClear(GL_DEPTH_BUFFER_BIT);
if (sWindowRotated) {
generateProjectionMatrix(sWindowWidth, sWindowHeight);
glViewport(0, 0, sWindowWidth, sWindowHeight);
sWindowRotated = 0;
}
if (!initialized) {
shader.initialize();
polygonRenderer.clearPolygons();
textRenderer.clearTexts();
clock_t t9 = clock();
engine.initialize();
clock_t t0 = clock();
timeMetric("Engine finished", t9, t0);
initialized = true;
}
viewController.updateViewMatrix(tick);
CurrentFrameData frame = viewController.getCurrentFrameData();
textRenderer.calculateOffsetMatrices(frame);
polygonRenderer.renderPolygons(frame);
frame.combinedMatrix[14] += 0.1;
frame.combinedMatrix[16+14] += 0.1;
textRenderer.renderTexts(frame);
frame.combinedMatrix[14] -= 0.1;
frame.combinedMatrix[16+14] -= 0.1;
}
PolygonRenderer.cpp摘录:
void PolygonRenderer::addPolygon(std::vector<GLfloat> vertices, int viewGroup) {
GLuint vertexBuffer;
glGenBuffers(1, &vertexBuffer);
glBindBuffer(GL_ARRAY_BUFFER, vertexBuffer);
glBufferData(GL_ARRAY_BUFFER, vertices.size() * sizeof(GLfloat),
vertices.data(), GL_STATIC_DRAW);
polygons.push_back(PolygonRenderObject{vertexBuffer,
(long)vertices.size() / 6, viewGroup});
}
void PolygonRenderer::renderPolygons(CurrentFrameData frame) {
glUseProgram(shader.get(0));
GLuint projectionLocation =
glGetUniformLocation(shader.get(0), "projection");
glUniformMatrix4fv(projectionLocation, 1, GL_FALSE, projectionMatrix);
GLuint viewLocation = glGetUniformLocation(shader.get(0), "view");
glBindAttribLocation(shader.get(0), 0, "vertexPosition");
glBindAttribLocation(shader.get(0), 1, "color");
glEnableVertexAttribArray(0);
glEnableVertexAttribArray(1);
std::vector<PolygonRenderObject>::iterator it;
for (it = polygons.begin(); it != polygons.end(); it++) {
glUniformMatrix4fv(viewLocation, 1, GL_FALSE,
&frame.combinedMatrix[16 * it->ViewGroup]);
glBindBuffer(GL_ARRAY_BUFFER, it->Buffer);
glVertexAttribPointer(0, 3, GL_FLOAT, GL_FALSE, 6 * sizeof(GLfloat), 0);
glBindBuffer(GL_ARRAY_BUFFER, it->Buffer);
glVertexAttribPointer(1, 3, GL_FLOAT, GL_FALSE, 6 * sizeof(GLfloat),
(GLvoid*)(3 * sizeof(GLfloat)));
glDrawArrays(GL_TRIANGLES, 0, (int)it->VertexCount);
}
glDisableVertexAttribArray(0);
glDisableVertexAttribArray(1);
// Clean up
glBindTexture(GL_TEXTURE_2D, 0);
}
shaders.get(0)
的着色器源:
std::string noTextureVertex =
"attribute vec3 vertexPosition; \n"
"attribute vec3 color; \n"
"varying vec3 fragmentColor; \n"
"uniform mat4 projection; \n"
"uniform mat4 view; \n"
"void main(){ \n"
" gl_Position = projection * view * vec4(vertexPosition, 1); \n"
" fragmentColor = color; \n"
"}";
std::string noTextureFragment =
"precision mediump float; \n"
"varying vec3 fragmentColor; \n"
"void main(){ \n"
" gl_FragColor = vec4(fragmentColor, 1.0); \n"
"}";
修改:已添加glBindAttribLocation