/* key-event-filter.c generated by valac 0.40.8, the Vala compiler
 * generated from key-event-filter.vala, do not modify */

/*
 * Copyright (C) 2011-2018 Daiki Ueno <ueno@gnu.org>
 * Copyright (C) 2011-2018 Red Hat, Inc.
 *
 * This program is free software: you can redistribute it and/or modify
 * it under the terms of the GNU General Public License as published by
 * the Free Software Foundation, either version 3 of the License, or
 * (at your option) any later version.
 *
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU General Public License for more details.
 *
 * You should have received a copy of the GNU General Public License
 * along with this program.  If not, see <http://www.gnu.org/licenses/>.
 */


#include <glib.h>
#include <glib-object.h>


#define SKK_TYPE_KEY_EVENT_FILTER (skk_key_event_filter_get_type ())
#define SKK_KEY_EVENT_FILTER(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), SKK_TYPE_KEY_EVENT_FILTER, SkkKeyEventFilter))
#define SKK_KEY_EVENT_FILTER_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST ((klass), SKK_TYPE_KEY_EVENT_FILTER, SkkKeyEventFilterClass))
#define SKK_IS_KEY_EVENT_FILTER(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), SKK_TYPE_KEY_EVENT_FILTER))
#define SKK_IS_KEY_EVENT_FILTER_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), SKK_TYPE_KEY_EVENT_FILTER))
#define SKK_KEY_EVENT_FILTER_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS ((obj), SKK_TYPE_KEY_EVENT_FILTER, SkkKeyEventFilterClass))

typedef struct _SkkKeyEventFilter SkkKeyEventFilter;
typedef struct _SkkKeyEventFilterClass SkkKeyEventFilterClass;
typedef struct _SkkKeyEventFilterPrivate SkkKeyEventFilterPrivate;

#define SKK_TYPE_KEY_EVENT (skk_key_event_get_type ())
#define SKK_KEY_EVENT(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), SKK_TYPE_KEY_EVENT, SkkKeyEvent))
#define SKK_KEY_EVENT_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST ((klass), SKK_TYPE_KEY_EVENT, SkkKeyEventClass))
#define SKK_IS_KEY_EVENT(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), SKK_TYPE_KEY_EVENT))
#define SKK_IS_KEY_EVENT_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), SKK_TYPE_KEY_EVENT))
#define SKK_KEY_EVENT_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS ((obj), SKK_TYPE_KEY_EVENT, SkkKeyEventClass))

typedef struct _SkkKeyEvent SkkKeyEvent;
typedef struct _SkkKeyEventClass SkkKeyEventClass;
enum  {
	SKK_KEY_EVENT_FILTER_0_PROPERTY,
	SKK_KEY_EVENT_FILTER_NUM_PROPERTIES
};
static GParamSpec* skk_key_event_filter_properties[SKK_KEY_EVENT_FILTER_NUM_PROPERTIES];
enum  {
	SKK_KEY_EVENT_FILTER_FORWARDED_SIGNAL,
	SKK_KEY_EVENT_FILTER_NUM_SIGNALS
};
static guint skk_key_event_filter_signals[SKK_KEY_EVENT_FILTER_NUM_SIGNALS] = {0};

#define SKK_TYPE_SIMPLE_KEY_EVENT_FILTER (skk_simple_key_event_filter_get_type ())
#define SKK_SIMPLE_KEY_EVENT_FILTER(obj) (G_TYPE_CHECK_INSTANCE_CAST ((obj), SKK_TYPE_SIMPLE_KEY_EVENT_FILTER, SkkSimpleKeyEventFilter))
#define SKK_SIMPLE_KEY_EVENT_FILTER_CLASS(klass) (G_TYPE_CHECK_CLASS_CAST ((klass), SKK_TYPE_SIMPLE_KEY_EVENT_FILTER, SkkSimpleKeyEventFilterClass))
#define SKK_IS_SIMPLE_KEY_EVENT_FILTER(obj) (G_TYPE_CHECK_INSTANCE_TYPE ((obj), SKK_TYPE_SIMPLE_KEY_EVENT_FILTER))
#define SKK_IS_SIMPLE_KEY_EVENT_FILTER_CLASS(klass) (G_TYPE_CHECK_CLASS_TYPE ((klass), SKK_TYPE_SIMPLE_KEY_EVENT_FILTER))
#define SKK_SIMPLE_KEY_EVENT_FILTER_GET_CLASS(obj) (G_TYPE_INSTANCE_GET_CLASS ((obj), SKK_TYPE_SIMPLE_KEY_EVENT_FILTER, SkkSimpleKeyEventFilterClass))

