/* AbstractMenu.c generated by valac 0.56.17, the Vala compiler
 * generated from AbstractMenu.vala, do not modify */

/*
Copyright (C) 2014 2015 Johan Mattsson

This library is free software; you can redistribute it and/or modify 
it under the terms of the GNU Lesser General Public License as 
published by the Free Software Foundation; either version 3 of the 
License, or (at your option) any later version.

This library 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 
Lesser General Public License for more details.
*/

#include "birdfont.h"
#include <glib.h>
#include <float.h>
#include <math.h>
#include <gee.h>
#include <glib-object.h>
#include <stdlib.h>
#include <string.h>
#include <gio/gio.h>
#include <xmlbird.h>
#include <glib/gstdio.h>
#include <cairo-gobject.h>

#if !defined(VALA_STRICT_C)
#if !defined(__clang__) && defined(__GNUC__) && (__GNUC__ >= 14)
#pragma GCC diagnostic warning "-Wincompatible-pointer-types"
#elif defined(__clang__) && (__clang_major__ >= 16)
#pragma clang diagnostic ignored "-Wincompatible-function-pointer-types"
#pragma clang diagnostic ignored "-Wincompatible-pointer-types"
#endif
#endif

enum  {
	BIRD_FONT_ABSTRACT_MENU_0_PROPERTY,
	BIRD_FONT_ABSTRACT_MENU_SHOW_MENU_PROPERTY,
	BIRD_FONT_ABSTRACT_MENU_NUM_PROPERTIES
};
static GParamSpec* bird_font_abstract_menu_properties[BIRD_FONT_ABSTRACT_MENU_NUM_PROPERTIES];
#define _g_object_unref0(var) ((var == NULL) ? NULL : (var = (g_object_unref (var), NULL)))
#define _g_free0(var) (var = (g_free (var), NULL))
#define _g_error_free0(var) ((var == NULL) ? NULL : (var = (g_error_free (var), NULL)))

struct _BirdFontAbstractMenuPrivate {
	gboolean menu_visibility;
	BirdFontSubMenu* current_menu;
	BirdFontWidgetAllocation* allocation;
	gdouble width;
	gdouble height;
};

static gint BirdFontAbstractMenu_private_offset;
static gpointer bird_font_abstract_menu_parent_class = NULL;
VALA_EXTERN gboolean bird_font_settings_display_update_key_bindings;

VALA_EXTERN GFile* bird_font_bird_font_get_settings_directory (void);
static void bird_font_abstract_menu_finalize (GObject * obj);
static GType bird_font_abstract_menu_get_type_once (void);
static void _vala_bird_font_abstract_menu_get_property (GObject * object,
                                                 guint property_id,
                                                 GValue * value,
                                                 GParamSpec * pspec);
static void _vala_bird_font_abstract_menu_set_property (GObject * object,
                                                 guint property_id,
                                                 const GValue * value,
                                                 GParamSpec * pspec);

static inline gpointer
bird_font_abstract_menu_get_instance_private (BirdFontAbstractMenu* self)
{
	return G_STRUCT_MEMBER_P (self, BirdFontAbstractMenu_private_offset);
}

BirdFontAbstractMenu*
bird_font_abstract_menu_construct (GType object_type)
{
	BirdFontAbstractMenu * self = NULL;
	self = (BirdFontAbstractMenu*) g_object_new (object_type, NULL);
	return self;
}

BirdFontAbstractMenu*
bird_font_abstract_menu_new (void)
{
	return bird_font_abstract_menu_construct (BIRD_FONT_TYPE_ABSTRACT_MENU);
}

static gpointer
_g_object_ref0 (gpointer self)
{
	return self ? g_object_ref (self) : NULL;
}

BirdFontToolItem*
bird_font_abstract_menu_get_item_for_tool (BirdFontAbstractMenu* self,
                                           BirdFontTool* t)
{
	BirdFontToolItem* tm = NULL;
	BirdFontToolItem* result;
	g_return_val_if_fail (self != NULL, NULL);
	g_return_val_if_fail (t != NULL, NULL);
	{
		GeeArrayList* _item_list = NULL;
		GeeArrayList* _tmp0_;
		gint _item_size = 0;
		GeeArrayList* _tmp1_;
		gint _tmp2_;
		gint _tmp3_;
		gint _item_index = 0;
		_tmp0_ = self->sorted_menu_items;
		_item_list = _tmp0_;
		_tmp1_ = _item_list;
		_tmp2_ = gee_abstract_collection_get_size ((GeeAbstractCollection*) _tmp1_);
		_tmp3_ = _tmp2_;
		_item_size = _tmp3_;
		_item_index = -1;
		while (TRUE) {
			gint _tmp4_;
			gint _tmp5_;
			BirdFontMenuItem* item = NULL;
			GeeArrayList* _tmp6_;
			gpointer _tmp7_;
			BirdFontMenuItem* _tmp8_;
			_item_index = _item_index + 1;
			_tmp4_ = _item_index;
			_tmp5_ = _item_size;
			if (!(_tmp4_ < _tmp5_)) {
				break;
			}
			_tmp6_ = _item_list;
			_tmp7_ = gee_abstract_list_get ((GeeAbstractList*) _tmp6_, _item_index);
			item = (BirdFontMenuItem*) _tmp7_;
			_tmp8_ = item;
			if (BIRD_FONT_IS_TOOL_ITEM (_tmp8_)) {
				BirdFontMenuItem* _tmp9_;
				BirdFontToolItem* _tmp10_;
				BirdFontToolItem* _tmp11_;
				BirdFontTool* _tmp12_;
				_tmp9_ = item;
				_tmp10_ = _g_object_ref0 (G_TYPE_CHECK_INSTANCE_CAST (_tmp9_, BIRD_FONT_TYPE_TOOL_ITEM, BirdFontToolItem));
				_g_object_unref0 (tm);
				tm = _tmp10_;
				_tmp11_ = tm;
				_tmp12_ = _tmp11_->tool;
				if (_tmp12_ == t) {
					result = tm;
					_g_object_unref0 (item);
					return result;
				}
			}
			_g_object_unref0 (item);
		}
	}
	result = NULL;
	_g_object_unref0 (tm);
	return result;
}

