+-
Vala GtkTemplate:找不到UI资源

我正在尝试使用GtkTemplate,但确实很烦人。我已经定义了.ui文件资源,可以正确调用它,等等。

这是我的文件:

meson.build:

# project name and programming language
project('myproject', 'vala', 'c', version: '1.0.0')

# add resources to the executeable
gnome = import('gnome')
gresources = gnome.compile_resources(
    meson.project_name() + '.resources',
    'data/gresources.xml',
    c_name: 'resources'
)

executable(
    meson.project_name(),

    'src/OpenFileWindow.vala',
    'src/Main.vala',

    gresources,

    dependencies: [
        dependency('gtk+-3.0'),
        dependency('gio-2.0'),
    ],
    install: true
)

src / OpenFileWindow.vala:

using Gtk;

namespace MyProject {

    [GtkTemplate (ui="/ui/OpenFileWindow.ui")]
    public class OpenFileWindow : Window {
        [GtkChild]
        Button btn_browse;

        public OpenFileWindow() {

        }

        [GtkCallback]
        private void btn_browse_clicked(Button btn) {
            stdout.printf("CLICKED");
        }
    }
}

ui / OpenFileWindow.ui:

<?xml version="1.0" encoding="UTF-8"?>
<!-- Generated with glade 3.22.1 -->
<interface>
  <requires lib="gtk+" version="3.20"/>
  <template class="OpenFileWindow" parent="GtkWindow">
    <property name="can_focus">False</property>
    <child>
      <object class="GtkButton" id="btn_browse">
        <property name="label">gtk-open</property>
        <property name="visible">True</property>
        <property name="can_focus">True</property>
        <property name="receives_default">True</property>
        <property name="use_stock">True</property>
        <property name="image_position">top</property>
        <property name="always_show_image">True</property>
        <signal name="clicked" handler="myproject_openfilewindow_btn_browse_clicked" swapped="no"/>
      </object>
    </child>
  </template>
</interface>

data / gresources.xml:

<?xml version="1.0" encoding="UTF-8"?>
<gresources>
  <gresource prefix="/">
    <file preprocess="xml-stripblanks">ui/OpenFileWindow.ui</file>
  </gresource>
</gresources>

当我使用介子和忍者构建时,出现此错误:

valac -C --debug --debug --pkg gio-2.0 --pkg gtk+-3.0 --color=always --directory myproject@exe --basedir ../ --gresources=../data/gresources.xml ../src/OpenFileWindow.vala ../src/Main.vala

../src/OpenFileWindow.vala:6.5-6.40: error: UI resource not found: `/ui/OpenFileWindow.ui'. Please make sure to specify the proper GResources xml files with --gresources and alternative search locations with --gresourcesdir.
    public class OpenFileWindow : Window {

什么问题,我真的看不出来...谢谢!

0
投票

GResource是只读文件系统,用于已嵌入到已编译二进制文件中的文件。在Vala GUI项目中,此文件可用于以二进制格式存储图像,图标等。

GtkBuilder UI定义文件也可以嵌入,并且Vala通过[GtkTemplate][GtkChild][GtkCallback]属性对此提供了额外的支持。此支持的一部分包括在编译时进行类型检查。该检查需要获取源文件并计算出GResource内存中文件系统的文件名,这是项目失败的地方。任何想要改善此问题的人都应在Vala编译器中修补codegen/valagtkmodule.vala。但是,就目前而言,要使您的项目正常运行,您将需要对资源使用更扁平的文件结构。

首先将data/gresource.xml移至ui/目录。然后将prefix更改为/ui。这意味着内存文件系统将使用与您在Vala代码中使用的GtkTemplate属性匹配的名称。另外,从文件名中删除ui/以提供平面目录结构:

<?xml version="1.0" encoding="UTF-8"?>
<gresources>
  <gresource prefix="/ui/">
    <file preprocess="xml-stripblanks">OpenFileWindow.ui</file>
  </gresource>
</gresources>

您还需要修改gresources文件中meson.build的定义:

gresources = gnome.compile_resources(
    meson.project_name() + '.resources',
    'ui/gresources.xml',
    source_dir: ['ui']
)

这使用source_dir使引用保持在扁平化的目录结构中。

您现在应该不再收到错误消息。以Geary为例,该示例项目使用了大量的GtkBuilder UI文件。该项目的GResource文件与其他文件位于同一目录中。

您的项目将仍然无法编译,因为Vala编译器已识别出[GtkCallback]没有信号。这是一个名称解析问题,您只需要从以下位置更改OpenFileWindow.ui文件中的一行:

<signal name="clicked" handler="myproject_openfilewindow_btn_browse_clicked" swapped="no"/>

to

<signal name="clicked" handler="btn_browse_clicked" swapped="no"/>