typedef struct _SkkSimpleKeyEventFilter SkkSimpleKeyEventFilter;
typedef struct _SkkSimpleKeyEventFilterClass SkkSimpleKeyEventFilterClass;
typedef struct _SkkSimpleKeyEventFilterPrivate SkkSimpleKeyEventFilterPrivate;
enum  {
	SKK_SIMPLE_KEY_EVENT_FILTER_0_PROPERTY,
	SKK_SIMPLE_KEY_EVENT_FILTER_NUM_PROPERTIES
};
static GParamSpec* skk_simple_key_event_filter_properties[SKK_SIMPLE_KEY_EVENT_FILTER_NUM_PROPERTIES];

#define SKK_TYPE_MODIFIER_TYPE (skk_modifier_type_get_type ())

struct _SkkKeyEventFilter {
	GObject parent_instance;
	SkkKeyEventFilterPrivate * priv;
};

struct _SkkKeyEventFilterClass {
	GObjectClass parent_class;
	SkkKeyEvent* (*filter_key_event) (SkkKeyEventFilter* self, SkkKeyEvent* key);
	void (*reset) (SkkKeyEventFilter* self);
};

struct _SkkSimpleKeyEventFilter {
	SkkKeyEventFilter parent_instance;
	SkkSimpleKeyEventFilterPrivate * priv;
};

struct _SkkSimpleKeyEventFilterClass {
	SkkKeyEventFilterClass parent_class;
};

typedef enum  {
	SKK_MODIFIER_TYPE_NONE = 0,
	SKK_MODIFIER_TYPE_SHIFT_MASK = 1 << 0,
	SKK_MODIFIER_TYPE_LOCK_MASK = 1 << 1,
	SKK_MODIFIER_TYPE_CONTROL_MASK = 1 << 2,
	SKK_MODIFIER_TYPE_MOD1_MASK = 1 << 3,
	SKK_MODIFIER_TYPE_MOD2_MASK = 1 << 4,
	SKK_MODIFIER_TYPE_MOD3_MASK = 1 << 5,
	SKK_MODIFIER_TYPE_MOD4_MASK = 1 << 6,
	SKK_MODIFIER_TYPE_MOD5_MASK = 1 << 7,
	SKK_MODIFIER_TYPE_LSHIFT_MASK = 1 << 22,
	SKK_MODIFIER_TYPE_RSHIFT_MASK = 1 << 23,
	SKK_MODIFIER_TYPE_USLEEP_MASK = 1 << 24,
	SKK_MODIFIER_TYPE_SUPER_MASK = 1 << 26,
	SKK_MODIFIER_TYPE_HYPER_MASK = 1 << 27,
	SKK_MODIFIER_TYPE_META_MASK = 1 << 28,
	SKK_MODIFIER_TYPE_RELEASE_MASK = 1 << 30
} SkkModifierType;


static gpointer skk_key_event_filter_parent_class = NULL;
static gpointer skk_simple_key_event_filter_parent_class = NULL;

GType skk_key_event_filter_get_type (void) G_GNUC_CONST;
GType skk_key_event_get_type (void) G_GNUC_CONST;
SkkKeyEvent* skk_key_event_filter_filter_key_event (SkkKeyEventFilter* self,
                                                    SkkKeyEvent* key);
static SkkKeyEvent* skk_key_event_filter_real_filter_key_event (SkkKeyEventFilter* self,
                                                         SkkKeyEvent* key);
