이전에 설명한 이미지 파일을 보여주는 부분을 활용하여 작은 아이콘 이미지 를 배경 위에 표시하고 이 아이콘을 마우스로 움직이도록 하는 간단한 코드를 작성해 보도록 하겠습니다.
GooCanvasItem 은 마우스 이벤트를 처리할 수 있는 singal 이 연결되어 있습니다. 이중 “motion_notify_event”, “button_press_event”, “button_release_event” 를 이용하면 됩니다.
static gboolean dragging = FALSE; static double drag_x, drag_y; static gboolean on_motion_notify (GooCanvasItem *item, GooCanvasItem *target, GdkEventMotion *event, gpointer data) { if (dragging && GDK_BUTTON1_MASK) { double new_x = event->x; double new_y = event->y; goo_canvas_item_translate (item, new_x - drag_x, new_y - drag_y); } return 0; } static gboolean on_button_press (GooCanvasItem *item, GooCanvasItem *target, GdkEventButton *event, gpointer data) { GooCanvas *canvas; GdkCursor *fleur; canvas = goo_canvas_item_get_canvas (item); switch (event->button) { case 1: if (event->state & GDK_SHIFT_MASK) break; else { drag_x = event->x; drag_y = event->y; fleur = gdk_cursor_new (GDK_FLEUR); goo_canvas_pointer_grab (canvas, item, GDK_POINTER_MOTION_MASK | GDK_BUTTON_RELEASE_MASK, fleur, event->time); gdk_cursor_unref (fleur); dragging = TRUE; } break; case 2: goo_canvas_item_lower (item, NULL); break; case 3: goo_canvas_item_raise (item, NULL); break; default: break; } return TRUE; } static gboolean on_button_release (GooCanvasItem *item, GooCanvasItem *target, GdkEventButton *event, gpointer data) { GooCanvas *canvas; canvas = goo_canvas_item_get_canvas (item); goo_canvas_pointer_ungrab (canvas, item, event->time); dragging = FALSE; return TRUE; } int main (int argc, char *argv[]) { ... icon_pixbuf = gdk_pixbuf_new_from_file ("icon.png", &err); icon_item = goo_canvas_image_new (root, icon_pixbuf, -16, -16, NULL); goo_canvas_item_set_simple_transform (icon_item, 400, 400, 1, 0); goo_canvas_item_animate (icon2_item, 0, 0, 2, 0, FALSE, 400, 40, GOO_CANVAS_ANIMATE_BOUNCE); g_signal_connect (icon_item, "motion_notify_event", G_CALLBACK (on_motion_notify), NULL); g_signal_connect (icon_item, "button_press_event", G_CALLBACK (on_button_press), NULL); g_signal_connect (icon_item, "button_release_event", G_CALLBACK (on_button_release), NULL); ... }
이벤트 효과를 주기 위해서는 주의 해야할 점이 있습니다. 에니메이션 함수의 옵션중 Item 의 크기를 변경하는 옵션이 존재하는데 이 경우 크기가 점점 변하면서 이 Item 의 크기만 변하지 않고 cairo_surface까지 함께 크기가 변합니다. 따라서 위와 같이 이미지 위젯 생성시 (0,0) 위치를 기준이 실제 Item의 중간이 되도록 지정해 주지 않으면 크기가 변경되면서 Item의 위치도 함께 변경이 됩니다.

This work, unless otherwise expressly stated, is licensed under a Creative Commons Attribution-Noncommercial-No Derivative Works 2.0 Korea License.