diff options
-rw-r--r-- | Makefile.am | 5 | ||||
-rw-r--r-- | data/gl-eventviewlist.ui | 21 | ||||
-rw-r--r-- | data/gl-searchpopover.ui | 210 | ||||
-rw-r--r-- | data/org.gnome.Logs.gresource.xml | 1 | ||||
-rw-r--r-- | src/gl-eventviewlist.c | 102 | ||||
-rw-r--r-- | src/gl-searchpopover.c | 280 | ||||
-rw-r--r-- | src/gl-searchpopover.h | 49 |
7 files changed, 652 insertions, 16 deletions
diff --git a/Makefile.am b/Makefile.am index 10afe2e..762d858 100644 --- a/Makefile.am +++ b/Makefile.am @@ -30,6 +30,7 @@ gnome_logs_SOURCES = \ src/gl-eventview.c \ src/gl-eventviewdetail.c \ src/gl-eventviewlist.c \ + src/gl-searchpopover.c \ src/gl-eventviewrow.c \ src/gl-journal.c \ src/gl-journal-model.c \ @@ -50,7 +51,8 @@ gnome_logs_enum_headers = \ $(srcdir)/src/gl-eventtoolbar.h \ $(srcdir)/src/gl-eventview.h \ $(srcdir)/src/gl-eventviewrow.h \ - $(srcdir)/src/gl-util.h + $(srcdir)/src/gl-util.h \ + $(srcdir)/src/gl-searchpopover.h noinst_gnome_logs_headers = \ src/gl-application.h \ @@ -59,6 +61,7 @@ noinst_gnome_logs_headers = \ src/gl-eventview.h \ src/gl-eventviewdetail.h \ src/gl-eventviewlist.h \ + src/gl-searchpopover.h \ src/gl-eventviewrow.h \ src/gl-journal.h \ src/gl-journal-model.h \ diff --git a/data/gl-eventviewlist.ui b/data/gl-eventviewlist.ui index 61dfa98..df8c75c 100644 --- a/data/gl-eventviewlist.ui +++ b/data/gl-eventviewlist.ui @@ -25,10 +25,25 @@ <property name="visible">True</property> <signal name="notify::search-mode-enabled" handler="on_search_bar_notify_search_mode_enabled"/> <child> - <object class="GtkSearchEntry" id="search_entry"> + <object class="GtkBox" id="search_entry_box"> + <property name="orientation">horizontal</property> <property name="visible">True</property> - <property name="width-request">400</property> - <signal name="search-changed" handler="on_search_entry_changed" /> + <style> + <class name="linked"/> + </style> + <child> + <object class="GtkSearchEntry" id="search_entry"> + <property name="visible">True</property> + <property name="width-request">400</property> + <signal name="search-changed" handler="on_search_entry_changed" /> + </object> + </child> + <child> + <object class="GtkMenuButton" id="search_dropdown_button"> + <property name="tooltip-text" translatable="yes">Select journal field and timestamp range filtering options</property> + <property name="visible">True</property> + </object> + </child> </object> </child> </object> diff --git a/data/gl-searchpopover.ui b/data/gl-searchpopover.ui new file mode 100644 index 0000000..adeaee5 --- /dev/null +++ b/data/gl-searchpopover.ui @@ -0,0 +1,210 @@ +<interface domain="gnome-logs"> + <template class="GlSearchPopover" parent="GtkPopover"> + <signal name="closed" handler="search_popover_closed"/> + <child> + <object class="GtkGrid" id="popover_grid"> + <property name="visible">True</property> + <property name="border_width">20</property> + <property name="row_spacing">8</property> + <property name="column_spacing">18</property> + <child> + <object class="GtkStack" id="parameter_stack"> + <property name="visible">True</property> + <property name="vhomogeneous">False</property> + <property name="transition_type">crossfade</property> + <child> + <object class="GtkButton" id="select_parameter_button"> + <property name="visible">True</property> + <property name="can_focus">True</property> + <property name="receives_default">True</property> + <property name="tooltip_text" translatable="yes">Select a Journal Field to filter the Logs according to it</property> + <signal name="clicked" handler="select_parameter_button_clicked"/> + <child> + <object class="GtkBox" id="parameter_filter_box"> + <property name="visible">True</property> + <child> + <object class="GtkLabel" id="parameter_button_label"> + <property name="visible">True</property> + <property name="hexpand">True</property> + <property name="label" translatable="yes">All Available Fields</property> + <property name="width_chars">30</property> + <property name="xalign">0</property> + </object> + <packing> + <property name="expand">False</property> + <property name="fill">True</property> + <property name="position">0</property> + </packing> + </child> + <child> + <object class="GtkImage" id="parameter_button_image"> + <property name="visible">True</property> + <property name="icon_name">pan-down-symbolic</property> + </object> + <packing> + <property name="expand">False</property> + <property name="fill">True</property> + <property name="position">1</property> + </packing> + </child> + </object> + </child> + </object> + <packing> + <property name="name">parameter-button</property> + </packing> + </child> + <child> + <object class="GtkScrolledWindow" id="parameter_scrolled_window"> + <property name="height_request">150</property> + <property name="visible">True</property> + <property name="can_focus">True</property> + <property name="shadow_type">in</property> + <child> + <object class="GtkTreeView" id="parameter_treeview"> + <property name="visible">True</property> + <property name="model">parameter_liststore</property> + <property name="headers-visible">False</property> + <property name="activate-on-single-click">True</property> + <signal name="row-activated" handler="on_parameter_treeview_row_activated"/> + <child> + <object class="GtkTreeViewColumn" id="parameter-column"> + <property name="title">Parameters</property> + <property name="visible">True</property> + <child> + <object class="GtkCellRendererText" id="test-renderer"/> + <attributes> + <attribute name="text">0</attribute> + </attributes> + </child> + </object> + </child> + <child internal-child="selection"> + <object class="GtkTreeSelection" id="selection"> + <property name="mode">GTK_SELECTION_BROWSE</property> + </object> + </child> + </object> + </child> + </object> + <packing> + <property name="name">parameter-list</property> + <property name="position">1</property> + </packing> + </child> + </object> + <packing> + <property name="left_attach">0</property> + <property name="top_attach">1</property> + <property name="width">2</property> + </packing> + </child> + <child> + <object class="GtkStack" id="parameter_label_stack"> + <property name="visible">True</property> + <child> + <object class="GtkLabel" id="what_dim_label"> + <property name="visible">True</property> + <property name="margin_top">10</property> + <!-- Translators: What [journal fields to search in] --> + <property name="label" translatable="yes">What</property> + <property name="xalign">0</property> + <style> + <class name="dim-label"/> + </style> + </object> + <packing> + <property name="name">what-label</property> + <property name="title">page0</property> + </packing> + </child> + <child> + <object class="GtkLabel" id="select_parameter_dim_label"> + <property name="visible">True</property> + <property name="margin_top">10</property> + <property name="label" translatable="yes">Select Journal Field…</property> + <property name="xalign">0</property> + <style> + <class name="dim-label"/> + </style> + </object> + <packing> + <property name="name">select-parameter-label</property> + <property name="title">page1</property> + <property name="position">1</property> + </packing> + </child> + </object> + <packing> + <property name="left_attach">0</property> + <property name="top_attach">0</property> + <property name="width">2</property> + </packing> + </child> + </object> + </child> + </template> + <object class="GtkListStore" id="parameter_liststore"> + <columns> + <column type="gchararray"/> + <column type="gboolean"/> + <column type="GlSearchPopoverJournalFieldFilter"/> + </columns> + <data> + <row> + <col id="0" translatable="yes">All Available Fields</col> + <col id="1">False</col> + <col id="2">GL_SEARCH_POPOVER_JOURNAL_FIELD_FILTER_ALL_AVAILABLE_FIELDS</col> + </row> + <row> + <col id="0">Separator</col> + <col id="1">True</col> + </row> + <row> + <col id="0" translatable="yes">PID</col> + <col id="1">False</col> + <col id="2">GL_SEARCH_POPOVER_JOURNAL_FIELD_FILTER_PID</col> + </row> + <row> + <col id="0" translatable="yes">UID</col> + <col id="1">False</col> + <col id="2">GL_SEARCH_POPOVER_JOURNAL_FIELD_FILTER_UID</col> + </row> + <row> + <col id="0" translatable="yes">GID</col> + <col id="1">False</col> + <col id="2">GL_SEARCH_POPOVER_JOURNAL_FIELD_FILTER_GID</col> + </row> + <row> + <col id="0" translatable="yes">Message</col> + <col id="1">False</col> + <col id="2">GL_SEARCH_POPOVER_JOURNAL_FIELD_FILTER_MESSAGE</col> + </row> + <row> + <col id="0" translatable="yes">Process Name</col> + <col id="1">False</col> + <col id="2">GL_SEARCH_POPOVER_JOURNAL_FIELD_FILTER_PROCESS_NAME</col> + </row> + <row> + <col id="0" translatable="yes">Systemd Unit</col> + <col id="1">False</col> + <col id="2">GL_SEARCH_POPOVER_JOURNAL_FIELD_FILTER_SYSTEMD_UNIT</col> + </row> + <row> + <col id="0" translatable="yes">Kernel Device</col> + <col id="1">False</col> + <col id="2">GL_SEARCH_POPOVER_JOURNAL_FIELD_FILTER_KERNEL_DEVICE</col> + </row> + <row> + <col id="0" translatable="yes">Audit Session</col> + <col id="1">False</col> + <col id="2">GL_SEARCH_POPOVER_JOURNAL_FIELD_FILTER_AUDIT_SESSION</col> + </row> + <row> + <col id="0" translatable="yes">Executable Path</col> + <col id="1">False</col> + <col id="2">GL_SEARCH_POPOVER_JOURNAL_FIELD_FILTER_EXECUTABLE_PATH</col> + </row> + </data> + </object> +</interface> diff --git a/data/org.gnome.Logs.gresource.xml b/data/org.gnome.Logs.gresource.xml index f91a628..291fd85 100644 --- a/data/org.gnome.Logs.gresource.xml +++ b/data/org.gnome.Logs.gresource.xml @@ -6,6 +6,7 @@ <file preprocess="xml-stripblanks">gl-eventviewlist.ui</file> <file preprocess='xml-stripblanks'>gl-eventtoolbar.ui</file> <file preprocess='xml-stripblanks'>gl-eventviewdetail.ui</file> + <file preprocess='xml-stripblanks'>gl-searchpopover.ui</file> <file>gl-style.css</file> <file preprocess='xml-stripblanks'>gl-window.ui</file> </gresource> diff --git a/src/gl-eventviewlist.c b/src/gl-eventviewlist.c index ad3f5bd..9849fe7 100644 --- a/src/gl-eventviewlist.c +++ b/src/gl-eventviewlist.c @@ -30,6 +30,7 @@ #include "gl-eventviewrow.h" #include "gl-journal-model.h" #include "gl-util.h" +#include "gl-searchpopover.h" struct _GlEventViewList { @@ -50,6 +51,8 @@ typedef struct GtkWidget *event_search; GtkWidget *event_scrolled; GtkWidget *search_entry; + GtkWidget *search_dropdown_button; + GlSearchPopoverJournalFieldFilter journal_search_field; gchar *search_text; const gchar *boot_match; } GlEventViewListPrivate; @@ -451,18 +454,50 @@ query_add_category_matches (GlQuery *query, static void query_add_search_matches (GlQuery *query, - const gchar *search_text) + const gchar *search_text, + GlSearchPopoverJournalFieldFilter journal_search_field) { - /* Add substring matches */ - gl_query_add_match (query, "_PID", search_text, SEARCH_TYPE_SUBSTRING); - gl_query_add_match (query, "_UID", search_text, SEARCH_TYPE_SUBSTRING); - gl_query_add_match (query, "_GID", search_text, SEARCH_TYPE_SUBSTRING); - gl_query_add_match (query, "MESSAGE", search_text, SEARCH_TYPE_SUBSTRING); - gl_query_add_match (query, "_COMM", search_text, SEARCH_TYPE_SUBSTRING); - gl_query_add_match (query, "_SYSTEMD_UNIT", search_text, SEARCH_TYPE_SUBSTRING); - gl_query_add_match (query, "_KERNEL_DEVICE", search_text, SEARCH_TYPE_SUBSTRING); - gl_query_add_match (query, "_AUDIT_SESSION", search_text, SEARCH_TYPE_SUBSTRING); - gl_query_add_match (query, "_EXE", search_text, SEARCH_TYPE_SUBSTRING); + switch (journal_search_field) + { + case GL_SEARCH_POPOVER_JOURNAL_FIELD_FILTER_ALL_AVAILABLE_FIELDS: + gl_query_add_match (query, "_PID", search_text, SEARCH_TYPE_SUBSTRING); + gl_query_add_match (query, "_UID", search_text, SEARCH_TYPE_SUBSTRING); + gl_query_add_match (query, "_GID", search_text, SEARCH_TYPE_SUBSTRING); + gl_query_add_match (query, "MESSAGE", search_text, SEARCH_TYPE_SUBSTRING); + gl_query_add_match (query, "_COMM", search_text, SEARCH_TYPE_SUBSTRING); + gl_query_add_match (query, "_SYSTEMD_UNIT", search_text, SEARCH_TYPE_SUBSTRING); + gl_query_add_match (query, "_KERNEL_DEVICE", search_text, SEARCH_TYPE_SUBSTRING); + gl_query_add_match (query, "_AUDIT_SESSION", search_text, SEARCH_TYPE_SUBSTRING); + gl_query_add_match (query, "_EXE", search_text, SEARCH_TYPE_SUBSTRING); + break; + case GL_SEARCH_POPOVER_JOURNAL_FIELD_FILTER_PID: + gl_query_add_match (query, "_PID", search_text, SEARCH_TYPE_SUBSTRING); + break; + case GL_SEARCH_POPOVER_JOURNAL_FIELD_FILTER_UID: + gl_query_add_match (query, "_UID", search_text, SEARCH_TYPE_SUBSTRING); + break; + case GL_SEARCH_POPOVER_JOURNAL_FIELD_FILTER_GID: + gl_query_add_match (query, "_GID", search_text, SEARCH_TYPE_SUBSTRING); + break; + case GL_SEARCH_POPOVER_JOURNAL_FIELD_FILTER_MESSAGE: + gl_query_add_match (query, "MESSAGE", search_text, SEARCH_TYPE_SUBSTRING); + break; + case GL_SEARCH_POPOVER_JOURNAL_FIELD_FILTER_PROCESS_NAME: + gl_query_add_match (query, "_COMM", search_text, SEARCH_TYPE_SUBSTRING); + break; + case GL_SEARCH_POPOVER_JOURNAL_FIELD_FILTER_SYSTEMD_UNIT: + gl_query_add_match (query, "_SYSTEMD_UNIT", search_text, SEARCH_TYPE_SUBSTRING); + break; + case GL_SEARCH_POPOVER_JOURNAL_FIELD_FILTER_KERNEL_DEVICE: + gl_query_add_match (query, "_KERNEL_DEVICE", search_text, SEARCH_TYPE_SUBSTRING); + break; + case GL_SEARCH_POPOVER_JOURNAL_FIELD_FILTER_AUDIT_SESSION: + gl_query_add_match (query, "_AUDIT_SESSION", search_text, SEARCH_TYPE_SUBSTRING); + break; + case GL_SEARCH_POPOVER_JOURNAL_FIELD_FILTER_EXECUTABLE_PATH: + gl_query_add_match (query, "_EXE", search_text, SEARCH_TYPE_SUBSTRING); + break; + } } /* Create query object according to selected category */ @@ -481,7 +516,7 @@ create_query_object (GlEventViewList *view) query_add_category_matches (query, list, priv->boot_match); - query_add_search_matches (query, priv->search_text); + query_add_search_matches (query, priv->search_text, priv->journal_search_field); return query; } @@ -676,6 +711,45 @@ gl_event_list_view_edge_reached (GtkScrolledWindow *scrolled, } static void +search_popover_journal_search_field_changed (GlSearchPopover *popover, + GParamSpec *psec, + GlEventViewList *view) +{ + GlEventViewListPrivate *priv = gl_event_view_list_get_instance_private (view); + GlQuery *query; + + priv->journal_search_field = gl_search_popover_get_journal_search_field (popover); + + query = create_query_object (view); + + gl_journal_model_take_query (priv->journal_model, query); +} + +/* Get the view elements from ui file and link it with the drop down button */ +static void +set_up_search_popover (GlEventViewList *view) +{ + + GlEventViewListPrivate *priv; + GtkWidget *search_popover; + + priv = gl_event_view_list_get_instance_private (view); + + search_popover = gl_search_popover_new (); + + /* Grab/Remove keyboard focus from popover menu when it is opened or closed */ + g_signal_connect (search_popover, "show", (GCallback) gtk_widget_grab_focus, NULL); + g_signal_connect_swapped (search_popover, "closed", (GCallback) gtk_widget_grab_focus, view); + + g_signal_connect (search_popover, "notify::journal-search-field", + G_CALLBACK (search_popover_journal_search_field_changed), view); + + /* Link the drop down button with search popover */ + gtk_menu_button_set_popover (GTK_MENU_BUTTON (priv->search_dropdown_button), + search_popover); +} + +static void gl_event_view_list_finalize (GObject *object) { GlEventViewList *view = GL_EVENT_VIEW_LIST (object); @@ -708,6 +782,8 @@ gl_event_view_list_class_init (GlEventViewListClass *klass) event_scrolled); gtk_widget_class_bind_template_child_private (widget_class, GlEventViewList, search_entry); + gtk_widget_class_bind_template_child_private (widget_class, GlEventViewList, + search_dropdown_button); gtk_widget_class_bind_template_callback (widget_class, on_search_entry_changed); @@ -758,6 +834,8 @@ gl_event_view_list_init (GlEventViewList *view) priv->clock_format = g_settings_get_enum (settings, CLOCK_FORMAT); g_object_unref (settings); + set_up_search_popover (view); + g_signal_connect (categories, "notify::category", G_CALLBACK (on_notify_category), view); } diff --git a/src/gl-searchpopover.c b/src/gl-searchpopover.c new file mode 100644 index 0000000..ef72667 --- /dev/null +++ b/src/gl-searchpopover.c @@ -0,0 +1,280 @@ +/* + * GNOME Logs - View and search logs + * Copyright (C) 2016 Pranav Ganorkar <pranavg189@gmail.com> + * + * 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 "gl-searchpopover.h" +#include "gl-enums.h" + +#include <glib/gi18n.h> + +struct _GlSearchPopover +{ + /*< private >*/ + GtkPopover parent_instance; +}; + +typedef struct +{ + /* Search popover elements */ + GtkWidget *parameter_stack; + GtkWidget *parameter_button_label; + GtkWidget *parameter_label_stack; + GtkWidget *parameter_treeview; + GtkListStore *parameter_liststore; + + GlSearchPopoverJournalFieldFilter journal_search_field; +} GlSearchPopoverPrivate; + +enum +{ + PROP_0, + PROP_JOURNAL_SEARCH_FIELD, + N_PROPERTIES +}; + +enum +{ + COLUMN_JOURNAL_FIELD_LABEL, + COLUMN_JOURNAL_FIELD_SHOW_SEPARATOR, + COLUMN_JOURNAL_FIELD_ENUM_VALUE, + JOURNAL_FIELD_N_COLUMNS +}; + +static GParamSpec *obj_properties[N_PROPERTIES] = { NULL, }; + +G_DEFINE_TYPE_WITH_PRIVATE (GlSearchPopover, gl_search_popover, GTK_TYPE_POPOVER) + +/* Event handlers for search popover elements */ +static void +search_popover_closed (GtkPopover *popover, + gpointer user_data) +{ + GlSearchPopoverPrivate *priv; + + priv = gl_search_popover_get_instance_private (GL_SEARCH_POPOVER (user_data)); + + gtk_stack_set_visible_child_name (GTK_STACK (priv->parameter_stack), "parameter-button"); + gtk_stack_set_visible_child_name (GTK_STACK (priv->parameter_label_stack), "what-label"); +} + +static void +select_parameter_button_clicked (GtkButton *button, + gpointer user_data) +{ + GlSearchPopoverPrivate *priv; + GtkTreeSelection *selection; + GtkTreeModel *model; + GtkTreeIter iter; + gboolean valid; + + priv = gl_search_popover_get_instance_private (GL_SEARCH_POPOVER (user_data)); + + gtk_stack_set_visible_child_name (GTK_STACK (priv->parameter_stack), "parameter-list"); + gtk_stack_set_visible_child_name (GTK_STACK (priv->parameter_label_stack), "select-parameter-label"); + + model = GTK_TREE_MODEL (priv->parameter_liststore); + + valid = gtk_tree_model_get_iter_first (model, &iter); + + while (valid) + { + GlSearchPopoverJournalFieldFilter journal_field_enum_value; + + gtk_tree_model_get (GTK_TREE_MODEL (priv->parameter_liststore), &iter, + COLUMN_JOURNAL_FIELD_ENUM_VALUE, &journal_field_enum_value, + -1); + + if (priv->journal_search_field == journal_field_enum_value) + { + break; + } + + valid = gtk_tree_model_iter_next (model, &iter); + } + + selection = gtk_tree_view_get_selection (GTK_TREE_VIEW (priv->parameter_treeview)); + + gtk_tree_selection_select_iter (selection, &iter); +} + +static gboolean +parameter_treeview_row_seperator (GtkTreeModel *model, + GtkTreeIter *iter, + gpointer user_data) +{ + GlSearchPopover *popover; + GlSearchPopoverPrivate *priv; + gboolean show_separator; + + popover = GL_SEARCH_POPOVER (user_data); + + priv = gl_search_popover_get_instance_private (popover); + + gtk_tree_model_get (GTK_TREE_MODEL (priv->parameter_liststore), iter, + COLUMN_JOURNAL_FIELD_SHOW_SEPARATOR, &show_separator, + -1); + + return show_separator; +} + +static void +on_parameter_treeview_row_activated (GtkTreeView *tree_view, + GtkTreePath *path, + GtkTreeViewColumn *column, + gpointer user_data) +{ + GtkTreeIter iter; + GlSearchPopover *popover; + GlSearchPopoverPrivate *priv; + gchar *journal_field_label; + GlSearchPopoverJournalFieldFilter journal_field_enum_value; + + popover = GL_SEARCH_POPOVER (user_data); + + priv = gl_search_popover_get_instance_private (popover); + + gtk_tree_model_get_iter (GTK_TREE_MODEL (priv->parameter_liststore), &iter, path); + + gtk_tree_model_get (GTK_TREE_MODEL (priv->parameter_liststore), &iter, + COLUMN_JOURNAL_FIELD_LABEL, &journal_field_label, + COLUMN_JOURNAL_FIELD_ENUM_VALUE, &journal_field_enum_value, + -1); + + gtk_label_set_label (GTK_LABEL (priv->parameter_button_label), + _(journal_field_label)); + + priv->journal_search_field = journal_field_enum_value; + + g_object_notify_by_pspec (G_OBJECT (popover), + obj_properties[PROP_JOURNAL_SEARCH_FIELD]); + + gtk_stack_set_visible_child_name (GTK_STACK (priv->parameter_stack), "parameter-button"); + gtk_stack_set_visible_child_name (GTK_STACK (priv->parameter_label_stack), "what-label"); + + g_free (journal_field_label); +} + +GlSearchPopoverJournalFieldFilter +gl_search_popover_get_journal_search_field (GlSearchPopover *popover) +{ + GlSearchPopoverPrivate *priv; + + priv = gl_search_popover_get_instance_private (popover); + + return priv->journal_search_field; +} + +static void +gl_search_popover_get_property (GObject *object, + guint prop_id, + GValue *value, + GParamSpec *pspec) +{ + GlSearchPopover *popover = GL_SEARCH_POPOVER (object); + GlSearchPopoverPrivate *priv = gl_search_popover_get_instance_private (popover); + + switch (prop_id) + { + case PROP_JOURNAL_SEARCH_FIELD: + g_value_set_enum (value, priv->journal_search_field); + break; + default: + G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec); + break; + } +} + +static void +gl_search_popover_set_property (GObject *object, + guint prop_id, + const GValue *value, + GParamSpec *pspec) +{ + GlSearchPopover *popover = GL_SEARCH_POPOVER (object); + GlSearchPopoverPrivate *priv = gl_search_popover_get_instance_private (popover); + + switch (prop_id) + { + case PROP_JOURNAL_SEARCH_FIELD: + priv->journal_search_field = g_value_get_enum (value); + break; + default: + G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec); + break; + } +} + +static void +gl_search_popover_class_init (GlSearchPopoverClass *klass) +{ + GObjectClass *gobject_class = G_OBJECT_CLASS (klass); + GtkWidgetClass *widget_class = GTK_WIDGET_CLASS (klass); + + gobject_class->get_property = gl_search_popover_get_property; + gobject_class->set_property = gl_search_popover_set_property; + + obj_properties[PROP_JOURNAL_SEARCH_FIELD] = g_param_spec_enum ("journal-search-field", "Journal Search Field", + "The Journal search field by which to filter the logs", + GL_TYPE_SEARCH_POPOVER_JOURNAL_FIELD_FILTER, + GL_SEARCH_POPOVER_JOURNAL_FIELD_FILTER_ALL_AVAILABLE_FIELDS, + G_PARAM_READWRITE | + G_PARAM_STATIC_STRINGS); + + g_object_class_install_properties (gobject_class, N_PROPERTIES, + obj_properties); + + gtk_widget_class_set_template_from_resource (widget_class, + "/org/gnome/Logs/gl-searchpopover.ui"); + gtk_widget_class_bind_template_child_private (widget_class, GlSearchPopover, + parameter_stack); + gtk_widget_class_bind_template_child_private (widget_class, GlSearchPopover, + parameter_button_label); + gtk_widget_class_bind_template_child_private (widget_class, GlSearchPopover, + parameter_label_stack); + gtk_widget_class_bind_template_child_private (widget_class, GlSearchPopover, + parameter_treeview); + gtk_widget_class_bind_template_child_private (widget_class, GlSearchPopover, + parameter_liststore); + + gtk_widget_class_bind_template_callback (widget_class, + search_popover_closed); + gtk_widget_class_bind_template_callback (widget_class, + select_parameter_button_clicked); + gtk_widget_class_bind_template_callback (widget_class, + on_parameter_treeview_row_activated); +} + +static void +gl_search_popover_init (GlSearchPopover *popover) +{ + GlSearchPopoverPrivate *priv; + + gtk_widget_init_template (GTK_WIDGET (popover)); + + priv = gl_search_popover_get_instance_private (popover); + + gtk_tree_view_set_row_separator_func (GTK_TREE_VIEW (priv->parameter_treeview), + (GtkTreeViewRowSeparatorFunc) parameter_treeview_row_seperator, + popover, + NULL); +} + +GtkWidget * +gl_search_popover_new (void) +{ + return g_object_new (GL_TYPE_SEARCH_POPOVER, NULL); +} diff --git a/src/gl-searchpopover.h b/src/gl-searchpopover.h new file mode 100644 index 0000000..faf0a1f --- /dev/null +++ b/src/gl-searchpopover.h @@ -0,0 +1,49 @@ +/* + * GNOME Logs - View and search logs + * Copyright (C) 2016 Pranav Ganorkar <pranavg189@gmail.com> + * + * 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/>. + */ + +#ifndef GL_SEARCH_POPOVER_H_ +#define GL_SEARCH_POPOVER_H_ + +#include <gtk/gtk.h> + +G_BEGIN_DECLS + +/* Rows in parameter treeview */ +typedef enum +{ + GL_SEARCH_POPOVER_JOURNAL_FIELD_FILTER_ALL_AVAILABLE_FIELDS, + GL_SEARCH_POPOVER_JOURNAL_FIELD_FILTER_PID, + GL_SEARCH_POPOVER_JOURNAL_FIELD_FILTER_UID, + GL_SEARCH_POPOVER_JOURNAL_FIELD_FILTER_GID, + GL_SEARCH_POPOVER_JOURNAL_FIELD_FILTER_MESSAGE, + GL_SEARCH_POPOVER_JOURNAL_FIELD_FILTER_PROCESS_NAME, + GL_SEARCH_POPOVER_JOURNAL_FIELD_FILTER_SYSTEMD_UNIT, + GL_SEARCH_POPOVER_JOURNAL_FIELD_FILTER_KERNEL_DEVICE, + GL_SEARCH_POPOVER_JOURNAL_FIELD_FILTER_AUDIT_SESSION, + GL_SEARCH_POPOVER_JOURNAL_FIELD_FILTER_EXECUTABLE_PATH +} GlSearchPopoverJournalFieldFilter; + +#define GL_TYPE_SEARCH_POPOVER (gl_search_popover_get_type ()) +G_DECLARE_FINAL_TYPE (GlSearchPopover, gl_search_popover, GL, SEARCH_POPOVER, GtkPopover) + +GtkWidget * gl_search_popover_new (void); +GlSearchPopoverJournalFieldFilter gl_search_popover_get_journal_search_field (GlSearchPopover *popover); + +G_END_DECLS + +#endif /* GL_SEARCH_POPOVER_H_ */ |