/** @return true if the keybindings consumes the event. */
gboolean
bird_font_abstract_menu_process_key_binding_events (BirdFontAbstractMenu* self,
                                                    guint keyval)
{
	gchar* display = NULL;
	BirdFontFontDisplay* current_display = NULL;
	BirdFontFontDisplay* _tmp0_;
	BirdFontToolItem* tm = NULL;
	gunichar lower_keyval = 0U;
	BirdFontFontDisplay* _tmp1_;
	gchar* _tmp2_;
	BirdFontFontDisplay* _tmp3_;
	gboolean result;
	g_return_val_if_fail (self != NULL, FALSE);
	_tmp0_ = bird_font_main_window_get_current_display ();
	current_display = _tmp0_;
	lower_keyval = g_unichar_tolower ((gunichar) keyval);
	_tmp1_ = current_display;
	_tmp2_ = bird_font_font_display_get_name (_tmp1_);
	_g_free0 (display);
	display = _tmp2_;
	_tmp3_ = current_display;
	if (BIRD_FONT_IS_GLYPH_TAB (_tmp3_)) {
		gchar* _tmp4_;
		_tmp4_ = g_strdup ("Glyph");
		_g_free0 (display);
		display = _tmp4_;
	}
	{
		GeeArrayList* _item_list = NULL;
		GeeArrayList* _tmp5_;
		gint _item_size = 0;
		GeeArrayList* _tmp6_;
		gint _tmp7_;
		gint _tmp8_;
		gint _item_index = 0;
		_tmp5_ = self->sorted_menu_items;
		_item_list = _tmp5_;
		_tmp6_ = _item_list;
		_tmp7_ = gee_abstract_collection_get_size ((GeeAbstractCollection*) _tmp6_);
		_tmp8_ = _tmp7_;
		_item_size = _tmp8_;
		_item_index = -1;
		while (TRUE) {
			gint _tmp9_;
			gint _tmp10_;
			BirdFontMenuItem* item = NULL;
			GeeArrayList* _tmp11_;
			gpointer _tmp12_;
			gboolean _tmp13_ = FALSE;
			gboolean _tmp14_ = FALSE;
			BirdFontMenuItem* _tmp15_;
			_item_index = _item_index + 1;
			_tmp9_ = _item_index;
			_tmp10_ = _item_size;
			if (!(_tmp9_ < _tmp10_)) {
				break;
			}
			_tmp11_ = _item_list;
			_tmp12_ = gee_abstract_list_get ((GeeAbstractList*) _tmp11_, _item_index);
			item = (BirdFontMenuItem*) _tmp12_;
			_tmp15_ = item;
			if (g_unichar_tolower (_tmp15_->key) == lower_keyval) {
				BirdFontMenuItem* _tmp16_;
				_tmp16_ = item;
				_tmp14_ = _tmp16_->modifiers == bird_font_key_bindings_modifier;
			} else {
				_tmp14_ = FALSE;
			}
			if (_tmp14_) {
				BirdFontMenuItem* _tmp17_;
				const gchar* _tmp18_;
				_tmp17_ = item;
				_tmp18_ = display;
				_tmp13_ = bird_font_menu_item_in_display (_tmp17_, _tmp18_);
			} else {
				_tmp13_ = FALSE;
			}
			if (_tmp13_) {
				gboolean _tmp19_ = FALSE;
				BirdFontFontDisplay* _tmp20_;
				_tmp20_ = current_display;
				if (!bird_font_font_display_needs_modifier (_tmp20_)) {
					_tmp19_ = TRUE;
				} else {
					BirdFontMenuItem* _tmp21_;
					_tmp21_ = item;
					_tmp19_ = _tmp21_->modifiers != BIRD_FONT_NONE;
				}
				if (_tmp19_) {
					gboolean _tmp22_ = FALSE;
					BirdFontMenuItem* _tmp25_;
					if (!bird_font_settings_display_update_key_bindings) {
						BirdFontMenuItem* _tmp23_;
						_tmp23_ = item;
						_tmp22_ = !BIRD_FONT_IS_TOOL_ITEM (_tmp23_);
					} else {
						_tmp22_ = FALSE;
					}
					if (_tmp22_) {
						BirdFontMenuItem* _tmp24_;
						_tmp24_ = item;
						g_signal_emit_by_name (_tmp24_, "action");
						result = TRUE;
						_g_object_unref0 (item);
						_g_object_unref0 (tm);
						_g_object_unref0 (current_display);
						_g_free0 (display);
						return result;
					}
					_tmp25_ = item;
					if (BIRD_FONT_IS_TOOL_ITEM (_tmp25_)) {
						BirdFontMenuItem* _tmp26_;
						BirdFontToolItem* _tmp27_;
						BirdFontToolItem* _tmp28_;
						const gchar* _tmp29_;
						_tmp26_ = item;
						_tmp27_ = _g_object_ref0 (G_TYPE_CHECK_INSTANCE_CAST (_tmp26_, BIRD_FONT_TYPE_TOOL_ITEM, BirdFontToolItem));
						_g_object_unref0 (tm);
						tm = _tmp27_;
						_tmp28_ = tm;
						_tmp29_ = display;
						if (bird_font_menu_item_in_display ((BirdFontMenuItem*) _tmp28_, _tmp29_)) {
							BirdFontToolItem* _tmp30_;
							BirdFontTool* _tmp31_;
							_tmp30_ = tm;
							_tmp31_ = _tmp30_->tool;
							if (_tmp31_->editor_events) {
								BirdFontToolbox* _tmp32_;
								BirdFontToolbox* _tmp33_;
								BirdFontToolItem* _tmp34_;
								BirdFontTool* _tmp35_;
								BirdFontToolItem* _tmp36_;
								BirdFontTool* _tmp37_;
								BirdFontToolItem* _tmp38_;
								BirdFontTool* _tmp39_;
								_tmp32_ = bird_font_main_window_get_toolbox ();
								_tmp33_ = _tmp32_;
								_tmp34_ = tm;
								_tmp35_ = _tmp34_->tool;
								bird_font_toolbox_set_current_tool (_tmp33_, _tmp35_);
								_g_object_unref0 (_tmp33_);
								_tmp36_ = tm;
								_tmp37_ = _tmp36_->tool;
								_tmp38_ = tm;
								_tmp39_ = _tmp38_->tool;
								g_signal_emit_by_name (_tmp37_, "select-action", _tmp39_);
								result = TRUE;
								_g_object_unref0 (item);
								_g_object_unref0 (tm);
								_g_object_unref0 (current_display);
								_g_free0 (display);
								return result;
							} else {
								BirdFontToolItem* _tmp40_;
								BirdFontTool* _tmp41_;
								BirdFontToolItem* _tmp42_;
								BirdFontTool* _tmp43_;
								_tmp40_ = tm;
								_tmp41_ = _tmp40_->tool;
								_tmp42_ = tm;
								_tmp43_ = _tmp42_->tool;
								g_signal_emit_by_name (_tmp41_, "select-action", _tmp43_);
								result = TRUE;
								_g_object_unref0 (item);
								_g_object_unref0 (tm);
								_g_object_unref0 (current_display);
								_g_free0 (display);
								return result;
							}
						}
					}
				}
			}
			_g_object_unref0 (item);
		}
	}
	result = FALSE;
	_g_object_unref0 (tm);
	_g_object_unref0 (current_display);
	_g_free0 (display);
	return result;
}

void
bird_font_abstract_menu_load_key_bindings (BirdFontAbstractMenu* self)
{
	GFile* default_key_bindings = NULL;
	GFile* _tmp0_;
	GFile* user_key_bindings = NULL;
	GFile* _tmp1_;
	GFile* _tmp2_;
	GFile* _tmp3_;
	GFile* _tmp4_;
	GFile* _tmp5_;
	GFile* _tmp7_;
	g_return_if_fail (self != NULL);
	_tmp0_ = bird_font_search_paths_find_file (NULL, "key_bindings.xml");
	default_key_bindings = _tmp0_;
	_tmp1_ = bird_font_bird_font_get_settings_directory ();
	_tmp2_ = _tmp1_;
	_tmp3_ = bird_font_get_child (_tmp2_, "key_bindings.xml");
	_tmp4_ = _tmp3_;
	_g_object_unref0 (_tmp2_);
	user_key_bindings = _tmp4_;
	_tmp5_ = default_key_bindings;
	if (g_file_query_exists (_tmp5_, NULL)) {
		GFile* _tmp6_;
		_tmp6_ = default_key_bindings;
		bird_font_abstract_menu_parse_key_bindings (self, _tmp6_);
	}
	_tmp7_ = user_key_bindings;
	if (g_file_query_exists (_tmp7_, NULL)) {
		GFile* _tmp8_;
		_tmp8_ = user_key_bindings;
		bird_font_abstract_menu_parse_key_bindings (self, _tmp8_);
	}
	_g_object_unref0 (user_key_bindings);
	_g_object_unref0 (default_key_bindings);
}

void
bird_font_abstract_menu_parse_key_bindings (BirdFontAbstractMenu* self,
                                            GFile* f)
{
	gchar* xml_data = NULL;
	BXmlParser* parser = NULL;
	GError* _inner_error0_ = NULL;
	g_return_if_fail (self != NULL);
	g_return_if_fail (f != NULL);
	{
		gchar* _tmp0_;
		gchar* _tmp1_;
		gchar* _tmp2_ = NULL;
		BXmlParser* _tmp3_;
		BXmlParser* _tmp4_;
		BTag* _tmp5_;
		BTag* _tmp6_;
		_tmp0_ = g_file_get_path (f);
		_tmp1_ = (gchar*) _tmp0_;
		g_file_get_contents (_tmp1_, &_tmp2_, NULL, &_inner_error0_);
		_g_free0 (xml_data);
		xml_data = _tmp2_;
		_g_free0 (_tmp1_);
		if (G_UNLIKELY (_inner_error0_ != NULL)) {
			goto __catch0_g_error;
		}
		_tmp3_ = b_xml_parser_new (xml_data);
		_g_object_unref0 (parser);
		parser = _tmp3_;
		_tmp4_ = parser;
		_tmp5_ = b_xml_parser_get_root_tag (_tmp4_);
		_tmp6_ = _tmp5_;
		bird_font_abstract_menu_parse_bindings (self, _tmp6_);
		_g_object_unref0 (_tmp6_);
	}
	goto __finally0;
	__catch0_g_error:
	{
		GError* e = NULL;
		GError* _tmp7_;
		const gchar* _tmp8_;
		e = _inner_error0_;
		_inner_error0_ = NULL;
		_tmp7_ = e;
		_tmp8_ = _tmp7_->message;
		g_warning ("AbstractMenu.vala:146: %s", _tmp8_);
		_g_error_free0 (e);
	}
	__finally0:
	if (G_UNLIKELY (_inner_error0_ != NULL)) {
		_g_object_unref0 (parser);
		_g_free0 (xml_data);
		g_critical ("file %s: line %d: uncaught error: %s (%s, %d)", __FILE__, __LINE__, _inner_error0_->message, g_quark_to_string (_inner_error0_->domain), _inner_error0_->code);
		g_clear_error (&_inner_error0_);
		return;
	}
	_g_object_unref0 (parser);
	_g_free0 (xml_data);
}

void
bird_font_abstract_menu_parse_bindings (BirdFontAbstractMenu* self,
                                        BTag* tag)
{
	g_return_if_fail (self != NULL);
	g_return_if_fail (tag != NULL);
	{
		BTagIterator* _t_it = NULL;
		BTagIterator* _tmp0_;
		_tmp0_ = b_tag_iterator (tag);
		_t_it = _tmp0_;
		while (TRUE) {
			BTagIterator* _tmp1_;
			BTag* t = NULL;
			BTagIterator* _tmp2_;
			BTag* _tmp3_;
			BTag* _tmp4_;
			gchar* _tmp5_;
			gchar* _tmp6_;
			gboolean _tmp7_;
			_tmp1_ = _t_it;
			if (!b_tag_iterator_next (_tmp1_)) {
				break;
			}
			_tmp2_ = _t_it;
			_tmp3_ = b_tag_iterator_get (_tmp2_);
			t = _tmp3_;
			_tmp4_ = t;
			_tmp5_ = b_tag_get_name (_tmp4_);
			_tmp6_ = _tmp5_;
			_tmp7_ = g_strcmp0 (_tmp6_, "action") == 0;
			_g_free0 (_tmp6_);
			if (_tmp7_) {
				BTag* _tmp8_;
				BAttributes* _tmp9_;
				BAttributes* _tmp10_;
				_tmp8_ = t;
				_tmp9_ = b_tag_get_attributes (_tmp8_);
				_tmp10_ = _tmp9_;
				bird_font_abstract_menu_parse_binding (self, _tmp10_);
				_g_object_unref0 (_tmp10_);
			}
			_g_object_unref0 (t);
		}
		_g_object_unref0 (_t_it);
	}
}

