Linux内核开发者求助:用GTK实现CISPR测试全屏滚动H
实现全屏黑底滚动"H"的GTK方案
作为Linux内核开发者,你已经搭好了全屏黑屏的基础框架,这点很棒!要实现滚动的"H"效果,我们可以基于现有代码,用几个GTK/GLib的工具就能轻松搞定,下面一步步给你拆解:
核心组件与工具
GtkFixed:替代默认容器,让我们能精准控制"H"的坐标位置(默认容器会自动布局,不适合自定义滚动路径)GtkLabel:继续用它显示"H",比自定义绘制更简单上手,适合GUI新手g_timeout_add():GLib的定时器函数,定时更新标签位置,形成连续滚动动画- Pango字体工具:调整"H"的大小和样式,让它在测试中更清晰
具体修改步骤
1. 替换布局容器为GtkFixed
原来的代码直接把Label加到Window里,Window默认用的是自动布局容器,我们换成GtkFixed来手动控制位置:
// 替换原有的gtk_container_add部分 GtkWidget *fixed = gtk_fixed_new(); gtk_container_add(GTK_CONTAINER(window), fixed); gtk_container_add(GTK_CONTAINER(fixed), label);
2. 初始化滚动位置变量
在main函数开头定义静态变量跟踪"H"的位置(单线程GTK程序里静态变量足够安全):
static int pos_x = 0; // 水平滚动位置 static int pos_y; // 垂直居中位置
窗口显示后,计算垂直居中的Y坐标,同时把"H"初始位置放在窗口左侧外,准备滚动进入:
// 在gtk_widget_show_all(window)之后添加: int win_width, win_height; gtk_window_get_size(GTK_WINDOW(window), &win_width, &win_height); int label_width, label_height; gtk_widget_get_size_request(label, &label_width, &label_height); // 垂直居中 pos_y = (win_height - label_height) / 2; // 初始位置在窗口左侧外 pos_x = -label_width; gtk_fixed_move(GTK_FIXED(fixed), label, pos_x, pos_y);
3. 编写滚动动画回调函数
写一个函数定时更新位置,让"H"从左向右滚动,滚出右侧后重新从左侧进入:
gboolean scroll_h(gpointer user_data) { GtkWidget *fixed = GTK_WIDGET(user_data); GtkWidget *label = gtk_bin_get_child(GTK_BIN(fixed)); int win_width; gtk_window_get_size(GTK_WINDOW(gtk_widget_get_toplevel(fixed)), &win_width, NULL); int label_width; gtk_widget_get_size_request(label, &label_width, NULL); pos_x += 5; // 滚动速度,数值越大越快,可根据需求调整 if (pos_x > win_width) { pos_x = -label_width; // 滚出屏幕后重置到左侧外 } gtk_fixed_move(GTK_FIXED(fixed), label, pos_x, pos_y); return G_SOURCE_CONTINUE; // 保持定时器持续触发 }
4. 启动动画定时器
在窗口初始化完成后,添加定时器控制帧率(比如每30毫秒更新一次,接近30帧/秒的流畅度):
// 设置完初始位置后添加 g_timeout_add(30, scroll_h, fixed);
5. 调整标签样式
把"H"改成白色、大字体,背景设为黑色,匹配测试需求:
// 创建Label后添加: gtk_label_set_text(GTK_LABEL(label), "H"); // 设置48号字体,可根据屏幕大小调整 PangoFontDescription *font = pango_font_description_from_string("Sans 48"); gtk_widget_modify_font(label, font); pango_font_description_free(font); // 黑底白字 gtk_widget_modify_bg(label, GTK_STATE_NORMAL, &gdk_color_black); gtk_widget_modify_fg(label, GTK_STATE_NORMAL, &gdk_color_white);
完整修改后的代码示例
#include <gtk/gtk.h> #include <pango/pango.h> static int pos_x = 0; static int pos_y; gboolean scroll_h(gpointer user_data) { GtkWidget *fixed = GTK_WIDGET(user_data); GtkWidget *label = gtk_bin_get_child(GTK_BIN(fixed)); int win_width; gtk_window_get_size(GTK_WINDOW(gtk_widget_get_toplevel(fixed)), &win_width, NULL); int label_width; gtk_widget_get_size_request(label, &label_width, NULL); pos_x += 5; if (pos_x > win_width) { pos_x = -label_width; } gtk_fixed_move(GTK_FIXED(fixed), label, pos_x, pos_y); return G_SOURCE_CONTINUE; } int main (int argc, char *argv[]) { GtkWidget *window; GtkWidget *label; GtkWidget *fixed; gtk_init (&argc, &argv); window = gtk_window_new(GTK_WINDOW_TOPLEVEL); gtk_window_set_decorated(GTK_WINDOW(window), FALSE); // 窗口背景设为黑色 gtk_widget_modify_bg(window, GTK_STATE_NORMAL, &gdk_color_black); // 创建Fixed布局容器 fixed = gtk_fixed_new(); gtk_container_add(GTK_CONTAINER(window), fixed); // 创建显示"H"的标签 label = gtk_label_new("H"); // 设置字体大小 PangoFontDescription *font = pango_font_description_from_string("Sans 48"); gtk_widget_modify_font(label, font); pango_font_description_free(font); // 设置标签黑底白字 gtk_widget_modify_bg(label, GTK_STATE_NORMAL, &gdk_color_black); gtk_widget_modify_fg(label, GTK_STATE_NORMAL, &gdk_color_white); gtk_container_add(GTK_CONTAINER(fixed), label); // 隐藏光标 GdkCursor* cursor = gdk_cursor_new(GDK_BLANK_CURSOR); GdkWindow* win = gtk_widget_get_window(window); gdk_window_set_cursor(win, cursor); gtk_widget_show_all(window); // 计算初始位置 int win_width, win_height; gtk_window_get_size(GTK_WINDOW(window), &win_width, &win_height); int label_width, label_height; gtk_widget_get_size_request(label, &label_width, &label_height); pos_y = (win_height - label_height) / 2; pos_x = -label_width; gtk_fixed_move(GTK_FIXED(fixed), label, pos_x, pos_y); // 启动滚动动画 g_timeout_add(30, scroll_h, fixed); gtk_main(); return 0; }
编译注意事项
编译时需要链接GTK3和Pango库,用以下命令:
gcc -o scroll_h scroll_h.c `pkg-config --cflags --libs gtk+-3.0`
如果需要调整滚动方向(比如上下滚动),只需要把逻辑改成更新pos_y即可,非常灵活。
内容的提问来源于stack exchange,提问作者md.jamal
相关产品推荐
相关产品推荐

