You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

MacOS下cairo_show_text返回无效表面错误如何解决?

macOS下Cairo调用cairo_show_text出现“表面类型不适合操作”错误的解决方法

问题背景

在macOS环境中调用自定义的cairo_text_outline函数时,cairo_show_text返回错误状态码13,提示the surface type is not appropriate for the operation,但相同代码在Linux和Windows平台可正常运行。

自定义函数代码

void cairo_text_outline (cairo_t *cr, double x, double y,
                         const char *p)
{
  cairo_set_source_rgb(cr, 1.0, 1.0, 1.0);
  cairo_move_to(cr, x - 1.0, y - 1.0);
  printf("3 %s\n", cairo_status_to_string(cairo_status(cr)));
  if (cairo_status(cr))
    abort();
  cairo_show_text(cr, p);
  printf("4 %d %s\n", cairo_status(cr),
         cairo_status_to_string(cairo_status(cr)));
  if (cairo_status(cr))
    abort();
}

调用位置代码

[...]
  /* text */                                                               
  cairo_identity_matrix(cr);                                               
  cairo_set_font(cr, &g_font_courier_new);                                 
  cairo_set_font_size(cr, 20);                                             
  cairo_text_extents(cr, seq->title, &te);                                 
  cairo_text_outline(cr, 20.0, window->h - te.height - te.y_bearing - 20,  
              seq->title);                                                 
  [...]

错误输出

3 no error has occurred
4 13 the surface type is not appropriate for the operation

解决方法

1. 改用路径渲染文本替换cairo_show_text

macOS的Quartz后端对cairo_show_text的支持存在限制,可通过将文本转换为路径再填充的方式绕过该问题,修改自定义函数如下:

void cairo_text_outline (cairo_t *cr, double x, double y,
                         const char *p)
{
  cairo_set_source_rgb(cr, 1.0, 1.0, 1.0);
  cairo_move_to(cr, x - 1.0, y - 1.0);
  // 替换cairo_show_text为路径渲染
  cairo_text_path(cr, p);
  cairo_fill(cr);
  
  printf("4 %d %s\n", cairo_status(cr),
         cairo_status_to_string(cairo_status(cr)));
  if (cairo_status(cr))
    abort();
}

2. 调整字体加载方式

macOS上Cairo依赖Quartz字体系统,直接使用cairo_set_font传入自定义字体结构易出现兼容性问题,改用系统原生字体加载方式:

// 替换原有的cairo_set_font调用
cairo_select_font_face(cr, "Courier New", CAIRO_FONT_SLANT_NORMAL, CAIRO_FONT_WEIGHT_NORMAL);
cairo_set_font_size(cr, 20);

3. 检查并确认Cairo表面类型

通过cairo_surface_get_type(cairo_get_target(cr))确认当前使用的表面类型,如果是CAIRO_SURFACE_TYPE_QUARTZ,确保创建表面时使用cairo_quartz_surface_create而非通用创建函数,避免配置错误。

4. 更新Cairo版本

旧版Cairo的Quartz后端存在已知Bug,升级到最新稳定版可修复多数平台兼容性问题。

内容的提问来源于stack exchange,提问作者thodg

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.06.14 12:07:27