static gunichar
string_get_char (const gchar* self,
                 glong index)
{
	gunichar result;
	g_return_val_if_fail (self != NULL, 0U);
	result = g_utf8_get_char (((gchar*) self) + index);
	return result;
}

void
bird_font_abstract_menu_parse_binding (BirdFontAbstractMenu* self,
                                       BAttributes* attr)
{
	guint modifier = 0U;
	gunichar key = 0U;
	gchar* action = NULL;
	gchar* _tmp0_;
	BirdFontMenuItem* menu_action = NULL;
	BirdFontMenuItem* ma = NULL;
	GeeHashMap* _tmp50_;
	const gchar* _tmp51_;
	gpointer _tmp52_;
	BirdFontMenuItem* _tmp53_;
	g_return_if_fail (self != NULL);
	g_return_if_fail (attr != NULL);
	modifier = BIRD_FONT_NONE;
	key = (gunichar) '\0';
	_tmp0_ = g_strdup ("");
	action = _tmp0_;
	{
		BAttributesIterator* _a_it = NULL;
		BAttributesIterator* _tmp1_;
		_tmp1_ = b_attributes_iterator (attr);
		_a_it = _tmp1_;
		while (TRUE) {
			BAttributesIterator* _tmp2_;
			BAttribute* a = NULL;
			BAttributesIterator* _tmp3_;
			BAttribute* _tmp4_;
			BAttribute* _tmp5_;
			gchar* _tmp6_;
			gchar* _tmp7_;
			gboolean _tmp8_;
			gboolean _tmp12_ = FALSE;
			BAttribute* _tmp13_;
			gchar* _tmp14_;
			gchar* _tmp15_;
			gboolean _tmp16_;
			gboolean _tmp20_ = FALSE;
			BAttribute* _tmp21_;
			gchar* _tmp22_;
			gchar* _tmp23_;
			gboolean _tmp24_;
			gboolean _tmp28_ = FALSE;
			BAttribute* _tmp29_;
			gchar* _tmp30_;
			gchar* _tmp31_;
			gboolean _tmp32_;
			gboolean _tmp36_ = FALSE;
			BAttribute* _tmp37_;
			gchar* _tmp38_;
			gchar* _tmp39_;
			gboolean _tmp40_;
			BAttribute* _tmp44_;
			gchar* _tmp45_;
			gchar* _tmp46_;
			gboolean _tmp47_;
			_tmp2_ = _a_it;
			if (!b_attributes_iterator_next (_tmp2_)) {
				break;
			}
			_tmp3_ = _a_it;
			_tmp4_ = b_attributes_iterator_get (_tmp3_);
			a = _tmp4_;
			_tmp5_ = a;
			_tmp6_ = b_attribute_get_name (_tmp5_);
			_tmp7_ = _tmp6_;
			_tmp8_ = g_strcmp0 (_tmp7_, "key") == 0;
			_g_free0 (_tmp7_);
			if (_tmp8_) {
				BAttribute* _tmp9_;
				gchar* _tmp10_;
				gchar* _tmp11_;
				_tmp9_ = a;
				_tmp10_ = b_attribute_get_content (_tmp9_);
				_tmp11_ = _tmp10_;
				key = string_get_char (_tmp11_, (glong) 0);
				_g_free0 (_tmp11_);
			}
			_tmp13_ = a;
			_tmp14_ = b_attribute_get_name (_tmp13_);
			_tmp15_ = _tmp14_;
			_tmp16_ = g_strcmp0 (_tmp15_, "ctrl") == 0;
			_g_free0 (_tmp15_);
			if (_tmp16_) {
				BAttribute* _tmp17_;
				gchar* _tmp18_;
				gchar* _tmp19_;
				_tmp17_ = a;
				_tmp18_ = b_attribute_get_content (_tmp17_);
				_tmp19_ = _tmp18_;
				_tmp12_ = g_strcmp0 (_tmp19_, "true") == 0;
				_g_free0 (_tmp19_);
			} else {
				_tmp12_ = FALSE;
			}
			if (_tmp12_) {
				modifier |= BIRD_FONT_CTRL;
			}
			_tmp21_ = a;
			_tmp22_ = b_attribute_get_name (_tmp21_);
			_tmp23_ = _tmp22_;
			_tmp24_ = g_strcmp0 (_tmp23_, "alt") == 0;
			_g_free0 (_tmp23_);
			if (_tmp24_) {
				BAttribute* _tmp25_;
				gchar* _tmp26_;
				gchar* _tmp27_;
				_tmp25_ = a;
				_tmp26_ = b_attribute_get_content (_tmp25_);
				_tmp27_ = _tmp26_;
				_tmp20_ = g_strcmp0 (_tmp27_, "true") == 0;
				_g_free0 (_tmp27_);
			} else {
				_tmp20_ = FALSE;
			}
			if (_tmp20_) {
				modifier |= BIRD_FONT_ALT;
			}
			_tmp29_ = a;
			_tmp30_ = b_attribute_get_name (_tmp29_);
			_tmp31_ = _tmp30_;
			_tmp32_ = g_strcmp0 (_tmp31_, "command") == 0;
			_g_free0 (_tmp31_);
			if (_tmp32_) {
				BAttribute* _tmp33_;
				gchar* _tmp34_;
				gchar* _tmp35_;
				_tmp33_ = a;
				_tmp34_ = b_attribute_get_content (_tmp33_);
				_tmp35_ = _tmp34_;
				_tmp28_ = g_strcmp0 (_tmp35_, "true") == 0;
				_g_free0 (_tmp35_);
			} else {
				_tmp28_ = FALSE;
			}
			if (_tmp28_) {
				modifier |= BIRD_FONT_LOGO;
			}
			_tmp37_ = a;
			_tmp38_ = b_attribute_get_name (_tmp37_);
			_tmp39_ = _tmp38_;
			_tmp40_ = g_strcmp0 (_tmp39_, "shift") == 0;
			_g_free0 (_tmp39_);
			if (_tmp40_) {
				BAttribute* _tmp41_;
				gchar* _tmp42_;
				gchar* _tmp43_;
				_tmp41_ = a;
				_tmp42_ = b_attribute_get_content (_tmp41_);
				_tmp43_ = _tmp42_;
				_tmp36_ = g_strcmp0 (_tmp43_, "true") == 0;
				_g_free0 (_tmp43_);
			} else {
				_tmp36_ = FALSE;
			}
			if (_tmp36_) {
				modifier |= BIRD_FONT_SHIFT;
			}
			_tmp44_ = a;
			_tmp45_ = b_attribute_get_name (_tmp44_);
			_tmp46_ = _tmp45_;
			_tmp47_ = g_strcmp0 (_tmp46_, "action") == 0;
			_g_free0 (_tmp46_);
			if (_tmp47_) {
				BAttribute* _tmp48_;
				gchar* _tmp49_;
				_tmp48_ = a;
				_tmp49_ = b_attribute_get_content (_tmp48_);
				_g_free0 (action);
				action = _tmp49_;
			}
			_g_object_unref0 (a);
		}
		_g_object_unref0 (_a_it);
	}
	_tmp50_ = self->menu_items;
	_tmp51_ = action;
	_tmp52_ = gee_abstract_map_get ((GeeAbstractMap*) _tmp50_, _tmp51_);
	_g_object_unref0 (ma);
	ma = (BirdFontMenuItem*) _tmp52_;
	_tmp53_ = ma;
	if (_tmp53_ != NULL) {
		BirdFontMenuItem* _tmp54_;
		BirdFontMenuItem* _tmp55_;
		BirdFontMenuItem* _tmp56_;
		BirdFontMenuItem* _tmp57_;
		_tmp54_ = ma;
		_tmp55_ = _g_object_ref0 (G_TYPE_CHECK_INSTANCE_CAST (_tmp54_, BIRD_FONT_TYPE_MENU_ITEM, BirdFontMenuItem));
		_g_object_unref0 (menu_action);
		menu_action = _tmp55_;
		_tmp56_ = menu_action;
		_tmp56_->modifiers = modifier;
		_tmp57_ = menu_action;
		_tmp57_->key = key;
	}
	_g_object_unref0 (ma);
	_g_object_unref0 (menu_action);
	_g_free0 (action);
}

