blob: ca0e258f8ec848d817bba58a3ac1ee5cbd612abb [file] [log] [blame]
Vincent Scheibc5114c12010-04-08 08:49:50 -07001// Copyright (c) 2010 The Chromium OS Authors. All rights reserved.
2// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
4
5// Application that displays graphics using OpenGL [ES] with the intent
6// of being used in functional tests.
7
8#include <gflags/gflags.h>
9#include <stdio.h>
10#include <stdlib.h>
11#include <string.h>
12#include <time.h>
13
14#include <cmath>
15
16#include "main.h"
17#include "utils.h"
18
19
Kenneth Watersca03c732010-12-20 12:26:44 -080020#if defined(I915_WORKAROUND)
21#define V1 "gl_TexCoord[0]"
22#else
23#define V1 "v1"
24#endif
25
26
Vincent Scheibc5114c12010-04-08 08:49:50 -070027GLuint GenerateAndBindTexture() {
28 GLuint name = ~0;
29 glGenTextures(1, &name);
30 glBindTexture(GL_TEXTURE_2D, name);
31 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
32 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, GL_LINEAR);
Kenneth Watersca03c732010-12-20 12:26:44 -080033 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP_TO_EDGE);
34 glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, GL_CLAMP_TO_EDGE);
Vincent Scheibc5114c12010-04-08 08:49:50 -070035 return name;
36}
37
38
39unsigned char* CreateBitmap(int w, int h) {
40 unsigned char* bitmap = new unsigned char[w * h];
41 unsigned char* pixel = bitmap;
42 float w2 = w/2.0f;
43 float h2 = h/2.0f;
44 for (int y = 0; y < h; y++) {
45 for (int x = 0; x < w; x++) {
46 // Fill with soft ellipse
47 float dx = fabs((x - w2) / w2);
48 float dy = fabs((y - h2) / h2);
49 float dist2 = dx*dx + dy*dy;
50 if (dist2 > 1.f)
51 dist2 = 1.f;
52 *pixel = (1.f-dist2) * 255.f;
53 pixel++;
54 }
55 }
56 return bitmap;
57}
58
59
60const char kVertexShader[] =
Vincent Scheibdf7d51e2010-05-06 12:34:36 -070061 "attribute vec4 vertices;"
Kenneth Watersca03c732010-12-20 12:26:44 -080062 "varying vec4 v1;"
Vincent Scheibc5114c12010-04-08 08:49:50 -070063 "void main() {"
Vincent Scheibdf7d51e2010-05-06 12:34:36 -070064 " gl_Position = vertices;"
Kenneth Watersca03c732010-12-20 12:26:44 -080065 " " V1 " = vec4(vertices.yx, 0.0, 0.0);"
Vincent Scheibc5114c12010-04-08 08:49:50 -070066 "}";
67
68const char kFragmentShader[] =
69 "uniform sampler2D tex;"
Vincent Scheibdf7d51e2010-05-06 12:34:36 -070070 "uniform vec4 color;"
Kenneth Watersca03c732010-12-20 12:26:44 -080071 "varying vec4 v1;"
Vincent Scheibc5114c12010-04-08 08:49:50 -070072 "void main() {"
Kenneth Watersca03c732010-12-20 12:26:44 -080073 " gl_FragColor = color * texture2D(tex, " V1 ".xy);"
Vincent Scheibc5114c12010-04-08 08:49:50 -070074 "}";
75
Vincent Scheibdf7d51e2010-05-06 12:34:36 -070076// Command line flags
77DEFINE_double(screenshot1_sec, 2.f, "seconds delay before screenshot1_cmd");
78DEFINE_double(screenshot2_sec, 1.f, "seconds delay before screenshot2_cmd");
79DEFINE_string(screenshot1_cmd, "", "system command to take a screen shot 1");
80DEFINE_string(screenshot2_cmd, "", "system command to take a screen shot 2");
81DEFINE_double(cooldown_sec, 1.f, "seconds delay after all screenshots");
Vincent Scheibc5114c12010-04-08 08:49:50 -070082
83int main(int argc, char* argv[]) {
Vincent Scheibdf7d51e2010-05-06 12:34:36 -070084 // Configure full screen
Vincent Scheibc5114c12010-04-08 08:49:50 -070085 g_width = -1;
86 g_height = -1;
Vincent Scheibdf7d51e2010-05-06 12:34:36 -070087
Vincent Scheibc5114c12010-04-08 08:49:50 -070088 google::ParseCommandLineFlags(&argc, &argv, true);
89
90 if (!Init()) {
Ilja H. Friedel8faad302011-04-26 14:40:49 -070091 printf("# Error: Failed to initialize %s.\n", argv[0]);
Vincent Scheibc5114c12010-04-08 08:49:50 -070092 return 1;
93 }
94
95 InitContext();
96 glViewport(-g_width, -g_height, g_width*2, g_height*2);
97
98 unsigned char* bitmap = CreateBitmap(g_height, g_width);
99 GLuint texture = GenerateAndBindTexture();
100 glTexImage2D(GL_TEXTURE_2D, 0, GL_LUMINANCE, g_height, g_width, 0,
101 GL_LUMINANCE, GL_UNSIGNED_BYTE, bitmap);
102
103 GLfloat vertices[8] = {
104 0.f, 0.f,
105 1.f, 0.f,
106 0.f, 1.f,
107 1.f, 1.f,
108 };
109
Alexey Marinichev9f9b8732010-05-20 19:33:44 -0700110 GLuint program = glbench::InitShaderProgram(kVertexShader, kFragmentShader);
Vincent Scheibdf7d51e2010-05-06 12:34:36 -0700111 int attribute_index = glGetAttribLocation(program, "vertices");
Vincent Scheibc5114c12010-04-08 08:49:50 -0700112 glVertexAttribPointer(attribute_index, 2, GL_FLOAT, GL_FALSE, 0, vertices);
113 glEnableVertexAttribArray(attribute_index);
114
115 int texture_sampler = glGetUniformLocation(program, "tex");
Vincent Scheibdf7d51e2010-05-06 12:34:36 -0700116 glUniform1i(texture_sampler, 0);
Vincent Scheibc5114c12010-04-08 08:49:50 -0700117
Vincent Scheibdf7d51e2010-05-06 12:34:36 -0700118 int display_color = glGetUniformLocation(program, "color");
119 float white[4] = {1.0f, 1.0f, 1.0f, 1.0f};
120 float blue[4] = {0.5f, 0.5f, 1.0f, 1.0f};
121
122 uint64_t last_event_time = GetUTime();
123 enum State {
124 kStateScreenShot1,
125 kStateScreenShot2,
126 kStateCooldown,
127 kStateExit
128 } state = kStateScreenShot1;
129 float seconds_delay_for_next_state[] = {
130 FLAGS_screenshot1_sec,
131 FLAGS_screenshot2_sec,
132 FLAGS_cooldown_sec,
133 0
134 };
135
Vincent Scheibc5114c12010-04-08 08:49:50 -0700136 do {
Vincent Scheibdf7d51e2010-05-06 12:34:36 -0700137 // Draw
Vincent Scheibc5114c12010-04-08 08:49:50 -0700138 glClear(GL_COLOR_BUFFER_BIT);
Vincent Scheibdf7d51e2010-05-06 12:34:36 -0700139 if (state == kStateScreenShot1)
140 glUniform4fv(display_color, 1, white);
141 else
142 glUniform4fv(display_color, 1, blue);
Vincent Scheibc5114c12010-04-08 08:49:50 -0700143 glDrawArrays(GL_TRIANGLE_STRIP, 0, 4);
144 SwapBuffers();
Vincent Scheibdf7d51e2010-05-06 12:34:36 -0700145
146 // Loop until next event
147 float seconds_since_last_event =
148 static_cast<float>(GetUTime() - last_event_time) / 1000000ULL;
149 if (seconds_since_last_event < seconds_delay_for_next_state[state])
150 continue;
151
152 // State change. Perform action.
153 switch(state) {
154 case kStateScreenShot1:
155 system(FLAGS_screenshot1_cmd.c_str());
156 break;
157 case kStateScreenShot2:
158 system(FLAGS_screenshot2_cmd.c_str());
159 break;
160 default:
161 break;
162 }
163
164 // Advance to next state
165 last_event_time = GetUTime();
166 state = static_cast<State>(state + 1);
167
168 } while (state != kStateExit);
Vincent Scheibc5114c12010-04-08 08:49:50 -0700169
170 glDeleteTextures(1, &texture);
171 DestroyContext();
172 return 0;
173}