Cairo 图形指南5形状与填充文档格式.docx
《Cairo 图形指南5形状与填充文档格式.docx》由会员分享,可在线阅读,更多相关《Cairo 图形指南5形状与填充文档格式.docx(16页珍藏版)》请在冰点文库上搜索。
window);
cairo_set_source_rgb(cr,0,0,0);
cairo_set_line_width(cr,1);
cairo_rectangle(cr,20,20,120,80);
cairo_rectangle(cr,180,20,80,80);
cairo_stroke_preserve(cr);
cairo_set_source_rgb(cr,1,1,1);
cairo_fill(cr);
cairo_arc(cr,330,60,40,0,2*M_PI);
cairo_arc(cr,90,160,40,M_PI/4,M_PI);
cairo_close_path(cr);
cairo_translate(cr,220,180);
cairo_scale(cr,1,0.7);
cairo_arc(cr,0,0,50,0,2*M_PI);
cairo_destroy(cr);
returnFALSE;
}
int
main(intargc,char*argv[])
GtkWidget*window;
GtkWidget*darea;
gtk_init(&
argc,&
argv);
window=gtk_window_new(GTK_WINDOW_TOPLEVEL);
darea=gtk_drawing_area_new();
gtk_container_add(GTK_CONTAINER(window),darea);
g_signal_connect(darea,"
expose-event"
G_CALLBACK(on_expose_event),NULL);
g_signal_connect(window,"
destroy"
G_CALLBACK(gtk_main_quit),NULL);
gtk_window_set_position(GTK_WINDOW(window),
GTK_WIN_POS_CENTER);
gtk_window_set_default_size(GTK_WINDOW(window),390,240);
gtk_widget_show_all(window);
gtk_main();
return0;
这个示例,绘制了矩形、正方形、圆、圆弧和椭圆。
下面对关键代码简单分析:
绘制矩形与正方形。
正方形在cairo中是矩形的一种特例。
画了一个圆,圆心为(330,60)px,半径为40px。
Cairo所谓的圆,其实是起始角为0度,终止角为360度的弧线。
画椭圆的方法也与画圆类似,只是需要先设定长轴与短轴的比例,在本例中为1:
0.7。
复杂的图形
复杂的图形是由简单的图形拼凑出来的,譬如下面这个绘制圆角矩形的程序。
staticvoid
draw_round_rectangle(cairo_t*cr,
doublex,doubley,
doublewidth,doubleheight,doubler)
cairo_move_to(cr,x+r,y);
cairo_line_to(cr,x+width-r,y);
cairo_move_to(cr,x+width,y+r);
cairo_line_to(cr,x+width,y+height-r);
cairo_move_to(cr,x+width-r,y+height);
cairo_line_to(cr,x+r,y+height);
cairo_move_to(cr,x,y+height-r);
cairo_line_to(cr,x,y+r);
cairo_arc(cr,x+r,y+r,r,M_PI,3*M_PI/2.0);
cairo_arc(cr,x+width-r,y+r,r,3*M_PI/2,2*M_PI);
cairo_arc(cr,x+width-r,y+height-r,r,0,M_PI/2);
cairo_arc(cr,x+r,y+height-r,r,M_PI/2,M_PI);
intwidth,height;
doublew,h,x,y,r;
gtk_window_get_size(GTK_WINDOW(widget),&
width,&
height);
x=width/5.0;
y=height/5.0;
w=3*width/5.0;
h=3*height/5.0;
r=h/4.0;
cairo_set_source_rgb(cr,0.8,0.4,0);
cairo_set_line_width(cr,6);
draw_round_rectangle(cr,x,y,w,h,r);
cairo_set_source_rgb(cr,0.8,0.8,0.2);
g_print("
test\n"
);
on_configure_event(GtkWidget*widget,
GdkEventConfigure*event,gpointerdata)
gdk_window_invalidate_rect(widget->
window,
&
widget->
allocation,
FALSE);
g_signal_connect(G_OBJECT(window),"
configure-event"
G_CALLBACK(on_configure_event),NULL);
gtk_window_set_default_size(GTK_WINDOW(window),400,300);
gtk_widget_set_app_paintable(window,TRUE);
注:
因为"
Thecairographicstutorial"
在这一部分所提供的示例程序不具代表性,因此写了这个程序。
该示例程序绘制了一个可跟随窗口尺寸进行缩放变化的圆角矩形。
自定义的draw_round_rectangle()函数利用Cairo提供的基本图元函数,利用直线段与圆弧拼凑出圆角矩形。
on_configure_event()函数用于响应窗口尺寸变化事件,在其中调用gdk_window_invalidate_rect()函数让窗口绘图区域失效,并产生窗口重绘制事件(即expose事件)。
填充(Fill)
虽然上一篇已经讲述了一些有关填充的知识,但这里所讲述的内容是与形状相关的。
填充可分为三种类型:
纯色、图案、渐变。
纯色(Solidcolor)
对象的颜色是采用红(R)、绿(G)、蓝(B)三原色描述的,Cairo的RGB取值是从0到1的双精浮点数。
cairo_set_source_rgb(cr,0.5,0.5,1);
cairo_rectangle(cr,20,20,100,100);
cairo_set_source_rgb(cr,0.6,0.6,0.6);
cairo_rectangle(cr,150,20,100,100);
cairo_set_source_rgb(cr,0,0.3,0);
cairo_rectangle(cr,20,140,100,100);
cairo_set_source_rgb(cr,1,0,0.5);
cairo_rectangle(cr,150,140,100,100);
g_signal_connect(G_OBJECT(window),"
gtk_window_set_default_size(GTK_WINDOW(window),270,260);
gtk_window_set_title(GTK_WINDOW(window),"
colors"
该示例绘制了4个正方形,分别采用四种不同颜色进行填充。
这个例子,由于很简单,就不再像原作者那样自作多情的分析了。
图案(Pattern)
所谓图案填充,就是将图片填充到形状内部。
cairo_surface_t*surface1;
cairo_surface_t*surface2;
cairo_surface_t*surface3;
cairo_surface_t*surface4;
create_surfaces()
surface1=cairo_image_surface_create_from_png("
blueweb.png"
surface2=cairo_image_surface_create_from_png("
maple.png"
surface3=cairo_image_surface_create_from_png("
crack.png"
surface4=
cairo_image_surface_create_from_png("
chocolate.png"
destroy_surfaces()
destroyingsurfaces"
cairo_surface_destroy(surface1);
cairo_surface_destroy(surface2);
cairo_surface_destroy(surface3);
cairo_surface_destroy(surface4);
cairo_pattern_t*pattern1;
cairo_pattern_t*pattern2;
cairo_pattern_t*pattern3;
cairo_pattern_t*pattern4;
pattern1=cairo_pattern_create_for_surface(surface1);
pattern2=cairo_pattern_create_for_surface(surface2);
pattern3=cairo_pattern_create_for_surface(surface3);
pattern4=cairo_pattern_create_for_surface(surface4);
cairo_set_source(cr,pattern1);
cairo_pattern_set_extend(cairo_get_source(cr),
CAIRO_EXTEND_REPEAT);
cairo_set_source(cr,pattern2);
cairo_arc(cr,200,70,50,0,2*M_PI);
cairo_set_source(cr,pattern3);
cairo_rectangle(cr