BirdFontMenuItem*
bird_font_abstract_menu_add_menu_item (BirdFontAbstractMenu* self,
                                       const gchar* label,
                                       const gchar* description,
                                       const gchar* display)
{
	BirdFontMenuItem* i = NULL;
	BirdFontMenuItem* _tmp0_;
	BirdFontMenuItem* result;
	g_return_val_if_fail (self != NULL, NULL);
	g_return_val_if_fail (label != NULL, NULL);
	g_return_val_if_fail (description != NULL, NULL);
	g_return_val_if_fail (display != NULL, NULL);
	_tmp0_ = bird_font_menu_item_new (label, description);
	i = _tmp0_;
	if (g_strcmp0 (description, "") != 0) {
		GeeHashMap* _tmp1_;
		BirdFontMenuItem* _tmp2_;
		GeeArrayList* _tmp3_;
		BirdFontMenuItem* _tmp4_;
		_tmp1_ = self->menu_items;
		_tmp2_ = i;
		gee_abstract_map_set ((GeeAbstractMap*) _tmp1_, description, _tmp2_);
		_tmp3_ = self->sorted_menu_items;
		_tmp4_ = i;
		gee_abstract_collection_add ((GeeAbstractCollection*) _tmp3_, _tmp4_);
	}
	if (g_strcmp0 (display, "") != 0) {
		BirdFontMenuItem* _tmp5_;
		_tmp5_ = i;
		bird_font_menu_item_add_display (_tmp5_, display);
	}
	result = i;
	return result;
}

void
bird_font_abstract_menu_button_release (BirdFontAbstractMenu* self,
                                        gint button,
                                        gdouble ex,
                                        gdouble ey)
{
	gdouble y = 0.0;
	gdouble x = 0.0;
	BirdFontWidgetAllocation* _tmp0_;
	g_return_if_fail (self != NULL);
	y = (gdouble) 0;
	_tmp0_ = self->priv->allocation;
	x = _tmp0_->width - self->priv->width;
	if (button == 1) {
		BirdFontSubMenu* _tmp15_;
		BirdFontSubMenu* _tmp16_;
		{
			GeeArrayList* _item_list = NULL;
			BirdFontSubMenu* _tmp1_;
			GeeArrayList* _tmp2_;
			gint _item_size = 0;
			GeeArrayList* _tmp3_;
			gint _tmp4_;
			gint _tmp5_;
			gint _item_index = 0;
			_tmp1_ = self->priv->current_menu;
			_tmp2_ = _tmp1_->items;
			_item_list = _tmp2_;
			_tmp3_ = _item_list;
			_tmp4_ = gee_abstract_collection_get_size ((GeeAbstractCollection*) _tmp3_);
			_tmp5_ = _tmp4_;
			_item_size = _tmp5_;
			_item_index = -1;
			while (TRUE) {
				gint _tmp6_;
				gint _tmp7_;
				BirdFontMenuItem* item = NULL;
				GeeArrayList* _tmp8_;
				gpointer _tmp9_;
				gboolean _tmp10_ = FALSE;
				BirdFontWidgetAllocation* _tmp11_;
				gdouble _tmp12_;
				_item_index = _item_index + 1;
				_tmp6_ = _item_index;
				_tmp7_ = _item_size;
				if (!(_tmp6_ < _tmp7_)) {
					break;
				}
				_tmp8_ = _item_list;
				_tmp9_ = gee_abstract_list_get ((GeeAbstractList*) _tmp8_, _item_index);
				item = (BirdFontMenuItem*) _tmp9_;
				_tmp11_ = self->priv->allocation;
				_tmp12_ = ex;
				if ((x <= _tmp12_) && (_tmp12_ < ((gdouble) _tmp11_->width))) {
					gdouble _tmp13_;
					_tmp13_ = ey;
					_tmp10_ = (y <= _tmp13_) && (_tmp13_ <= (y + self->priv->height));
				} else {
					_tmp10_ = FALSE;
				}
				if (_tmp10_) {
					BirdFontMenuItem* _tmp14_;
					_tmp14_ = item;
					g_signal_emit_by_name (_tmp14_, "action");
					bird_font_glyph_canvas_redraw ();
					_g_object_unref0 (item);
					return;
				}
				y += self->priv->height;
				_g_object_unref0 (item);
			}
		}
		bird_font_abstract_menu_set_show_menu (self, FALSE);
		_tmp15_ = self->top_menu;
		_tmp16_ = _g_object_ref0 (G_TYPE_CHECK_INSTANCE_CAST (_tmp15_, BIRD_FONT_TYPE_SUB_MENU, BirdFontSubMenu));
		_g_object_unref0 (self->priv->current_menu);
		self->priv->current_menu = _tmp16_;
		bird_font_glyph_canvas_redraw ();
	}
}

void
bird_font_abstract_menu_add_tool_key_bindings (BirdFontAbstractMenu* self)
{
	BirdFontToolItem* tool_item = NULL;
	g_return_if_fail (self != NULL);
	{
		GeeArrayList* _tool_set_list = NULL;
		BirdFontToolbox* _tmp0_;
		BirdFontToolbox* _tmp1_;
		GeeArrayList* _tmp2_;
		GeeArrayList* _tmp3_;
		gint _tool_set_size = 0;
		GeeArrayList* _tmp4_;
		gint _tmp5_;
		gint _tmp6_;
		gint _tool_set_index = 0;
		_tmp0_ = bird_font_main_window_get_toolbox ();
		_tmp1_ = _tmp0_;
		_tmp2_ = _tmp1_->tool_sets;
		_tmp3_ = _tmp2_;
		_g_object_unref0 (_tmp1_);
		_tool_set_list = _tmp3_;
		_tmp4_ = _tool_set_list;
		_tmp5_ = gee_abstract_collection_get_size ((GeeAbstractCollection*) _tmp4_);
		_tmp6_ = _tmp5_;
		_tool_set_size = _tmp6_;
		_tool_set_index = -1;
		while (TRUE) {
			gint _tmp7_;
			gint _tmp8_;
			BirdFontToolCollection* tool_set = NULL;
			GeeArrayList* _tmp9_;
			gpointer _tmp10_;
			_tool_set_index = _tool_set_index + 1;
			_tmp7_ = _tool_set_index;
			_tmp8_ = _tool_set_size;
			if (!(_tmp7_ < _tmp8_)) {
				break;
			}
			_tmp9_ = _tool_set_list;
			_tmp10_ = gee_abstract_list_get ((GeeAbstractList*) _tmp9_, _tool_set_index);
			tool_set = (BirdFontToolCollection*) _tmp10_;
			{
				GeeArrayList* _e_list = NULL;
				BirdFontToolCollection* _tmp11_;
				GeeArrayList* _tmp12_;
				gint _e_size = 0;
				GeeArrayList* _tmp13_;
				gint _tmp14_;
				gint _tmp15_;
				gint _e_index = 0;
				_tmp11_ = tool_set;
				_tmp12_ = bird_font_tool_collection_get_expanders (_tmp11_);
				_e_list = _tmp12_;
				_tmp13_ = _e_list;
				_tmp14_ = gee_abstract_collection_get_size ((GeeAbstractCollection*) _tmp13_);
				_tmp15_ = _tmp14_;
				_e_size = _tmp15_;
				_e_index = -1;
				while (TRUE) {
					gint _tmp16_;
					gint _tmp17_;
					BirdFontExpander* e = NULL;
					GeeArrayList* _tmp18_;
					gpointer _tmp19_;
					_e_index = _e_index + 1;
					_tmp16_ = _e_index;
					_tmp17_ = _e_size;
					if (!(_tmp16_ < _tmp17_)) {
						break;
					}
					_tmp18_ = _e_list;
					_tmp19_ = gee_abstract_list_get ((GeeAbstractList*) _tmp18_, _e_index);
					e = (BirdFontExpander*) _tmp19_;
					{
						GeeArrayList* _t_list = NULL;
						BirdFontExpander* _tmp20_;
						GeeArrayList* _tmp21_;
						gint _t_size = 0;
						GeeArrayList* _tmp22_;
						gint _tmp23_;
						gint _tmp24_;
						gint _t_index = 0;
						_tmp20_ = e;
						_tmp21_ = _tmp20_->tool;
						_t_list = _tmp21_;
						_tmp22_ = _t_list;
						_tmp23_ = gee_abstract_collection_get_size ((GeeAbstractCollection*) _tmp22_);
						_tmp24_ = _tmp23_;
						_t_size = _tmp24_;
						_t_index = -1;
						while (TRUE) {
							gint _tmp25_;
							gint _tmp26_;
							BirdFontTool* t = NULL;
							GeeArrayList* _tmp27_;
							gpointer _tmp28_;
							BirdFontTool* _tmp29_;
							BirdFontToolItem* _tmp30_;
							gboolean _tmp31_ = FALSE;
							BirdFontToolItem* _tmp32_;
							const gchar* _tmp33_;
							_t_index = _t_index + 1;
							_tmp25_ = _t_index;
							_tmp26_ = _t_size;
							if (!(_tmp25_ < _tmp26_)) {
								break;
							}
							_tmp27_ = _t_list;
							_tmp28_ = gee_abstract_list_get ((GeeAbstractList*) _tmp27_, _t_index);
							t = (BirdFontTool*) _tmp28_;
							_tmp29_ = t;
							_tmp30_ = bird_font_tool_item_new (_tmp29_);
							_g_object_unref0 (tool_item);
							tool_item = _tmp30_;
							_tmp32_ = tool_item;
							_tmp33_ = ((BirdFontMenuItem*) _tmp32_)->identifier;
							if (g_strcmp0 (_tmp33_, "") != 0) {
								BirdFontToolItem* _tmp34_;
								const gchar* _tmp35_;
								_tmp34_ = tool_item;
								_tmp35_ = ((BirdFontMenuItem*) _tmp34_)->identifier;
								_tmp31_ = !bird_font_abstract_menu_has_menu_item (self, _tmp35_);
							} else {
								_tmp31_ = FALSE;
							}
							if (_tmp31_) {
								GeeHashMap* _tmp36_;
								BirdFontToolItem* _tmp37_;
								const gchar* _tmp38_;
								BirdFontToolItem* _tmp39_;
								GeeArrayList* _tmp40_;
								BirdFontToolItem* _tmp41_;
								_tmp36_ = self->menu_items;
								_tmp37_ = tool_item;
								_tmp38_ = ((BirdFontMenuItem*) _tmp37_)->identifier;
								_tmp39_ = tool_item;
								gee_abstract_map_set ((GeeAbstractMap*) _tmp36_, _tmp38_, (BirdFontMenuItem*) _tmp39_);
								_tmp40_ = self->sorted_menu_items;
								_tmp41_ = tool_item;
								gee_abstract_collection_add ((GeeAbstractCollection*) _tmp40_, (BirdFontMenuItem*) _tmp41_);
							}
							{
								GeeArrayList* _d_list = NULL;
								BirdFontToolCollection* _tmp42_;
								GeeArrayList* _tmp43_;
								gint _d_size = 0;
								GeeArrayList* _tmp44_;
								gint _tmp45_;
								gint _tmp46_;
								gint _d_index = 0;
								_tmp42_ = tool_set;
								_tmp43_ = bird_font_tool_collection_get_displays (_tmp42_);
								_d_list = _tmp43_;
								_tmp44_ = _d_list;
								_tmp45_ = gee_abstract_collection_get_size ((GeeAbstractCollection*) _tmp44_);
								_tmp46_ = _tmp45_;
								_d_size = _tmp46_;
								_d_index = -1;
								while (TRUE) {
									gint _tmp47_;
									gint _tmp48_;
									gchar* d = NULL;
									GeeArrayList* _tmp49_;
									gpointer _tmp50_;
									BirdFontToolItem* _tmp51_;
									const gchar* _tmp52_;
									_d_index = _d_index + 1;
									_tmp47_ = _d_index;
									_tmp48_ = _d_size;
									if (!(_tmp47_ < _tmp48_)) {
										break;
									}
									_tmp49_ = _d_list;
									_tmp50_ = gee_abstract_list_get ((GeeAbstractList*) _tmp49_, _d_index);
									d = (gchar*) _tmp50_;
									_tmp51_ = tool_item;
									_tmp52_ = d;
									bird_font_menu_item_add_display ((BirdFontMenuItem*) _tmp51_, _tmp52_);
									_g_free0 (d);
								}
								_g_object_unref0 (_d_list);
							}
							_g_object_unref0 (t);
						}
					}
					_g_object_unref0 (e);
				}
				_g_object_unref0 (_e_list);
			}
			_g_object_unref0 (tool_set);
		}
	}
	_g_object_unref0 (tool_item);
}

