What it is
Cairo is a 2D graphics library that supports vector graphics, including drawing shapes, text, and images. It provides high-quality rendering for multiple output targets such as screens, PDFs, SVGs, and image buffers.
Cairo allows developers to draw lines, curves, shapes, text, and images on various surfaces, such as image buffers, PDFs, or windows. It supports transformations, anti-aliasing, and compositing.
Installation
sudo apt install libcairo2-devGetting started
The smallest useful thing you can do with it, and what each part means.
#include <cairo.h>
int main() {
cairo_surface_t *surface = cairo_image_surface_create(CAIRO_FORMAT_ARGB32, 200, 200);
cairo_t *cr = cairo_create(surface);
cairo_set_source_rgb(cr, 0, 0, 0);
cairo_move_to(cr, 10, 10);
cairo_line_to(cr, 190, 190);
cairo_stroke(cr);
cairo_surface_write_to_png(surface, "line.png");
cairo_destroy(cr);
cairo_surface_destroy(surface);
return 0;
}#include <cairo.h>
int main() {
cairo_surface_t *surface = cairo_image_surface_create(CAIRO_FORMAT_ARGB32, 200, 200);
cairo_t *cr = cairo_create(surface);
cairo_set_source_rgb(cr, 1, 0, 0); // Red color
cairo_rectangle(cr, 50, 50, 100, 100);
cairo_fill(cr);
cairo_surface_write_to_png(surface, "rectangle.png");
cairo_destroy(cr);
cairo_surface_destroy(surface);
return 0;
}Advanced usage
Where the library earns its place over a simpler alternative.
#include <cairo.h>
int main() {
cairo_surface_t *surface = cairo_image_surface_create(CAIRO_FORMAT_ARGB32, 300, 100);
cairo_t *cr = cairo_create(surface);
cairo_select_font_face(cr, "Sans", CAIRO_FONT_SLANT_NORMAL, CAIRO_FONT_WEIGHT_BOLD);
cairo_set_font_size(cr, 32);
cairo_set_source_rgb(cr, 0, 0, 1); // Blue
cairo_move_to(cr, 10, 50);
cairo_show_text(cr, "Hello Cairo!");
cairo_surface_write_to_png(surface, "text.png");
cairo_destroy(cr);
cairo_surface_destroy(surface);
return 0;
}#include <cairo.h>
int main() {
cairo_surface_t *surface = cairo_image_surface_create(CAIRO_FORMAT_ARGB32, 200, 200);
cairo_t *cr = cairo_create(surface);
cairo_translate(cr, 100, 100);
cairo_scale(cr, 1.5, 1.5);
cairo_arc(cr, 0, 0, 50, 0, 2 * 3.14159);
cairo_set_source_rgb(cr, 0, 1, 0); // Green
cairo_fill(cr);
cairo_surface_write_to_png(surface, "circle.png");
cairo_destroy(cr);
cairo_surface_destroy(surface);
return 0;
}#include <cairo.h>
int main() {
cairo_surface_t *surface = cairo_pdf_surface_create("output.pdf", 400, 400);
cairo_t *cr = cairo_create(surface);
cairo_set_source_rgb(cr, 0, 0, 0);
cairo_move_to(cr, 50, 50);
cairo_line_to(cr, 350, 350);
cairo_stroke(cr);
cairo_destroy(cr);
cairo_surface_destroy(surface);
return 0;
}Errors and fixes
The failures you are most likely to hit, and what actually resolves them.
- CAIRO_STATUS_INVALID_SURFACE
- Ensure the surface is properly created before performing drawing operations.
- CAIRO_STATUS_NO_MEMORY
- Check memory allocation and ensure sufficient resources for large surfaces.
- CAIRO_STATUS_WRITE_ERROR
- Ensure the output file path is correct and writable.
Best practices
- Always destroy the Cairo context and surface to free resources.
- Use appropriate surface types (image, PDF, SVG) for your output needs.
- Leverage transformations to simplify drawing operations.
- Use anti-aliasing for smooth graphics.
- Organize drawing code with functions to improve readability.
Background
Why it exists, and what it was reacting to.
Cairo was developed to provide a powerful, consistent 2D graphics API across multiple platforms. It is widely used in GUI toolkits, desktop applications, and embedded systems for rendering vector graphics and producing high-quality output.
