eek-gtk-keyboard: Trigger event feedback on button press

Use libfeedback to trigger feedback for the button press event.

Closes: #166
This commit is contained in:
Guido Günther
2020-01-29 18:19:38 +01:00
parent e89c9b02a0
commit ec58442724
4 changed files with 67 additions and 1 deletions

View File

@ -37,6 +37,10 @@
#include "src/layout.h"
#include "src/submission.h"
#define LIBFEEDBACK_USE_UNSTABLE_API
#include <libfeedback.h>
#define SQUEEKBOARD_APP_ID "sm.puri.squeekboard"
typedef struct _EekGtkKeyboardPrivate
{
@ -48,6 +52,7 @@ typedef struct _EekGtkKeyboardPrivate
LevelKeyboard *keyboard; // unowned reference; it's kept in server-context
GdkEventSequence *sequence; // unowned reference
LfbEvent *event;
} EekGtkKeyboardPrivate;
G_DEFINE_TYPE_WITH_PRIVATE (EekGtkKeyboard, eek_gtk_keyboard, GTK_TYPE_DRAWING_AREA)
@ -135,6 +140,19 @@ eek_gtk_keyboard_real_size_allocate (GtkWidget *self,
size_allocate (self, allocation);
}
static void
on_event_triggered (LfbEvent *event,
GAsyncResult *res,
gpointer unused)
{
g_autoptr (GError) err = NULL;
if (!lfb_event_trigger_feedback_finish (event, res, &err)) {
g_warning ("Failed to trigger feedback for '%s': %s",
lfb_event_get_event (event), err->message);
}
}
static void depress(EekGtkKeyboard *self,
gdouble x, gdouble y, guint32 time)
{
@ -299,6 +317,11 @@ eek_gtk_keyboard_dispose (GObject *object)
priv->keyboard = NULL;
}
if (priv->event) {
g_clear_object (&priv->event);
lfb_uninit ();
}
G_OBJECT_CLASS (eek_gtk_keyboard_parent_class)->dispose (object);
}
@ -330,7 +353,13 @@ eek_gtk_keyboard_class_init (EekGtkKeyboardClass *klass)
static void
eek_gtk_keyboard_init (EekGtkKeyboard *self)
{
(void)self;
EekGtkKeyboardPrivate *priv = eek_gtk_keyboard_get_instance_private (EEK_GTK_KEYBOARD (self));
g_autoptr(GError) err = NULL;
if (lfb_init(SQUEEKBOARD_APP_ID, &err))
priv->event = lfb_event_new ("button-pressed");
else
g_warning ("Failed to init libfeedback: %s", err->message);
}
static void
@ -376,3 +405,24 @@ eek_gtk_keyboard_new (EekboardContextService *eekservice,
return GTK_WIDGET(box);*/
return GTK_WIDGET(ret);
}
/**
* eek_gtk_keyboard_emit_feedback:
*
* Emit button press haptic feedback via libfeedack.
*/
void
eek_gtk_keyboard_emit_feedback (EekGtkKeyboard *self)
{
EekGtkKeyboardPrivate *priv;
g_return_if_fail (EEK_IS_GTK_KEYBOARD (self));
priv = eek_gtk_keyboard_get_instance_private (EEK_GTK_KEYBOARD (self));
if (priv->event) {
lfb_event_trigger_feedback_async (priv->event,
NULL,
(GAsyncReadyCallback)on_event_triggered,
NULL);
}
}

View File

@ -49,6 +49,7 @@ struct _EekGtkKeyboardClass
GType eek_gtk_keyboard_get_type (void) G_GNUC_CONST;
GtkWidget *eek_gtk_keyboard_new (EekboardContextService *eekservice, struct submission *submission, struct squeek_layout_state *layout);
void eek_gtk_keyboard_emit_feedback (EekGtkKeyboard *self);
G_END_DECLS
#endif /* EEK_GTK_KEYBOARD_H */

View File

@ -52,6 +52,14 @@ pub mod c {
#[derive(Copy, Clone)]
pub struct EekGtkKeyboard(pub *const gtk_sys::GtkWidget);
#[no_mangle]
extern "C" {
#[allow(improper_ctypes)]
pub fn eek_gtk_keyboard_emit_feedback(
keyboard: EekGtkKeyboard,
);
}
/// Defined in eek-types.h
#[repr(C)]
#[derive(Clone, Debug, PartialEq)]
@ -341,6 +349,9 @@ pub mod c {
);
// maybe TODO: draw on the display buffer here
drawing::queue_redraw(ui_keyboard);
unsafe {
eek_gtk_keyboard_emit_feedback(ui_keyboard);
}
};
}
@ -404,6 +415,9 @@ pub mod c {
&state,
);
// maybe TODO: draw on the display buffer here
unsafe {
eek_gtk_keyboard_emit_feedback(ui_keyboard);
}
}
} else {
for wrapped_key in pressed {

View File

@ -38,6 +38,7 @@ deps = [
dependency('gio-2.0', version: '>=2.26.0'),
dependency('gnome-desktop-3.0', version: '>=3.0'),
dependency('gtk+-3.0', version: '>=3.0'),
dependency('libfeedback-0.0'),
dependency('wayland-client', version: '>=1.14'),
dependency('xkbcommon'),
cc.find_library('m'),