chiark / gitweb /
Merge branch 'master' of github.com:daid/Cura
[cura.git] / Cura / gui / util / openglGui.py
1 from __future__ import absolute_import
2 from __future__ import division
3
4 import wx
5 from wx import glcanvas
6 import OpenGL
7 OpenGL.ERROR_CHECKING = False
8 from OpenGL.GL import *
9
10 from Cura.gui.util import opengl
11
12 glButtonsTexture = None
13
14 class glGuiPanel(glcanvas.GLCanvas):
15         def __init__(self, parent):
16                 attribList = (glcanvas.WX_GL_RGBA, glcanvas.WX_GL_DOUBLEBUFFER, glcanvas.WX_GL_DEPTH_SIZE, 24, glcanvas.WX_GL_STENCIL_SIZE, 8)
17                 glcanvas.GLCanvas.__init__(self, parent, attribList = attribList)
18                 self._parent = parent
19                 self._context = glcanvas.GLContext(self)
20                 self._glGuiControlList = []
21                 self._glButtonsTexture = None
22                 self._buttonSize = 64
23
24                 wx.EVT_PAINT(self, self._OnGuiPaint)
25                 wx.EVT_SIZE(self, self._OnSize)
26                 wx.EVT_ERASE_BACKGROUND(self, self._OnEraseBackground)
27                 wx.EVT_LEFT_DOWN(self, self._OnGuiMouseLeftDown)
28                 wx.EVT_MOTION(self, self._OnGuiMouseMotion)
29
30         def _OnGuiMouseLeftDown(self,e):
31                 for ctrl in self._glGuiControlList:
32                         if ctrl.OnMouseDown(e.GetX(), e.GetY()):
33                                 return
34                 self.OnMouseLeftDown(e)
35
36         def _OnGuiMouseMotion(self,e):
37                 self.Refresh()
38                 for ctrl in self._glGuiControlList:
39                         if ctrl.OnMouseMotion(e.GetX(), e.GetY()):
40                                 return
41                 self.OnMouseMotion(e)
42
43         def _OnGuiPaint(self, e):
44                 dc = wx.PaintDC(self)
45                 self.SetCurrent(self._context)
46                 self.OnPaint(e)
47                 self._drawGui()
48                 glFlush()
49                 self.SwapBuffers()
50
51         def _drawGui(self):
52                 glDisable(GL_DEPTH_TEST)
53                 glEnable(GL_BLEND)
54                 glDisable(GL_LIGHTING)
55                 glColor4ub(255,255,255,255)
56
57                 glMatrixMode(GL_PROJECTION)
58                 glLoadIdentity()
59                 size = self.GetSize()
60                 glOrtho(0, size.GetWidth()-1, size.GetHeight()-1, 0, -1000.0, 1000.0)
61                 glMatrixMode(GL_MODELVIEW)
62                 glLoadIdentity()
63
64                 for glButton in self._glGuiControlList:
65                         glButton.draw()
66
67         def _OnEraseBackground(self,event):
68                 #Workaround for windows background redraw flicker.
69                 pass
70
71         def _OnSize(self,e):
72                 self.Refresh()
73
74         def OnMouseLeftDown(self,e):
75                 pass
76         def OnMouseMotion(self, e):
77                 pass
78         def OnPaint(self, e):
79                 pass
80
81 class glButton(object):
82         def __init__(self, parent, imageID, tooltip, x, y, callback):
83                 self._tooltip = tooltip
84                 self._parent = parent
85                 self._imageID = imageID
86                 self._x = x
87                 self._y = y
88                 self._callback = callback
89                 self._parent._glGuiControlList.append(self)
90                 self._selected = False
91                 self._focus = False
92                 self._hidden = False
93
94         def setSelected(self, value):
95                 self._selected = value
96
97         def setHidden(self, value):
98                 self._hidden = value
99
100         def getSelected(self):
101                 return self._selected
102
103         def _getSize(self):
104                 return self._parent._buttonSize
105
106         def _getPixelPos(self):
107                 bs = self._getSize()
108                 x = self._x * bs * 1.3 + bs * 0.8
109                 y = self._y * bs * 1.3 + bs * 0.8
110                 if self._x < 0:
111                         x = self._parent.GetSize().GetWidth() + x - bs * 0.2
112                 return x, y
113
114         def draw(self):
115                 if self._hidden:
116                         return
117                 if self._parent._glButtonsTexture is None:
118                         self._parent._glButtonsTexture = opengl.loadGLTexture('glButtons.png')
119
120                 cx = (self._imageID % 4) / 4
121                 cy = int(self._imageID / 4) / 4
122                 bs = self._parent._buttonSize
123                 pos = self._getPixelPos()
124
125                 glPushMatrix()
126                 glTranslatef(pos[0], pos[1], 0)
127                 glBindTexture(GL_TEXTURE_2D, self._parent._glButtonsTexture)
128                 glEnable(GL_TEXTURE_2D)
129                 scale = 0.8
130                 if self._selected:
131                         scale = 1.0
132                 elif self._focus:
133                         scale = 0.9
134                 glScalef(bs * scale, bs * scale, bs * scale)
135                 glColor4ub(255,255,255,255)
136                 glBegin(GL_QUADS)
137                 glTexCoord2f(cx+0.25, cy)
138                 glVertex2f( 0.5,-0.5)
139                 glTexCoord2f(cx, cy)
140                 glVertex2f(-0.5,-0.5)
141                 glTexCoord2f(cx, cy+0.25)
142                 glVertex2f(-0.5, 0.5)
143                 glTexCoord2f(cx+0.25, cy+0.25)
144                 glVertex2f( 0.5, 0.5)
145                 glEnd()
146                 glDisable(GL_TEXTURE_2D)
147                 if self._focus:
148                         glColor4ub(0,0,0,255)
149                         glTranslatef(0, -0.55, 0)
150                         opengl.glDrawStringCenter(self._tooltip)
151                 glPopMatrix()
152
153         def _checkHit(self, x, y):
154                 if self._hidden:
155                         return False
156                 bs = self._getSize()
157                 pos = self._getPixelPos()
158                 return -bs * 0.5 <= x - pos[0] <= bs * 0.5 and -bs * 0.5 <= y - pos[1] <= bs * 0.5
159
160         def OnMouseMotion(self, x, y):
161                 if self._checkHit(x, y):
162                         self._focus = True
163                         return True
164                 self._focus = False
165                 return False
166
167         def OnMouseDown(self, x, y):
168                 if self._checkHit(x, y):
169                         self._callback()
170                         return True
171                 return False