gboolean
bird_font_abstract_menu_has_menu_item (BirdFontAbstractMenu* self,
                                       const gchar* identifier)
{
	gboolean result;
	g_return_val_if_fail (self != NULL, FALSE);
	g_return_val_if_fail (identifier != NULL, FALSE);
	{
		GeeArrayList* _mi_list = NULL;
		GeeArrayList* _tmp0_;
		gint _mi_size = 0;
		GeeArrayList* _tmp1_;
		gint _tmp2_;
		gint _tmp3_;
		gint _mi_index = 0;
		_tmp0_ = self->sorted_menu_items;
		_mi_list = _tmp0_;
		_tmp1_ = _mi_list;
		_tmp2_ = gee_abstract_collection_get_size ((GeeAbstractCollection*) _tmp1_);
		_tmp3_ = _tmp2_;
		_mi_size = _tmp3_;
		_mi_index = -1;
		while (TRUE) {
			gint _tmp4_;
			gint _tmp5_;
			BirdFontMenuItem* mi = NULL;
			GeeArrayList* _tmp6_;
			gpointer _tmp7_;
			BirdFontMenuItem* _tmp8_;
			const gchar* _tmp9_;
			_mi_index = _mi_index + 1;
			_tmp4_ = _mi_index;
			_tmp5_ = _mi_size;
			if (!(_tmp4_ < _tmp5_)) {
				break;
			}
			_tmp6_ = _mi_list;
			_tmp7_ = gee_abstract_list_get ((GeeAbstractList*) _tmp6_, _mi_index);
			mi = (BirdFontMenuItem*) _tmp7_;
			_tmp8_ = mi;
			_tmp9_ = _tmp8_->identifier;
			if (g_strcmp0 (_tmp9_, identifier) == 0) {
				result = TRUE;
				_g_object_unref0 (mi);
				return result;
			}
			_g_object_unref0 (mi);
		}
	}
	result = FALSE;
	return result;
}

void
bird_font_abstract_menu_set_menu (BirdFontAbstractMenu* self,
                                  BirdFontSubMenu* m)
{
	BirdFontSubMenu* _tmp0_;
	g_return_if_fail (self != NULL);
	g_return_if_fail (m != NULL);
	_tmp0_ = _g_object_ref0 (m);
	_g_object_unref0 (self->priv->current_menu);
	self->priv->current_menu = _tmp0_;
	bird_font_glyph_canvas_redraw ();
}

gdouble
bird_font_abstract_menu_layout_width (BirdFontAbstractMenu* self)
{
	BirdFontText* key_binding = NULL;
	BirdFontText* _tmp0_;
	gdouble font_size = 0.0;
	gdouble w = 0.0;
	gdouble result;
	g_return_val_if_fail (self != NULL, 0.0);
	_tmp0_ = bird_font_text_new ("", (gdouble) 17, (gdouble) 0);
	key_binding = _tmp0_;
	font_size = (gdouble) 17;
	self->priv->width = (gdouble) 0;
	{
		GeeArrayList* _item_list = NULL;
		BirdFontSubMenu* _tmp1_;
		GeeArrayList* _tmp2_;
		gint _item_size = 0;
		GeeArrayList* _tmp3_;
		gint _tmp4_;
		gint _tmp5_;
		gint _item_index = 0;
		_tmp1_ = self->priv->current_menu;
		_tmp2_ = _tmp1_->items;
		_item_list = _tmp2_;
		_tmp3_ = _item_list;
		_tmp4_ = gee_abstract_collection_get_size ((GeeAbstractCollection*) _tmp3_);
		_tmp5_ = _tmp4_;
		_item_size = _tmp5_;
		_item_index = -1;
		while (TRUE) {
			gint _tmp6_;
			gint _tmp7_;
			BirdFontMenuItem* item = NULL;
			GeeArrayList* _tmp8_;
			gpointer _tmp9_;
			BirdFontText* _tmp10_;
			BirdFontMenuItem* _tmp11_;
			gchar* _tmp12_;
			gchar* _tmp13_;
			BirdFontMenuItem* _tmp14_;
			BirdFontText* _tmp15_;
			BirdFontText* _tmp16_;
			BirdFontMenuItem* _tmp17_;
			BirdFontText* _tmp18_;
			BirdFontText* _tmp19_;
			_item_index = _item_index + 1;
			_tmp6_ = _item_index;
			_tmp7_ = _item_size;
			if (!(_tmp6_ < _tmp7_)) {
				break;
			}
			_tmp8_ = _item_list;
			_tmp9_ = gee_abstract_list_get ((GeeAbstractList*) _tmp8_, _item_index);
			item = (BirdFontMenuItem*) _tmp9_;
			_tmp10_ = key_binding;
			_tmp11_ = item;
			_tmp12_ = bird_font_menu_item_get_key_bindings (_tmp11_);
			_tmp13_ = _tmp12_;
			bird_font_text_set_text (_tmp10_, _tmp13_);
			_g_free0 (_tmp13_);
			_tmp14_ = item;
			_tmp15_ = _tmp14_->label;
			bird_font_text_set_font_size (_tmp15_, font_size);
			_tmp16_ = key_binding;
			bird_font_text_set_font_size (_tmp16_, font_size);
			_tmp17_ = item;
			_tmp18_ = _tmp17_->label;
			w = bird_font_text_get_extent (_tmp18_);
			_tmp19_ = key_binding;
			w += bird_font_text_get_extent (_tmp19_);
			w += 3 * self->priv->height;
			if (w > self->priv->width) {
				self->priv->width = w;
			}
			_g_object_unref0 (item);
		}
	}
	result = self->priv->width;
	_g_object_unref0 (key_binding);
	return result;
}

