1 //
2 // Copyright (c) 2013 Mikko Mononen memon@inside.org
3 //
4 // This software is provided 'as-is', without any express or implied
5 // warranty.  In no event will the authors be held liable for any damages
6 // arising from the use of this software.
7 // Permission is granted to anyone to use this software for any purpose,
8 // including commercial applications, and to alter it and redistribute it
9 // freely, subject to the following restrictions:
10 // 1. The origin of this software must not be misrepresented; you must not
11 //    claim that you wrote the original software. If you use this software
12 //    in a product, an acknowledgment in the product documentation would be
13 //    appreciated but is not required.
14 // 2. Altered source versions must be plainly marked as such, and must not be
15 //    misrepresented as being the original software.
16 // 3. This notice may not be removed or altered from any source distribution.
17 //
18 
19 #include <stdio.h>
20 #define GLFW_INCLUDE_ES3
21 #define GLFW_INCLUDE_GLEXT
22 #include <GLFW/glfw3.h>
23 #include "nanovg.h"
24 #define NANOVG_GLES3_IMPLEMENTATION
25 #include "nanovg_gl.h"
26 #include "nanovg_gl_utils.h"
27 #include "demo.h"
28 #include "perf.h"
29 
30 
errorcb(int error,const char * desc)31 void errorcb(int error, const char* desc)
32 {
33 	printf("GLFW error %d: %s\n", error, desc);
34 }
35 
36 int blowup = 0;
37 int screenshot = 0;
38 int premult = 0;
39 
key(GLFWwindow * window,int key,int scancode,int action,int mods)40 static void key(GLFWwindow* window, int key, int scancode, int action, int mods)
41 {
42 	NVG_NOTUSED(scancode);
43 	NVG_NOTUSED(mods);
44 	if (key == GLFW_KEY_ESCAPE && action == GLFW_PRESS)
45 		glfwSetWindowShouldClose(window, GL_TRUE);
46 	if (key == GLFW_KEY_SPACE && action == GLFW_PRESS)
47 		blowup = !blowup;
48 	if (key == GLFW_KEY_S && action == GLFW_PRESS)
49 		screenshot = 1;
50 	if (key == GLFW_KEY_P && action == GLFW_PRESS)
51 		premult = !premult;
52 }
53 
main()54 int main()
55 {
56 	GLFWwindow* window;
57 	DemoData data;
58 	NVGcontext* vg = NULL;
59 	PerfGraph fps;
60 	double prevt = 0;
61 
62 	if (!glfwInit()) {
63 		printf("Failed to init GLFW.");
64 		return -1;
65 	}
66 
67 	initGraph(&fps, GRAPH_RENDER_FPS, "Frame Time");
68 
69 	glfwSetErrorCallback(errorcb);
70 
71 	glfwWindowHint(GLFW_CLIENT_API, GLFW_OPENGL_ES_API);
72 	glfwWindowHint(GLFW_CONTEXT_VERSION_MAJOR, 3);
73 	glfwWindowHint(GLFW_CONTEXT_VERSION_MINOR, 0);
74 
75 	window = glfwCreateWindow(1000, 600, "NanoVG", NULL, NULL);
76 //	window = glfwCreateWindow(1000, 600, "NanoVG", glfwGetPrimaryMonitor(), NULL);
77 	if (!window) {
78 		glfwTerminate();
79 		return -1;
80 	}
81 
82 	glfwSetKeyCallback(window, key);
83 
84 	glfwMakeContextCurrent(window);
85 
86 	vg = nvgCreateGLES3(NVG_ANTIALIAS | NVG_STENCIL_STROKES | NVG_DEBUG);
87 	if (vg == NULL) {
88 		printf("Could not init nanovg.\n");
89 		return -1;
90 	}
91 
92 	if (loadDemoData(vg, &data) == -1)
93 		return -1;
94 
95 	glfwSwapInterval(0);
96 
97 	glfwSetTime(0);
98 	prevt = glfwGetTime();
99 
100 	while (!glfwWindowShouldClose(window))
101 	{
102 		double mx, my, t, dt;
103 		int winWidth, winHeight;
104 		int fbWidth, fbHeight;
105 		float pxRatio;
106 
107 		t = glfwGetTime();
108 		dt = t - prevt;
109 		prevt = t;
110 		updateGraph(&fps, dt);
111 
112 		glfwGetCursorPos(window, &mx, &my);
113 		glfwGetWindowSize(window, &winWidth, &winHeight);
114 		glfwGetFramebufferSize(window, &fbWidth, &fbHeight);
115 		// Calculate pixel ration for hi-dpi devices.
116 		pxRatio = (float)fbWidth / (float)winWidth;
117 
118 		// Update and render
119 		glViewport(0, 0, fbWidth, fbHeight);
120 		if (premult)
121 			glClearColor(0,0,0,0);
122 		else
123 			glClearColor(0.3f, 0.3f, 0.32f, 1.0f);
124 		glClear(GL_COLOR_BUFFER_BIT|GL_DEPTH_BUFFER_BIT|GL_STENCIL_BUFFER_BIT);
125 
126 		glEnable(GL_BLEND);
127 		glBlendFunc(GL_SRC_ALPHA, GL_ONE_MINUS_SRC_ALPHA);
128 		glEnable(GL_CULL_FACE);
129 		glDisable(GL_DEPTH_TEST);
130 
131 		nvgBeginFrame(vg, winWidth, winHeight, pxRatio);
132 
133 		renderDemo(vg, mx,my, winWidth,winHeight, t, blowup, &data);
134 		renderGraph(vg, 5,5, &fps);
135 
136 		nvgEndFrame(vg);
137 
138 		glEnable(GL_DEPTH_TEST);
139 
140 		if (screenshot) {
141 			screenshot = 0;
142 			saveScreenShot(fbWidth, fbHeight, premult, "dump.png");
143 		}
144 
145 		glfwSwapBuffers(window);
146 		glfwPollEvents();
147 	}
148 
149 	freeDemoData(vg, &data);
150 
151 	nvgDeleteGLES3(vg);
152 
153 	glfwTerminate();
154 	return 0;
155 }
156