2012-09-19 2 views
0

gtk + 카이로 도면 영역 안에 선 (실제로는 사인파)을 그려보고 싶습니다.하지만 그렇게 할 방법을 찾을 수는 없습니다. 그래서 내 코드는 드로잉 영역을 정의합니다. 드로잉 영역은 드로잉 영역 자체에 흰색 배경을 그려주는 함수를 콜백합니다.이 시점에서 START 버튼을 누를 때마다 sin 파를 그리기 시작합니다. 버튼이 눌러졌습니다 (버튼에 드로잉 기능에 대한 콜백이 있습니다). 그래서 우선 ... 할 수 있을까요? 감사합니다. .GTK + 그리기 영역을 그리는 방법

#include <cairo.h> 
    #include <gtk/gtk.h> 

    int x = 0; 
    int x_old = 0; 
    float value = 0; 
    float value_old = 0; 
    GtkWidget *button = NULL; 
    GtkWidget *window = NULL; 
    GtkWidget *area = NULL; 
    GtkWidget *table = NULL; 

    static gboolean load_interface(GtkWidget *widget) 
    { 
    cairo_t *cr; 
    cr = gdk_cairo_create(area->window); 
    cairo_set_source_rgb(cr, 1, 1, 1); 
    cairo_rectangle(cr, 0, 0, 900, 400); 
    cairo_fill(cr); 
    } 

    void draw(GtkWidget *widget) 
    { 
    cairo_t *cr; 
    cr = gdk_cairo_create(widget->window); 

    x_old = x; 
    x = x + 15; 
    value_old = value; 
    value = value + 0.25; 

    cairo_set_source_rgb(cr, 0, 0, 0); 
    cairo_set_line_width (cr, 1); 
    cairo_move_to(cr, x_old, 100 + (sin(value_old))*50); 
    cairo_line_to(cr, x, 100 + (sin(value))*50); 
    cairo_stroke(cr); 
    } 


    int main (int argc, char *argv[]) 
    { 
     g_log_set_handler ("Gtk", G_LOG_LEVEL_WARNING, (GLogFunc) gtk_false, NULL); 
     gtk_init (&argc, &argv); 
     g_log_set_handler ("Gtk", G_LOG_LEVEL_WARNING, g_log_default_handler, NULL); 

     window = gtk_window_new (GTK_WINDOW_TOPLEVEL); 
     gtk_container_set_border_width (GTK_CONTAINER (window), 3); 
     gtk_window_set_title (GTK_WINDOW (window), "Draw"); 
     gtk_window_set_position (GTK_WINDOW (window), GTK_WIN_POS_CENTER); 
     gtk_widget_realize (window); 
     g_signal_connect (window, "destroy", gtk_main_quit, NULL); 

     table = gtk_table_new (10, 10, TRUE); 
     gtk_table_set_col_spacings(GTK_TABLE(table),10); 
     gtk_table_set_row_spacings(GTK_TABLE(table),5); 
     gtk_container_add (GTK_CONTAINER (window), table); 

     area = gtk_drawing_area_new(); 
     gtk_signal_connect (GTK_OBJECT(area), "event", G_CALLBACK (load_interface),  (gpointer)area); 
     gtk_table_attach_defaults (GTK_TABLE(table), area, 1, 10, 0, 10); 

     button = gtk_button_new_from_stock ("START"); 
     g_signal_connect (G_OBJECT (button), "clicked", G_CALLBACK (draw), (gpointer) window); 
     gtk_table_attach_defaults (GTK_TABLE(table), button, 0, 1, 0, 1); 

     gtk_widget_show_all (window); 
     gtk_main(); 

     return 0; 
    } 
+1

GTK2 또는 GTK3을 사용하고 있습니까? GTK2로 보이지만 잘 모르겠습니다. – liberforce

+0

예 Windows에서 GTK2를 사용하고 있습니다 ... – STiLLeN

답변

5

모든 드로잉은 GTK2의 경우 expose-event이고 GTK3의 경우 draw이라고하는 드로잉 영역 드로잉 이벤트에서 발생해야합니다. 버튼을 클릭 한 것에 대한 응답으로, 그려진 전체 장면을 계산하기 위해 재사용 할 일부 값만 변경하면됩니다. 이 값을 변경하면 도면 영역을 무효화하여 도면 영역에 gtk_widget_queue_draw을 호출하여 다시 그려야합니다. 그리고 그게 다야.

장면을 그리는 데 비용이 많이 드는 경우 cairo 클리핑 함수를 사용하여 변경된 내용 만 그리면 성능이 향상됩니다. 변경된 영역과 다시 그려야 할 영역에 대한 힌트를주기 위해 gtk_widget_queue_draw 대신 gtk_widget_queue_draw_area을 사용하십시오. 을 참조하십시오

현재로서는 GTK_OBJECT (사용되지 않음)으로 캐스트를 사용하지 말고 G_OBJECT을 대신 사용하십시오. 이것은 GTK3 로의 포팅을 더 쉽게 만든다.

관련 문제