void
bird_font_abstract_menu_draw (BirdFontAbstractMenu* self,
                              BirdFontWidgetAllocation* allocation,
                              cairo_t* cr)
{
	gdouble y = 0.0;
	gdouble x = 0.0;
	gdouble label_x = 0.0;
	gdouble label_y = 0.0;
	gdouble font_size = 0.0;
	BirdFontText* key_binding = NULL;
	gdouble binding_extent = 0.0;
	BirdFontText* _tmp0_;
	BirdFontWidgetAllocation* _tmp1_;
	g_return_if_fail (self != NULL);
	g_return_if_fail (allocation != NULL);
	g_return_if_fail (cr != NULL);
	self->priv->width = bird_font_abstract_menu_layout_width (self);
	_tmp0_ = bird_font_text_new ("", (gdouble) 17, (gdouble) 0);
	_g_object_unref0 (key_binding);
	key_binding = _tmp0_;
	x = allocation->width - self->priv->width;
	y = (gdouble) 0;
	font_size = (gdouble) 17;
	_tmp1_ = _g_object_ref0 (allocation);
	_g_object_unref0 (self->priv->allocation);
	self->priv->allocation = _tmp1_;
	{
		GeeArrayList* _item_list = NULL;
		BirdFontSubMenu* _tmp2_;
		GeeArrayList* _tmp3_;
		gint _item_size = 0;
		GeeArrayList* _tmp4_;
		gint _tmp5_;
		gint _tmp6_;
		gint _item_index = 0;
		_tmp2_ = self->priv->current_menu;
		_tmp3_ = _tmp2_->items;
		_item_list = _tmp3_;
		_tmp4_ = _item_list;
		_tmp5_ = gee_abstract_collection_get_size ((GeeAbstractCollection*) _tmp4_);
		_tmp6_ = _tmp5_;
		_item_size = _tmp6_;
		_item_index = -1;
		while (TRUE) {
			gint _tmp7_;
			gint _tmp8_;
			BirdFontMenuItem* item = NULL;
			GeeArrayList* _tmp9_;
			gpointer _tmp10_;
			BirdFontMenuItem* _tmp11_;
			BirdFontText* _tmp12_;
			BirdFontMenuItem* _tmp13_;
			BirdFontText* _tmp14_;
			BirdFontText* _tmp15_;
			BirdFontMenuItem* _tmp16_;
			gchar* _tmp17_;
			gchar* _tmp18_;
			BirdFontText* _tmp19_;
			BirdFontText* _tmp20_;
			BirdFontText* _tmp21_;
			BirdFontText* _tmp22_;
			BirdFontText* _tmp23_;
			_item_index = _item_index + 1;
			_tmp7_ = _item_index;
			_tmp8_ = _item_size;
			if (!(_tmp7_ < _tmp8_)) {
				break;
			}
			_tmp9_ = _item_list;
			_tmp10_ = gee_abstract_list_get ((GeeAbstractList*) _tmp9_, _item_index);
			item = (BirdFontMenuItem*) _tmp10_;
			cairo_save (cr);
			bird_font_theme_color (cr, "Menu Background");
			cairo_rectangle (cr, x, y, self->priv->width, self->priv->height);
			cairo_fill (cr);
			cairo_restore (cr);
			cairo_save (cr);
			label_x = (allocation->width - self->priv->width) + (0.7 * self->priv->height);
			label_y = (y + font_size) - 1;
			_tmp11_ = item;
			_tmp12_ = _tmp11_->label;
			bird_font_theme_text_color (_tmp12_, "Menu Foreground");
			_tmp13_ = item;
			_tmp14_ = _tmp13_->label;
			bird_font_text_draw_at_baseline (_tmp14_, cr, label_x, label_y, "");
			_tmp15_ = key_binding;
			_tmp16_ = item;
			_tmp17_ = bird_font_menu_item_get_key_bindings (_tmp16_);
			_tmp18_ = _tmp17_;
			bird_font_text_set_text (_tmp15_, _tmp18_);
			_g_free0 (_tmp18_);
			_tmp19_ = key_binding;
			bird_font_text_set_font_size (_tmp19_, font_size);
			_tmp20_ = key_binding;
			binding_extent = bird_font_text_get_extent (_tmp20_);
			label_x = ((x + self->priv->width) - binding_extent) - (0.6 * self->priv->height);
			_tmp21_ = key_binding;
			bird_font_text_set_font_size (_tmp21_, font_size);
			_tmp22_ = key_binding;
			bird_font_theme_text_color (_tmp22_, "Menu Foreground");
			_tmp23_ = key_binding;
			bird_font_text_draw_at_baseline (_tmp23_, cr, label_x, label_y, "");
			y += self->priv->height;
			_g_object_unref0 (item);
		}
	}
	_g_object_unref0 (key_binding);
}

static gchar*
g_unichar_to_string (gunichar self)
{
	gchar* str = NULL;
	gchar* _tmp0_;
	gchar* result;
	_tmp0_ = g_new0 (gchar, 7);
	str = (gchar*) _tmp0_;
	g_unichar_to_utf8 (self, str);
	result = str;
	return result;
}

static const gchar*
string_to_string (const gchar* self)
{
	const gchar* result;
	g_return_val_if_fail (self != NULL, NULL);
	result = self;
	return result;
}

static gchar*
bool_to_string (gboolean self)
{
	gchar* result;
	if (self) {
		gchar* _tmp0_;
		_tmp0_ = g_strdup ("true");
		result = _tmp0_;
		return result;
	} else {
		gchar* _tmp1_;
		_tmp1_ = g_strdup ("false");
		result = _tmp1_;
		return result;
	}
}

