1 #pragma once
2 
3 #ifdef WIN32
4 #  include <windows.h>
5 #endif
6 
7 #include <GL/glfw.h>
8 
9 #include <cstdio>
10 #include <cstdlib>
11 #include <iostream>
12 #include <cstring>
13 #include <algorithm>
14 //#include <GL/gl.h>
15 
16 #include "../math3d++/math3d++.h"
17 #include <vector>
18 #include <list>
19 #include <sstream>
20 #include <map>
21 
22 using namespace math3d;
23 
24 using namespace std;
25 
26 typedef pair<string,string> str_pair_t;
27 typedef vector<str_pair_t> vec_str_pair_t;
28 typedef vector<vec2> vec2_ary_t;
29 typedef vector<double> double_ary_t;
30 typedef vector<float> float_ary_t;
31 typedef vector<string> str_ary_t;
32 typedef map<string,string> map_str_str_t;
33 
34 double_ary_t vec2_ary_to_double_ary(vec2_ary_t v2ary);
35 float_ary_t vec2_ary_to_float_ary(vec2_ary_t v2ary);
36 
37 extern float g_max_x;
38 extern float g_max_y;
39 
40 #define FOR_EACH_CONST(_type_,_container_,_name_) \
41 for(_type_::const_iterator _name_ = _container_.begin(),_name_##_end=_container_.end();_name_!=_name_##_end;++_name_)
42 
43 #define FOR_EACH(_type_,_container_,_name_) \
44 for(_type_::iterator _name_ = _container_.begin(),_name_##_end=_container_.end();_name_!=_name_##_end;++_name_)
45 
46 // constrain time to repeated 0..c
47 float get_time_con(float c);
48 float get_time_con_time(float t, float c);
49 
50 void save_texture_as_ppm(GLuint texid,const char *fname);
51 void draw_textured_quad(float size, GLuint texture,bool blend=false);
52 
53 struct Line;
54 void draw_aa_line(Line l,float width = 2.0,vec4 color = vec4(1.0,1.0,1.0,1.0),float stipple=0.0);
55 
56 GLuint move_texture_red_component(GLuint texid);
57 
58 template <class T>
to_string(const T & t)59 string to_string (const T& t)
60 {
61   stringstream ss;
62   ss << t;
63   return ss.str();
64 }
65 
66 template <class T>
from_string(const string & s)67 T from_string (const string& s)
68 {
69   T t;
70   stringstream ss(s);
71   ss >> t;
72   return t;
73 }
74 
75 template <class T>
clamp(const T & val,const T & min,const T & max)76 T clamp(const T& val, const T& min,const T& max)
77 {
78   if(val > max)
79     return max;
80   else if(val < min)
81     return min;
82 
83   return val;
84 }
85 
clamp_0_1(float val)86 static inline float clamp_0_1(float val)
87 {
88   return clamp<float>(val,0.0,1.0);
89 }
90 
91 #define RAND_0_1 ((float)rand()/RAND_MAX)
92 #define RAND_1_1 rand_range(-1.0,1.0)
93 
94 #define LERP(t, a, b) ( a + t * (b - a) )
95 #define INV_LERP(t, a, b) ( (t - a) / (b - a) )
96 
rand_range(float min,float max)97 static inline float rand_range(float min,float max)
98 {
99   return LERP(RAND_0_1,min,max);
100 }
101 
lerp(float t,const vec2 & a,const vec2 & b)102 static inline vec2 lerp(float t,const vec2& a,const vec2& b)
103 {
104   return vec2(
105     LERP(t,a[0],b[0]),
106     LERP(t,a[1],b[1])
107     );
108 }
109 
fade_in(float start_at,float full_at,float t)110 static inline float fade_in(float start_at,float full_at,float t)
111 { return clamp<float>(INV_LERP(t,start_at,full_at),0.0,1.0); }
112 
fade_out(float start_at,float clear_at,float t)113 static inline float fade_out(float start_at,float clear_at,float t)
114 { return 1.0 - fade_in(start_at,clear_at,t); }
115 
fade_in_out(float in_start,float in_end,float out_start,float out_end,float t)116 static inline float fade_in_out(float in_start,float in_end, float out_start, float out_end, float t)
117 {
118   if (t<=in_end)
119     return fade_in(in_start,in_end,t);
120   else
121     return fade_out(out_start,out_end,t);
122 }
123 
124 
125 //
126 class FPScounter
127 {
128   float m_interval;
129   unsigned int m_frames;
130   float m_old_t;
131   float m_fps;
132 public:
133   FPScounter(float interval=1.0);
134 
135   float next_frame(void);
136 };
137 
138 class Gl
139 {
140 public:
141   // supported OGL version
is_available(int major,int minor)142   static bool is_available(int major,int minor)
143   {
144     int glver[3] = {0};
145     glfwGetGLVersion(&glver[0],&glver[1],&glver[2]);
146 
147     if (glver[0]>major || (glver[0]==major && glver[1] >=minor))
148       return true;
149     else
150       return false;
151   }
152 
153   // check for extension support
is_available(const char * extension)154   static bool is_available(const char *extension)
155   {
156     return (glfwExtensionSupported(extension) == GL_TRUE ? true : false);
157   }
158 
159 };
160 
161 class Mouse
162 {
163   float m_x,m_y;
164   int m_last_pos_x,m_last_pos_y;
165   float m_accel;
166 
167 public:
Mouse()168   Mouse() : m_x(g_max_x/2.0), m_y(g_max_y/2.0), m_last_pos_x(0),m_last_pos_y(0)
169   {
170     glfwSetMousePos(0,0);
171     m_accel = 0.001; // 0.01 too fast, 0.001 normal , 0.0001 too slow,
172   }
173 
set_accel(int a)174   void set_accel(int a) // 1..10
175   {
176     float r = ((10.0-a+1.0) / 10.0) * 2.0;
177     float d = pow((float)10.0,r);
178     m_accel = 0.01 / d;
179   }
180 
update(void)181   void update(void)
182   {
183     int pos_x,pos_y;
184     glfwGetMousePos(&pos_x,&pos_y);
185 
186     float delta_x = (float)(m_last_pos_x - pos_x) * m_accel;
187     float delta_y = (float)(m_last_pos_y - pos_y) * m_accel;
188 
189 //    printf("x: %i -> %i, y: %i -> %i\n",m_last_pos_x,pos_x,m_last_pos_y,pos_y);
190 
191     m_last_pos_x = pos_x;
192     m_last_pos_y = pos_y;
193 
194     m_x -= delta_x;
195     m_y -= delta_y;
196 
197     if (m_x<0.0) m_x = 0.0;
198     if (m_x>g_max_x) m_x = g_max_x;
199     if (m_y<0.0) m_y = 0.0;
200     if (m_y>g_max_y) m_y = g_max_y;
201   }
202 
draw(GLuint texture)203   void draw(GLuint texture)
204   {
205     float crosshair_size = 0.04;
206     glPushMatrix();
207     glLoadIdentity();
208     glTranslatef(m_x,m_y,0.0);
209 
210     float t = get_time_con_time(glfwGetTime(), 4.0);
211     float angle = t/4.0 * 360.0;
212     glRotatef(angle,0,0,1);
213     glColor4f(1.0,1.0,1.0,1.0);
214     draw_textured_quad(crosshair_size, texture, true);
215 
216     glPopMatrix();
217   }
218 
get_pos(void)219   vec2 get_pos(void)
220   {
221     return vec2(m_x,m_y);
222   }
223 };
224