4 # Copyright (C) 2010 Stefanos Harhalakis
6 # This file is part of wifieye.
8 # wifieye is free software: you can redistribute it and/or modify
9 # it under the terms of the GNU General Public License as published by
10 # the Free Software Foundation, either version 3 of the License, or
11 # (at your option) any later version.
13 # wifieye is distributed in the hope that it will be useful,
14 # but WITHOUT ANY WARRANTY; without even the implied warranty of
15 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 # GNU General Public License for more details.
18 # You should have received a copy of the GNU General Public License
19 # along with wifieye. If not, see <http://www.gnu.org/licenses/>.
21 # $Id: 0.py 2265 2010-02-21 19:16:26Z v13 $
23 __version__ = "$Id: 0.py 2265 2010-02-21 19:16:26Z v13 $"
28 from hildondesktop import *
34 from portrait import FremantleRotation
36 from xdg.IconTheme import getIconPath
42 # Background surface for icons
46 # Fall-back to default/blue if not found or name==None
47 def getIcon(name, iconsize):
49 idef='tasklaunch_default_application'
51 # If name==None then use the default icon
52 if name==None or name=='':
57 ico=getIconPath(iname, iconsize)
59 # If not found then use the default icon
61 ico=getIconPath(idef, iconsize)
63 ret=gtk.gdk.pixbuf_new_from_file_at_size(ico, iconsize, iconsize)
67 class Icon(gobject.GObject):
68 def __init__(self, isconfig, config):
69 self.__gobject_init__()
71 self.isconfig=isconfig
93 def timePressed(self):
94 """ return how much time a button is pressed """
95 dt=time.time() - self.lastpress
106 self.icon=dt['icon2']
112 return(self.config.iconsize+self.config.iconspace)
114 def setAngle(self, angle):
115 """ Set the angle. Return True if the angle changed or False if it
116 didn't. The caller should invalidate the icon """
118 # The step in degrees
121 angle2=int(angle/step)*step
123 if angle2==self.angle:
128 # The caller should be responsible for redrawing.
129 # If we call invalidate() here there is the risk of having
130 # icons rotate individually using different angles
135 def mkbg(self, t_pressed):
136 """ Create the background of the icon and cache it as a global
137 variable among all icons and widget instances """
140 if iconbg!=None and t_pressed<=0.001:
143 w=self.config.iconsize + self.config.iconspace
144 s=cairo.ImageSurface(cairo.FORMAT_ARGB32, w, w)
146 cr=gtk.gdk.CairoContext(cr0)
148 cr.set_source_rgba(0.1, 0.1, 0.1, 1)
152 if t_pressed>0.001 and \
153 (t_pressed <= self.presstime or self.ispressed):
154 t=1.0 * min(t_pressed, self.presstime) / self.presstime
157 cr.set_source_rgba(0, g, b, 0.7)
159 cr.set_source_rgba(0.3, 0.3, 0.3, 0.7)
163 x3=x + (self.config.iconspace/6)
164 y3=y + (self.config.iconspace/6)
167 w=self.config.iconsize+(self.config.iconspace*2/3)
170 cr.arc(x3+w-r, y3+r, r, pi*1.5, pi*2)
171 cr.arc(x3+w-r, y3+w-r, r, 0, pi*0.5)
172 cr.arc(x3+r, y3+w-r, r, pi*0.5, pi)
173 cr.arc(x3+r, y3+r, r, pi, pi*1.5)
187 """ Return the icon as a surface. Cache it. """
191 w=self.config.iconsize
192 s=cairo.ImageSurface(cairo.FORMAT_ARGB32, w, w)
194 cr=gtk.gdk.CairoContext(cr0)
196 cr.set_source_pixbuf(self.icon, 0, 0)
203 def get_paint_icon(self):
204 """ Return the icon to paint as a surface. The icon is rotated
205 as needed. The result is cached. """
208 if self.timePressed() <= self.presstime or self.ispressed:
215 if not pressed and self.cached_icons.has_key(angle):
216 return(self.cached_icons[angle])
218 w=self.config.iconsize + self.config.iconspace
219 s=cairo.ImageSurface(cairo.FORMAT_ARGB32, w, w)
221 cr=gtk.gdk.CairoContext(cr0)
223 # Paint the background
226 cr.set_source_surface(s2, 0, 0)
230 # If there is no icon then don't do anything more
232 # Get the icon as a surface (get_sicon() will cache the surface)
233 sicon=self.get_sicon()
235 # Width is the iconsize plus the empty border around the icon
236 #w=self.config.iconsize + self.config.iconspace
238 # This is used to locate the center of the surface
241 # This is the delta from the center where icons are drawn
242 dx2=int(self.config.iconsize/2)
246 # A transformation matrix with dx/dy set to point to the center
247 m=cairo.Matrix(1, 0, 0, 1, dx, dx)
249 # Transform degrees to rads
250 rot=-1 * pi * 2 * self.angle / 360
253 cr.set_source_surface(sicon, -dx2, -dx2) # Faster than pixbuf
254 # cr.set_source_pixbuf(icon2, -dx2, -dx2)
260 self.cached_icons[angle]=s
265 def draw(self, cr, x, y):
266 self.draw_queued=False
270 if self.icon==None and not self.isconfig:
274 s=self.get_paint_icon()
275 cr.set_source_surface(s, x, y)
282 def timerPressed(self):
283 # if not self.ispressed:
288 if self.timePressed()>self.presstime:
296 # Double-time: time for pressed and time for not-pressed
297 if time.time() - self.lastpress > self.presstime*2:
300 self.lastpress=time.time()
302 gobject.timeout_add(20, self.timerPressed)
305 dt=time.time() - self.lastpress
308 if dt<=self.presstime:
310 if self.clickcount==1:
312 elif self.clickcount==2:
313 self.emit('double-click')
314 if self.clickcount==3:
315 self.emit('tripple-click')
317 elif dt>self.presstime and dt<2:
318 self.emit('long-press')
323 def setWindow(self, window):
326 def invalidate(self, window=None):
338 self.draw_queued=True
339 w=self.config.iconsize + self.config.iconspace
340 rect=gdk.Rectangle(self.x, self.y, w, w)
341 gdk.Window.invalidate_rect(window, rect, True)
343 gobject.type_register(Icon)
344 signals=['click', 'double-click', 'tripple-click', 'long-press']
346 gobject.signal_new(s, Icon, gobject.SIGNAL_RUN_FIRST,
347 gobject.TYPE_NONE, ())
349 # vim: set ts=8 sts=4 sw=4 noet formatoptions=r ai nocindent: