Web   ·   Wiki   ·   Activities   ·   Blog   ·   Lists   ·   Chat   ·   Meeting   ·   Bugs   ·   Git   ·   Translate   ·   Archive   ·   People   ·   Donate
summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorjmpc <jumapico@gmail.com>2009-10-28 04:37:58 (GMT)
committer jmpc <jumapico@gmail.com>2009-10-28 04:37:58 (GMT)
commit556cdf2d27560b6b9aeb4dac0f98ad8da2a937c0 (patch)
tree13b8c721085755b38d9ab62f6a99dca195725f1b
parentcbfcad25c0d47b7e3f1279308ab0a599ab7a134d (diff)
Agregados los eventos de expose y button_press al widget Cake.escalable
-rwxr-xr-xcake.py135
1 files changed, 76 insertions, 59 deletions
diff --git a/cake.py b/cake.py
index b68db41..f2e14a3 100755
--- a/cake.py
+++ b/cake.py
@@ -12,95 +12,117 @@ import gtk
import cairo
+WIDTH = 500
+HEIGHT = 500
+RADIUS = 220
WRADIUS = 0.44
-def draw_grid(context, N):
- context.set_source_rgb(0, 0, 0)
- context.arc(250, 250, 500*WRADIUS, 0, 2 * math.pi)
- context.stroke()
- for i in xrange(N):
- angle = 2 * math.pi * i / N
- context.move_to(250, 250)
- context.line_to(
- 250 + 500*WRADIUS*math.cos(angle),
- 250 + 500*WRADIUS*math.sin(angle)
- )
- context.stroke()
-
-
-def mask_image(context, selected, image):
- context.set_source_surface(image, 0, 0)
- context.paint()
-
-
class Cake(gtk.DrawingArea):
+ """Widget que dibuja una torta y permite seleccionar trozos de ella"""
+
def __init__(self, N):
gtk.DrawingArea.__init__(self)
self.connect("expose_event", self.expose)
- #self.N = N
- #self.selected = N * [0]
- self.N = 5
- self.selected = [0, 0, 1, 1, 1]
+ self.connect("button_press_event", self.button_press)
+ # Los eventos del raton no estan activados para el DrawingArea
+ self.add_events(gtk.gdk.BUTTON_PRESS_MASK)
+ self.N = N
+ self.selected = N * [0]
def expose(self, widget, event):
+ """Manejador del evento expose_event"""
context = widget.window.cairo_create()
- # set a clip region for the expose event
+ # Elegimos solo la region expuesta al evento
context.rectangle(event.area.x, event.area.y, event.area.width, event.area.height)
context.clip()
- self.draw_image(context)
- return False
+ self.draw(context)
+ def button_press(self, widget, event):
+ """Manejador del evento button_press_event"""
+ x, y = event.get_coords()
+ if self.select(x, y):
+ self.draw(widget.window.cairo_create())
+
+
def draw(self, context):
- rect = self.get_allocation()
- x = rect.x + rect.width / 2
- y = rect.y + rect.height / 2
- radius = min(rect.width / 2, rect.height / 2) - 5
- context.arc(x, y, radius, 0, 2 * math.pi)
- context.set_source_rgb(1, 1, 1)
- context.fill_preserve()
- context.set_source_rgb(0, 0, 0)
- context.stroke()
-
-
- def draw_image(self, context):
- # Load images
+ """Dibuja el contenido del widget"""
+
+ def draw_grid(context, N):
+ """Dibuja la rejilla de la torta y sus subdivisiones"""
+ context.set_source_rgb(0, 0, 0)
+ context.arc(WIDTH/2, HEIGHT/2, RADIUS, 0, 2 * math.pi)
+ context.stroke()
+ for i in xrange(N):
+ angle = 2 * math.pi * i / N
+ context.move_to(WIDTH/2, HEIGHT/2)
+ context.line_to(
+ WIDTH/2 + RADIUS*math.cos(angle),
+ HEIGHT/2 + RADIUS*math.sin(angle)
+ )
+ context.stroke()
+
+
+ def mask_image(context, selected, image):
+ """Enmascara la imagen de la torta y dibuja solo los trozos que no
+ fueron seleccionados
+ """
+ N = len(selected)
+ image_ctx = cairo.Context(image)
+ image_ctx.set_operator(cairo.OPERATOR_CLEAR)
+ for sector in xrange(N):
+ if selected[sector]:
+ angle_start = 2 * math.pi * sector / N
+ angle_end = 2 * math.pi * (sector + 1) / N
+ image_ctx.move_to(WIDTH/2, HEIGHT/2)
+ image_ctx.line_to(
+ WIDTH/2 + RADIUS*math.cos(angle_start),
+ HEIGHT/2 + RADIUS*math.sin(angle_start)
+ )
+ image_ctx.arc(WIDTH/2, HEIGHT/2, RADIUS, angle_start,
+ angle_end)
+ image_ctx.close_path()
+ image_ctx.fill()
+ context.set_source_surface(image)
+ context.paint()
+
+
+ # Carga imagenes
image_bg = cairo.ImageSurface.create_from_png("bg.png")
image_fg = cairo.ImageSurface.create_from_png("fg.png")
- # Scale the surface
+ # Escala la imagen al tamaƱo de la superficie
rect = self.get_allocation()
context.save()
context.scale(
- #float(rect.width) / float(image.get_width()),
- #float(rect.height) / float(image.get_height())
- rect.width / 500.0,
- rect.height / 500.0,
+ float(rect.width) / WIDTH,
+ float(rect.height) / HEIGHT
)
- # Draw the background
+ # Dibuja el fondo
context.set_source_surface(image_bg, 0, 0)
context.paint()
- # Draw the foreground
+ # Dibuja el frente
mask_image(context, self.selected, image_fg)
- # Draw the grid
+ # Dibuja la rejilla
draw_grid(context, self.N)
context.restore()
def select(self, ux, uy):
- """
- Si x, y esta dentro de la torta cambiamos el sector.
-
- """
- # Transformamos las coordenadas del usuario al rango 0.0, 1.0.
+ """Selecciona un trozo de la torta. Devuelve True si un objeto fue
+ seleccionado, False en caso contrario."""
+ # Transformamos las coordenadas del usuario a coordenadas reales (0-1)
rect = self.get_allocation()
wx = float(ux - rect.x) / float(rect.width)
wy = float(uy - rect.y) / float(rect.height)
+ # Centramos
+ wx -= 0.5
+ wy -= 0.5
if math.pow(wx, 2) + math.pow(wy, 2) > math.pow(WRADIUS, 2):
return False
angle = math.atan2(wy, wx)
@@ -112,16 +134,11 @@ class Cake(gtk.DrawingArea):
return True
-def main():
+if __name__ == "__main__":
+ # Probamos el nuevo widget Cake
window = gtk.Window()
cake = Cake(6)
-
window.add(cake)
window.connect("destroy", gtk.main_quit)
window.show_all()
-
gtk.main()
-
-
-if __name__ == "__main__":
- main()