void skk_key_event_filter_reset (SkkKeyEventFilter* self);
static void skk_key_event_filter_real_reset (SkkKeyEventFilter* self);
SkkKeyEventFilter* skk_key_event_filter_construct (GType object_type);
GType skk_simple_key_event_filter_get_type (void) G_GNUC_CONST;
static SkkKeyEvent* skk_simple_key_event_filter_real_filter_key_event (SkkKeyEventFilter* base,
                                                                SkkKeyEvent* key);
GType skk_modifier_type_get_type (void) G_GNUC_CONST;
SkkModifierType skk_key_event_get_modifiers (SkkKeyEvent* self);
void skk_key_event_set_modifiers (SkkKeyEvent* self,
                                  SkkModifierType value);
SkkSimpleKeyEventFilter* skk_simple_key_event_filter_new (void);
SkkSimpleKeyEventFilter* skk_simple_key_event_filter_construct (GType object_type);


/**
         * Convert a key event to another.
         *
         * @param key a key event
         *
         * @return a KeyEvent or `null` if the result cannot be
         * fetched immediately
         */
static SkkKeyEvent*
skk_key_event_filter_real_filter_key_event (SkkKeyEventFilter* self,
                                            SkkKeyEvent* key)
{
	g_critical ("Type `%s' does not implement abstract method `skk_key_event_filter_filter_key_event'", g_type_name (G_TYPE_FROM_INSTANCE (self)));
	return NULL;
}


SkkKeyEvent*
skk_key_event_filter_filter_key_event (SkkKeyEventFilter* self,
                                       SkkKeyEvent* key)
{
	g_return_val_if_fail (self != NULL, NULL);
	return SKK_KEY_EVENT_FILTER_GET_CLASS (self)->filter_key_event (self, key);
}


/**
         * Reset the filter.
         */
static void
skk_key_event_filter_real_reset (SkkKeyEventFilter* self)
{
}


void
skk_key_event_filter_reset (SkkKeyEventFilter* self)
{
	g_return_if_fail (self != NULL);
	SKK_KEY_EVENT_FILTER_GET_CLASS (self)->reset (self);
}


SkkKeyEventFilter*
skk_key_event_filter_construct (GType object_type)
{
	SkkKeyEventFilter * self = NULL;
	self = (SkkKeyEventFilter*) g_object_new (object_type, NULL);
	return self;
}


static void
skk_key_event_filter_class_init (SkkKeyEventFilterClass * klass)
{
	skk_key_event_filter_parent_class = g_type_class_peek_parent (klass);
	((SkkKeyEventFilterClass *) klass)->filter_key_event = (SkkKeyEvent* (*) (SkkKeyEventFilter *, SkkKeyEvent*)) skk_key_event_filter_real_filter_key_event;
	((SkkKeyEventFilterClass *) klass)->reset = (void (*) (SkkKeyEventFilter *)) skk_key_event_filter_real_reset;
	/**
	         * Signal emitted when a new key event is generated in the filter.
	         *
	         * @param key a key event
	         */
	skk_key_event_filter_signals[SKK_KEY_EVENT_FILTER_FORWARDED_SIGNAL] = g_signal_new ("forwarded", SKK_TYPE_KEY_EVENT_FILTER, G_SIGNAL_RUN_LAST, 0, NULL, NULL, g_cclosure_marshal_VOID__OBJECT, G_TYPE_NONE, 1, SKK_TYPE_KEY_EVENT);
}


static void
skk_key_event_filter_instance_init (SkkKeyEventFilter * self)
{
}


/**
     * Base class of a key event filter.
     */
GType
skk_key_event_filter_get_type (void)
{
	static volatile gsize skk_key_event_filter_type_id__volatile = 0;
	if (g_once_init_enter (&skk_key_event_filter_type_id__volatile)) {
		static const GTypeInfo g_define_type_info = { sizeof (SkkKeyEventFilterClass), (GBaseInitFunc) NULL, (GBaseFinalizeFunc) NULL, (GClassInitFunc) skk_key_event_filter_class_init, (GClassFinalizeFunc) NULL, NULL, sizeof (SkkKeyEventFilter), 0, (GInstanceInitFunc) skk_key_event_filter_instance_init, NULL };
		GType skk_key_event_filter_type_id;
		skk_key_event_filter_type_id = g_type_register_static (G_TYPE_OBJECT, "SkkKeyEventFilter", &g_define_type_info, G_TYPE_FLAG_ABSTRACT);
		g_once_init_leave (&skk_key_event_filter_type_id__volatile, skk_key_event_filter_type_id);
	}
	return skk_key_event_filter_type_id__volatile;
}


