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

如何在GTK4中实现GtkFontDialog并添加字体过滤功能?

GTK4 中 GtkFontDialog 的字体过滤实现方法

GTK4.10 弃用 GtkFontChooserDialog 后,改用 GtkFontDialog 实现字体选择功能,字体过滤需要通过 GtkFontDialogFilter 对象完成,以下是具体实现步骤和代码示例:

1. 复用原有过滤回调函数

你之前的过滤逻辑可以完全复用,回调函数签名与GTK4的要求兼容:

static gboolean filter_font_cb (const PangoFontFamily *family,
                                const PangoFontFace   *face,
                                gpointer               data)
{
   const char *alias_families[] = {
     "DejaVu Sans Mono",
     "FreeMono",
     "Liberation Mono",
     "Mitra",
     "Monospace",
     "Nimbus Mono PS",
     "Noto Mono",
     "Tlwg Mono",
     "Tlwg Typo",
     "Ubuntu Mono",
     NULL
   };
   const char *family_name = pango_font_family_get_name(family);
   return g_strv_contains(alias_families, family_name);
}

2. 创建带过滤的 GtkFontDialog

方式一:使用 GtkFontDialogButton 触发对话框

这是GTK4推荐的快捷方式,按钮会自动关联对话框并处理展示逻辑:

// 创建字体对话框实例
GtkFontDialog *font_dialog = gtk_font_dialog_new();

// 创建过滤器并绑定过滤函数
GtkFontDialogFilter *filter = gtk_font_dialog_filter_new();
gtk_font_dialog_filter_set_filter_func(filter, filter_font_cb, NULL, NULL);

// 将过滤器关联到对话框
gtk_font_dialog_set_filter(font_dialog, filter);

// 创建对话框按钮,可设置初始字体
GtkWidget *font_button = gtk_font_dialog_button_new(font_dialog);
gtk_font_dialog_button_set_font_desc(font_button, pango_font_description_from_string("Monospace 12"));

// 绑定字体选中后的处理信号
g_signal_connect(font_button, "font-set", G_CALLBACK(on_font_set), NULL);

添加字体选中后的处理回调:

static void on_font_set(GtkFontDialogButton *button, gpointer user_data)
{
    PangoFontDescription *font_desc = gtk_font_dialog_button_get_font_desc(button);
    char *font_name = pango_font_description_to_string(font_desc);
    g_print("选中的字体:%s\n", font_name);
    g_free(font_name);
    pango_font_description_free(font_desc);
}

方式二:手动异步打开对话框

如果需要自定义触发逻辑(比如通过普通按钮打开),可以使用异步API:

// 字体选择完成后的回调
static void on_font_chosen(GObject *source_object, GAsyncResult *res, gpointer user_data)
{
    GtkFontDialog *dialog = GTK_FONT_DIALOG(source_object);
    PangoFontDescription *font_desc = gtk_font_dialog_choose_font_finish(dialog, res, NULL);
    if (font_desc != NULL) {
        char *font_name = pango_font_description_to_string(font_desc);
        g_print("选中的字体:%s\n", font_name);
        g_free(font_name);
        pango_font_description_free(font_desc);
    }
}

// 触发对话框的函数
void open_font_dialog(GtkWidget *widget, gpointer parent_window)
{
    GtkFontDialog *font_dialog = gtk_font_dialog_new();
    GtkFontDialogFilter *filter = gtk_font_dialog_filter_new();
    gtk_font_dialog_filter_set_filter_func(filter, filter_font_cb, NULL, NULL);
    gtk_font_dialog_set_filter(font_dialog, filter);

    // 异步打开对话框,parent_window为你的窗口实例
    gtk_font_dialog_choose_font(font_dialog, GTK_WINDOW(parent_window), NULL, NULL, on_font_chosen, NULL);
}

关键变化说明

  • GTK4 将过滤逻辑从 GtkFontChooser 接口剥离,改用独立的 GtkFontDialogFilter 对象管理,需先创建过滤器再绑定到对话框。
  • 原有过滤回调函数无需修改,可直接复用。
  • 推荐使用异步API处理对话框结果,避免阻塞主线程。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.06.19 06:17:06