void
bird_font_abstract_menu_write_key_bindings (BirdFontAbstractMenu* self)
{
	GDataOutputStream* os = NULL;
	GFile* file = NULL;
	gboolean has_ctrl = FALSE;
	gboolean has_alt = FALSE;
	gboolean has_command = FALSE;
	gboolean has_shift = FALSE;
	GFile* _tmp0_;
	GFile* _tmp1_;
	GFile* _tmp2_;
	GError* _inner_error0_ = NULL;
	g_return_if_fail (self != NULL);
	_tmp0_ = bird_font_bird_font_get_settings_directory ();
	_tmp1_ = _tmp0_;
	_tmp2_ = bird_font_get_child (_tmp1_, "key_bindings.xml");
	_g_object_unref0 (file);
	file = _tmp2_;
	_g_object_unref0 (_tmp1_);
	{
		GFile* _tmp3_;
		_tmp3_ = file;
		if (g_file_query_exists (_tmp3_, NULL)) {
			GFile* _tmp4_;
			_tmp4_ = file;
			g_file_delete (_tmp4_, NULL, &_inner_error0_);
			if (G_UNLIKELY (_inner_error0_ != NULL)) {
				goto __catch0_g_error;
			}
		}
	}
	goto __finally0;
	__catch0_g_error:
	{
		GError* e = NULL;
		GError* _tmp5_;
		const gchar* _tmp6_;
		e = _inner_error0_;
		_inner_error0_ = NULL;
		_tmp5_ = e;
		_tmp6_ = _tmp5_->message;
		g_warning ("AbstractMenu.vala:349: %s", _tmp6_);
		_g_error_free0 (e);
	}
	__finally0:
	if (G_UNLIKELY (_inner_error0_ != NULL)) {
		_g_object_unref0 (file);
		_g_object_unref0 (os);
		g_critical ("file %s: line %d: uncaught error: %s (%s, %d)", __FILE__, __LINE__, _inner_error0_->message, g_quark_to_string (_inner_error0_->domain), _inner_error0_->code);
		g_clear_error (&_inner_error0_);
		return;
	}
	{
		GFileOutputStream* _tmp7_ = NULL;
		GFile* _tmp8_;
		GFileOutputStream* _tmp9_;
		GDataOutputStream* _tmp10_;
		GDataOutputStream* _tmp11_;
		GDataOutputStream* _tmp12_;
		GDataOutputStream* _tmp13_;
		GDataOutputStream* _tmp65_;
		GDataOutputStream* _tmp66_;
		_tmp8_ = file;
		_tmp9_ = g_file_create (_tmp8_, G_FILE_CREATE_REPLACE_DESTINATION, NULL, &_inner_error0_);
		_tmp7_ = _tmp9_;
		if (G_UNLIKELY (_inner_error0_ != NULL)) {
			goto __catch1_g_error;
		}
		_tmp10_ = g_data_output_stream_new ((GOutputStream*) _tmp7_);
		_g_object_unref0 (os);
		os = _tmp10_;
		_tmp11_ = os;
		g_data_output_stream_put_string (_tmp11_, "<?xml version=\"1.0\" encoding=\"utf-8\" standalone=\"yes\"?>", NULL, &_inner_error0_);
		if (G_UNLIKELY (_inner_error0_ != NULL)) {
			_g_object_unref0 (_tmp7_);
			goto __catch1_g_error;
		}
		_tmp12_ = os;
		g_data_output_stream_put_string (_tmp12_, "\n", NULL, &_inner_error0_);
		if (G_UNLIKELY (_inner_error0_ != NULL)) {
			_g_object_unref0 (_tmp7_);
			goto __catch1_g_error;
		}
		_tmp13_ = os;
		g_data_output_stream_put_string (_tmp13_, "<bindings>\n", NULL, &_inner_error0_);
		if (G_UNLIKELY (_inner_error0_ != NULL)) {
			_g_object_unref0 (_tmp7_);
			goto __catch1_g_error;
		}
		{
			GeeArrayList* _item_list = NULL;
			GeeArrayList* _tmp14_;
			gint _item_size = 0;
			GeeArrayList* _tmp15_;
			gint _tmp16_;
			gint _tmp17_;
			gint _item_index = 0;
			_tmp14_ = self->sorted_menu_items;
			_item_list = _tmp14_;
			_tmp15_ = _item_list;
			_tmp16_ = gee_abstract_collection_get_size ((GeeAbstractCollection*) _tmp15_);
			_tmp17_ = _tmp16_;
			_item_size = _tmp17_;
			_item_index = -1;
			while (TRUE) {
				gint _tmp18_;
				gint _tmp19_;
				BirdFontMenuItem* item = NULL;
				GeeArrayList* _tmp20_;
				gpointer _tmp21_;
				GDataOutputStream* _tmp22_;
				GDataOutputStream* _tmp23_;
				BirdFontMenuItem* _tmp24_;
				gchar* _tmp25_;
				gchar* _tmp26_;
				const gchar* _tmp27_;
				gchar* _tmp28_;
				gchar* _tmp29_;
				BirdFontMenuItem* _tmp30_;
				GDataOutputStream* _tmp31_;
				gchar* _tmp32_;
				gchar* _tmp33_;
				const gchar* _tmp34_;
				gchar* _tmp35_;
				gchar* _tmp36_;
				BirdFontMenuItem* _tmp37_;
				GDataOutputStream* _tmp38_;
				gchar* _tmp39_;
				gchar* _tmp40_;
				const gchar* _tmp41_;
				gchar* _tmp42_;
				gchar* _tmp43_;
				BirdFontMenuItem* _tmp44_;
				GDataOutputStream* _tmp45_;
				gchar* _tmp46_;
				gchar* _tmp47_;
				const gchar* _tmp48_;
				gchar* _tmp49_;
				gchar* _tmp50_;
				BirdFontMenuItem* _tmp51_;
				GDataOutputStream* _tmp52_;
				gchar* _tmp53_;
				gchar* _tmp54_;
				const gchar* _tmp55_;
				gchar* _tmp56_;
				gchar* _tmp57_;
				GDataOutputStream* _tmp58_;
				BirdFontMenuItem* _tmp59_;
				const gchar* _tmp60_;
				const gchar* _tmp61_;
				gchar* _tmp62_;
				gchar* _tmp63_;
				GDataOutputStream* _tmp64_;
				_item_index = _item_index + 1;
				_tmp18_ = _item_index;
				_tmp19_ = _item_size;
				if (!(_tmp18_ < _tmp19_)) {
					break;
				}
				_tmp20_ = _item_list;
				_tmp21_ = gee_abstract_list_get ((GeeAbstractList*) _tmp20_, _item_index);
				item = (BirdFontMenuItem*) _tmp21_;
				_tmp22_ = os;
				g_data_output_stream_put_string (_tmp22_, "\t<action ", NULL, &_inner_error0_);
				if (G_UNLIKELY (_inner_error0_ != NULL)) {
					_g_object_unref0 (item);
					_g_object_unref0 (_tmp7_);
					goto __catch1_g_error;
				}
				_tmp23_ = os;
				_tmp24_ = item;
				_tmp25_ = g_unichar_to_string (_tmp24_->key);
				_tmp26_ = (gchar*) _tmp25_;
				_tmp27_ = string_to_string (_tmp26_);
				_tmp28_ = g_strconcat ("key=\"", _tmp27_, "\" ", NULL);
				_tmp29_ = _tmp28_;
				g_data_output_stream_put_string (_tmp23_, _tmp29_, NULL, &_inner_error0_);
				_g_free0 (_tmp29_);
				_g_free0 (_tmp26_);
				if (G_UNLIKELY (_inner_error0_ != NULL)) {
					_g_object_unref0 (item);
					_g_object_unref0 (_tmp7_);
					goto __catch1_g_error;
				}
				_tmp30_ = item;
				has_ctrl = (_tmp30_->modifiers & BIRD_FONT_CTRL) > ((guint) 0);
				_tmp31_ = os;
				_tmp32_ = bool_to_string (has_ctrl);
				_tmp33_ = _tmp32_;
				_tmp34_ = string_to_string (_tmp33_);
				_tmp35_ = g_strconcat ("ctrl=\"", _tmp34_, "\" ", NULL);
				_tmp36_ = _tmp35_;
				g_data_output_stream_put_string (_tmp31_, _tmp36_, NULL, &_inner_error0_);
				_g_free0 (_tmp36_);
				_g_free0 (_tmp33_);
				if (G_UNLIKELY (_inner_error0_ != NULL)) {
					_g_object_unref0 (item);
					_g_object_unref0 (_tmp7_);
					goto __catch1_g_error;
				}
				_tmp37_ = item;
				has_alt = (_tmp37_->modifiers & BIRD_FONT_ALT) > ((guint) 0);
				_tmp38_ = os;
				_tmp39_ = bool_to_string (has_alt);
				_tmp40_ = _tmp39_;
				_tmp41_ = string_to_string (_tmp40_);
				_tmp42_ = g_strconcat ("alt=\"", _tmp41_, "\" ", NULL);
				_tmp43_ = _tmp42_;
				g_data_output_stream_put_string (_tmp38_, _tmp43_, NULL, &_inner_error0_);
				_g_free0 (_tmp43_);
				_g_free0 (_tmp40_);
				if (G_UNLIKELY (_inner_error0_ != NULL)) {
					_g_object_unref0 (item);
					_g_object_unref0 (_tmp7_);
					goto __catch1_g_error;
				}
				_tmp44_ = item;
				has_command = (_tmp44_->modifiers & BIRD_FONT_LOGO) > ((guint) 0);
				_tmp45_ = os;
				_tmp46_ = bool_to_string (has_command);
				_tmp47_ = _tmp46_;
				_tmp48_ = string_to_string (_tmp47_);
				_tmp49_ = g_strconcat ("command=\"", _tmp48_, "\" ", NULL);
				_tmp50_ = _tmp49_;
				g_data_output_stream_put_string (_tmp45_, _tmp50_, NULL, &_inner_error0_);
				_g_free0 (_tmp50_);
				_g_free0 (_tmp47_);
				if (G_UNLIKELY (_inner_error0_ != NULL)) {
					_g_object_unref0 (item);
					_g_object_unref0 (_tmp7_);
					goto __catch1_g_error;
				}
				_tmp51_ = item;
				has_shift = (_tmp51_->modifiers & BIRD_FONT_SHIFT) > ((guint) 0);
				_tmp52_ = os;
				_tmp53_ = bool_to_string (has_shift);
				_tmp54_ = _tmp53_;
				_tmp55_ = string_to_string (_tmp54_);
				_tmp56_ = g_strconcat ("shift=\"", _tmp55_, "\" ", NULL);
				_tmp57_ = _tmp56_;
				g_data_output_stream_put_string (_tmp52_, _tmp57_, NULL, &_inner_error0_);
				_g_free0 (_tmp57_);
				_g_free0 (_tmp54_);
				if (G_UNLIKELY (_inner_error0_ != NULL)) {
					_g_object_unref0 (item);
					_g_object_unref0 (_tmp7_);
					goto __catch1_g_error;
				}
				_tmp58_ = os;
				_tmp59_ = item;
				_tmp60_ = _tmp59_->identifier;
				_tmp61_ = string_to_string (_tmp60_);
				_tmp62_ = g_strconcat ("action=\"", _tmp61_, "\" ", NULL);
				_tmp63_ = _tmp62_;
				g_data_output_stream_put_string (_tmp58_, _tmp63_, NULL, &_inner_error0_);
				_g_free0 (_tmp63_);
				if (G_UNLIKELY (_inner_error0_ != NULL)) {
					_g_object_unref0 (item);
					_g_object_unref0 (_tmp7_);
					goto __catch1_g_error;
				}
				_tmp64_ = os;
				g_data_output_stream_put_string (_tmp64_, "/>\n", NULL, &_inner_error0_);
				if (G_UNLIKELY (_inner_error0_ != NULL)) {
					_g_object_unref0 (item);
					_g_object_unref0 (_tmp7_);
					goto __catch1_g_error;
				}
				_g_object_unref0 (item);
			}
		}
		_tmp65_ = os;
		g_data_output_stream_put_string (_tmp65_, "</bindings>\n", NULL, &_inner_error0_);
		if (G_UNLIKELY (_inner_error0_ != NULL)) {
			_g_object_unref0 (_tmp7_);
			goto __catch1_g_error;
		}
		_tmp66_ = os;
		g_output_stream_close ((GOutputStream*) _tmp66_, NULL, &_inner_error0_);
		if (G_UNLIKELY (_inner_error0_ != NULL)) {
			_g_object_unref0 (_tmp7_);
			goto __catch1_g_error;
		}
		_g_object_unref0 (_tmp7_);
	}
	goto __finally1;
	__catch1_g_error:
	{
		GError* e = NULL;
		GError* _tmp67_;
		const gchar* _tmp68_;
		e = _inner_error0_;
		_inner_error0_ = NULL;
		_tmp67_ = e;
		_tmp68_ = _tmp67_->message;
		g_warning ("AbstractMenu.vala:384: %s", _tmp68_);
		_g_error_free0 (e);
	}
	__finally1:
	if (G_UNLIKELY (_inner_error0_ != NULL)) {
		_g_object_unref0 (file);
		_g_object_unref0 (os);
		g_critical ("file %s: line %d: uncaught error: %s (%s, %d)", __FILE__, __LINE__, _inner_error0_->message, g_quark_to_string (_inner_error0_->domain), _inner_error0_->code);
		g_clear_error (&_inner_error0_);
		return;
	}
	_g_object_unref0 (file);
	_g_object_unref0 (os);
}

