Создание сигналов в файлах VAPI
Я пытаюсь написать VAPI-файл для использования libui ( https://github.com/andlabs/libui) в Vala.
Я не знаю, как связать события от элементов управления с сигналами Вала.
В заголовках libui, например, при закрытии окна этот метод определяется:
_UI_EXTERN void uiWindowOnClosing(uiWindow *w, int (*f)(uiWindow *w, void *data), void *data);
В примерах C этот метод вызывается с методом "onClosing" в качестве аргумента:
uiWindowOnClosing(w, onClosing, NULL);
Как я могу сделать что-то вроде:
window.OnClosing.connect(()=>{print("End");});
3 ответа
Сигналы в Vala реализуются с использованием сигналов GLib, что является примером схемы наблюдателя. Чтобы использовать сигналы в Vala, класс должен наследовать от Object
и это не похоже на libui
использует GLib GObject. Поэтому невозможно использовать сигналы в этой привязке. Хотя можно использовать сигналы в привязке Vala. Например, gtksourceview VAPI связывает redo
а также undo
сигналы SourceBuffer
,
Шаблон используется в uiWindowOnClosing
это передать указатель на функцию C для использования в качестве обратного вызова. На стороне Вала они называются делегатами. libui
не добавил typedef для функциональной точки, поэтому Vala должен сгенерировать это. На это указывает использование [CCode (has_typedef = false)]
в вапи.
Другая проблема здесь - пустой указатель для пользовательских данных - void *data
, Это, вероятно, лучше всего связано с использованием простых обобщений.
Черновая резка при переплете будет:
[CCode (cname = "uiWindow")]
public class Window {
[CCode (has_typedef = false, simple_generics = true)]
public delegate int Callback<T> (T data);
[CCode (cname = "uiWindowOnClosing", simple_generics = true)]
public void on_closing<K> (Callback callback, K data);
}
Это не проверено, но должно дать вам лучшее представление о базовых концепциях.
Это невозможно. Валы signal
Механизм основан на сигнальной системе GLib. Вы можете заставить их использовать лямбды, но не сигналы.
Используя ваш код в vapi и вызывайте его так:
w.on_closing(()=>{Quit();return 0;}, null);
приносит это сообщение:
error: too many arguments to function ‘uiWindowOnClosing’
uiWindowOnClosing (_tmp3_, ___lambda4__ui_window_callback, NULL, NULL);
Но это работает:
public void on_closing (Callback callback);
в вапи и
w.on_closing(()=>{Quit();return 0;});
в коде Вала.
Спасибо за помощь.