/**
         * {@inheritDoc}
         */
static gpointer
_g_object_ref0 (gpointer self)
{
	return self ? g_object_ref (self) : NULL;
}


static SkkKeyEvent*
skk_simple_key_event_filter_real_filter_key_event (SkkKeyEventFilter* base,
                                                   SkkKeyEvent* key)
{
	SkkSimpleKeyEventFilter * self;
	SkkKeyEvent* result = NULL;
	SkkModifierType _tmp0_;
	SkkModifierType _tmp1_;
	SkkModifierType _tmp2_;
	SkkModifierType _tmp3_;
	SkkKeyEvent* _tmp4_;
	self = (SkkSimpleKeyEventFilter*) base;
	g_return_val_if_fail (key != NULL, NULL);
	_tmp0_ = skk_key_event_get_modifiers (key);
	_tmp1_ = _tmp0_;
	if ((_tmp1_ & SKK_MODIFIER_TYPE_RELEASE_MASK) != 0) {
		result = NULL;
		return result;
	}
	_tmp2_ = skk_key_event_get_modifiers (key);
	_tmp3_ = _tmp2_;
	skk_key_event_set_modifiers (key, _tmp3_ & (~SKK_MODIFIER_TYPE_SHIFT_MASK));
	_tmp4_ = _g_object_ref0 (key);
	result = _tmp4_;
	return result;
}


SkkSimpleKeyEventFilter*
skk_simple_key_event_filter_construct (GType object_type)
{
	SkkSimpleKeyEventFilter * self = NULL;
	self = (SkkSimpleKeyEventFilter*) skk_key_event_filter_construct (object_type);
	return self;
}


SkkSimpleKeyEventFilter*
skk_simple_key_event_filter_new (void)
{
	return skk_simple_key_event_filter_construct (SKK_TYPE_SIMPLE_KEY_EVENT_FILTER);
}


static void
skk_simple_key_event_filter_class_init (SkkSimpleKeyEventFilterClass * klass)
{
	skk_simple_key_event_filter_parent_class = g_type_class_peek_parent (klass);
	((SkkKeyEventFilterClass *) klass)->filter_key_event = (SkkKeyEvent* (*) (SkkKeyEventFilter *, SkkKeyEvent*)) skk_simple_key_event_filter_real_filter_key_event;
}


static void
skk_simple_key_event_filter_instance_init (SkkSimpleKeyEventFilter * self)
{
}


/**
     * Simple implementation of a key event filter.
     *
     * This class is rarely used in programs but specified as "filter"
     * property in rule metadata.
     *
     * @see Rule
     */
GType
skk_simple_key_event_filter_get_type (void)
{
	static volatile gsize skk_simple_key_event_filter_type_id__volatile = 0;
	if (g_once_init_enter (&skk_simple_key_event_filter_type_id__volatile)) {
		static const GTypeInfo g_define_type_info = { sizeof (SkkSimpleKeyEventFilterClass), (GBaseInitFunc) NULL, (GBaseFinalizeFunc) NULL, (GClassInitFunc) skk_simple_key_event_filter_class_init, (GClassFinalizeFunc) NULL, NULL, sizeof (SkkSimpleKeyEventFilter), 0, (GInstanceInitFunc) skk_simple_key_event_filter_instance_init, NULL };
		GType skk_simple_key_event_filter_type_id;
		skk_simple_key_event_filter_type_id = g_type_register_static (SKK_TYPE_KEY_EVENT_FILTER, "SkkSimpleKeyEventFilter", &g_define_type_info, 0);
		g_once_init_leave (&skk_simple_key_event_filter_type_id__volatile, skk_simple_key_event_filter_type_id);
	}
	return skk_simple_key_event_filter_type_id__volatile;
}