void
bird_font_abstract_menu_set_current_menu (BirdFontAbstractMenu* self,
                                          BirdFontSubMenu* menu)
{
	BirdFontSubMenu* _tmp0_;
	g_return_if_fail (self != NULL);
	g_return_if_fail (menu != NULL);
	_tmp0_ = _g_object_ref0 (menu);
	_g_object_unref0 (self->priv->current_menu);
	self->priv->current_menu = _tmp0_;
}

gboolean
bird_font_abstract_menu_get_show_menu (BirdFontAbstractMenu* self)
{
	gboolean result;
	g_return_val_if_fail (self != NULL, FALSE);
	result = self->priv->menu_visibility;
	return result;
}

void
bird_font_abstract_menu_set_show_menu (BirdFontAbstractMenu* self,
                                       gboolean value)
{
	gchar* tab_name = NULL;
	BirdFontSubMenu* _tmp0_;
	BirdFontSubMenu* _tmp1_;
	g_return_if_fail (self != NULL);
	self->priv->menu_visibility = value;
	_tmp0_ = self->top_menu;
	_tmp1_ = _g_object_ref0 (_tmp0_);
	_g_object_unref0 (self->priv->current_menu);
	self->priv->current_menu = _tmp1_;
	if (self->priv->menu_visibility) {
		BirdFontTabBar* _tmp2_;
		BirdFontTabBar* _tmp3_;
		BirdFontTab* _tmp4_;
		BirdFontTab* _tmp5_;
		BirdFontFontDisplay* _tmp6_;
		BirdFontFontDisplay* _tmp7_;
		gchar* _tmp8_;
		const gchar* _tmp9_;
		_tmp2_ = bird_font_main_window_get_tab_bar ();
		_tmp3_ = _tmp2_;
		_tmp4_ = bird_font_tab_bar_get_selected_tab (_tmp3_);
		_tmp5_ = _tmp4_;
		_tmp6_ = bird_font_tab_get_display (_tmp5_);
		_tmp7_ = _tmp6_;
		_tmp8_ = bird_font_font_display_get_name (_tmp7_);
		_g_free0 (tab_name);
		tab_name = _tmp8_;
		_g_object_unref0 (_tmp7_);
		_g_object_unref0 (_tmp5_);
		_g_object_unref0 (_tmp3_);
		_tmp9_ = tab_name;
		if (g_strcmp0 (_tmp9_, "Preview") == 0) {
			bird_font_menu_tab_select_overview ();
		}
		bird_font_main_window_hide_scrollbar ();
	} else {
		bird_font_main_window_show_scrollbar ();
	}
	_g_free0 (tab_name);
	g_object_notify_by_pspec ((GObject *) self, bird_font_abstract_menu_properties[BIRD_FONT_ABSTRACT_MENU_SHOW_MENU_PROPERTY]);
}

static void
bird_font_abstract_menu_class_init (BirdFontAbstractMenuClass * klass,
                                    gpointer klass_data)
{
	bird_font_abstract_menu_parent_class = g_type_class_peek_parent (klass);
	g_type_class_adjust_private_offset (klass, &BirdFontAbstractMenu_private_offset);
	G_OBJECT_CLASS (klass)->get_property = _vala_bird_font_abstract_menu_get_property;
	G_OBJECT_CLASS (klass)->set_property = _vala_bird_font_abstract_menu_set_property;
	G_OBJECT_CLASS (klass)->finalize = bird_font_abstract_menu_finalize;
	g_object_class_install_property (G_OBJECT_CLASS (klass), BIRD_FONT_ABSTRACT_MENU_SHOW_MENU_PROPERTY, bird_font_abstract_menu_properties[BIRD_FONT_ABSTRACT_MENU_SHOW_MENU_PROPERTY] = g_param_spec_boolean ("show-menu", "show-menu", "show-menu", FALSE, G_PARAM_STATIC_STRINGS | G_PARAM_READABLE | G_PARAM_WRITABLE));
}

static void
bird_font_abstract_menu_instance_init (BirdFontAbstractMenu * self,
                                       gpointer klass)
{
	BirdFontWidgetAllocation* _tmp0_;
	GeeHashMap* _tmp1_;
	GeeArrayList* _tmp2_;
	self->priv = bird_font_abstract_menu_get_instance_private (self);
	self->priv->menu_visibility = FALSE;
	_tmp0_ = bird_font_widget_allocation_new ();
	self->priv->allocation = _tmp0_;
	self->priv->width = (gdouble) 250;
	self->priv->height = (gdouble) 25;
	_tmp1_ = gee_hash_map_new (G_TYPE_STRING, (GBoxedCopyFunc) g_strdup, (GDestroyNotify) g_free, BIRD_FONT_TYPE_MENU_ITEM, (GBoxedCopyFunc) g_object_ref, (GDestroyNotify) g_object_unref, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL, NULL);
	self->menu_items = _tmp1_;
	_tmp2_ = gee_array_list_new (BIRD_FONT_TYPE_MENU_ITEM, (GBoxedCopyFunc) g_object_ref, (GDestroyNotify) g_object_unref, NULL, NULL, NULL);
	self->sorted_menu_items = _tmp2_;
}

static void
bird_font_abstract_menu_finalize (GObject * obj)
{
	BirdFontAbstractMenu * self;
	self = G_TYPE_CHECK_INSTANCE_CAST (obj, BIRD_FONT_TYPE_ABSTRACT_MENU, BirdFontAbstractMenu);
	_g_object_unref0 (self->top_menu);
	_g_object_unref0 (self->priv->current_menu);
	_g_object_unref0 (self->priv->allocation);
	_g_object_unref0 (self->menu_items);
	_g_object_unref0 (self->sorted_menu_items);
	G_OBJECT_CLASS (bird_font_abstract_menu_parent_class)->finalize (obj);
}

/** Interface for events from native window to the current tab. */
static GType
bird_font_abstract_menu_get_type_once (void)
{
	static const GTypeInfo g_define_type_info = { sizeof (BirdFontAbstractMenuClass), (GBaseInitFunc) NULL, (GBaseFinalizeFunc) NULL, (GClassInitFunc) bird_font_abstract_menu_class_init, (GClassFinalizeFunc) NULL, NULL, sizeof (BirdFontAbstractMenu), 0, (GInstanceInitFunc) bird_font_abstract_menu_instance_init, NULL };
	GType bird_font_abstract_menu_type_id;
	bird_font_abstract_menu_type_id = g_type_register_static (G_TYPE_OBJECT, "BirdFontAbstractMenu", &g_define_type_info, 0);
	BirdFontAbstractMenu_private_offset = g_type_add_instance_private (bird_font_abstract_menu_type_id, sizeof (BirdFontAbstractMenuPrivate));
	return bird_font_abstract_menu_type_id;
}

GType
bird_font_abstract_menu_get_type (void)
{
	static volatile gsize bird_font_abstract_menu_type_id__once = 0;
	if (g_once_init_enter (&bird_font_abstract_menu_type_id__once)) {
		GType bird_font_abstract_menu_type_id;
		bird_font_abstract_menu_type_id = bird_font_abstract_menu_get_type_once ();
		g_once_init_leave (&bird_font_abstract_menu_type_id__once, bird_font_abstract_menu_type_id);
	}
	return bird_font_abstract_menu_type_id__once;
}

static void
_vala_bird_font_abstract_menu_get_property (GObject * object,
                                            guint property_id,
                                            GValue * value,
                                            GParamSpec * pspec)
{
	BirdFontAbstractMenu * self;
	self = G_TYPE_CHECK_INSTANCE_CAST (object, BIRD_FONT_TYPE_ABSTRACT_MENU, BirdFontAbstractMenu);
	switch (property_id) {
		case BIRD_FONT_ABSTRACT_MENU_SHOW_MENU_PROPERTY:
		g_value_set_boolean (value, bird_font_abstract_menu_get_show_menu (self));
		break;
		default:
		G_OBJECT_WARN_INVALID_PROPERTY_ID (object, property_id, pspec);
		break;
	}
}

static void
_vala_bird_font_abstract_menu_set_property (GObject * object,
                                            guint property_id,
                                            const GValue * value,
                                            GParamSpec * pspec)
{
	BirdFontAbstractMenu * self;
	self = G_TYPE_CHECK_INSTANCE_CAST (object, BIRD_FONT_TYPE_ABSTRACT_MENU, BirdFontAbstractMenu);
	switch (property_id) {
		case BIRD_FONT_ABSTRACT_MENU_SHOW_MENU_PROPERTY:
		bird_font_abstract_menu_set_show_menu (self, g_value_get_boolean (value));
		break;
		default:
		G_OBJECT_WARN_INVALID_PROPERTY_ID (object, property_id, pspec);
		break;
	}
}

