mirror of
https://github.com/altlinux/admc.git
synced 2025-01-08 01:18:25 +03:00
move layout to glade
This commit is contained in:
parent
1e43d647ac
commit
31dfebd211
1
.gitignore
vendored
Normal file
1
.gitignore
vendored
Normal file
@ -0,0 +1 @@
|
||||
obj/*
|
1
Makefile
1
Makefile
@ -9,6 +9,7 @@ OBJS := $(addprefix $(OBJDIR)/, $(addsuffix .o, $(basename $(notdir $(SOURCES)))
|
||||
CFLAGS += -Isrc/libs/
|
||||
CFLAGS += -g -Wall -Wformat
|
||||
CFLAGS += `pkg-config --cflags gtk+-3.0`
|
||||
CFLAGS += -rdynamic
|
||||
LIBS += `pkg-config --libs gtk+-3.0`
|
||||
LIBS += -lldap -llber -lresolv -lgsasl
|
||||
|
||||
|
373
data/adtool.glade
Normal file
373
data/adtool.glade
Normal file
@ -0,0 +1,373 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<!-- Generated with glade 3.22.1 -->
|
||||
<interface>
|
||||
<requires lib="gtk+" version="3.20"/>
|
||||
<object class="GtkTreeStore" id="attributes_model">
|
||||
<columns>
|
||||
<!-- column-name Name -->
|
||||
<column type="gchararray"/>
|
||||
<!-- column-name Value -->
|
||||
<column type="gchararray"/>
|
||||
</columns>
|
||||
</object>
|
||||
<object class="GtkTreeStore" id="containers_model">
|
||||
<columns>
|
||||
<!-- column-name containers_model_column_DN -->
|
||||
<column type="gchararray"/>
|
||||
<!-- column-name containers_model_column_Name -->
|
||||
<column type="gchararray"/>
|
||||
</columns>
|
||||
</object>
|
||||
<object class="GtkTreeModelFilter" id="containers_model_filter">
|
||||
<property name="child_model">containers_model</property>
|
||||
</object>
|
||||
<object class="GtkTreeStore" id="contents_model">
|
||||
<columns>
|
||||
<!-- column-name DN -->
|
||||
<column type="gchararray"/>
|
||||
<!-- column-name Name -->
|
||||
<column type="gchararray"/>
|
||||
<!-- column-name Type -->
|
||||
<column type="gchararray"/>
|
||||
<!-- column-name Description -->
|
||||
<column type="gchararray"/>
|
||||
</columns>
|
||||
</object>
|
||||
<object class="GtkTreeModelFilter" id="contents_model_filter">
|
||||
<property name="child_model">contents_model</property>
|
||||
</object>
|
||||
<object class="GtkWindow" id="window">
|
||||
<property name="width_request">900</property>
|
||||
<property name="height_request">600</property>
|
||||
<property name="can_focus">False</property>
|
||||
<child type="titlebar">
|
||||
<placeholder/>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkBox">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<property name="orientation">vertical</property>
|
||||
<child>
|
||||
<object class="GtkMenuBar" id="menu_bar">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<child>
|
||||
<object class="GtkMenuItem">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<property name="label" translatable="yes">_File</property>
|
||||
<property name="use_underline">True</property>
|
||||
<child type="submenu">
|
||||
<object class="GtkMenu">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<child>
|
||||
<object class="GtkImageMenuItem">
|
||||
<property name="label">gtk-new</property>
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<property name="use_underline">True</property>
|
||||
<property name="use_stock">True</property>
|
||||
</object>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkImageMenuItem">
|
||||
<property name="label">gtk-open</property>
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<property name="use_underline">True</property>
|
||||
<property name="use_stock">True</property>
|
||||
</object>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkImageMenuItem">
|
||||
<property name="label">gtk-save</property>
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<property name="use_underline">True</property>
|
||||
<property name="use_stock">True</property>
|
||||
</object>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkImageMenuItem">
|
||||
<property name="label">gtk-save-as</property>
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<property name="use_underline">True</property>
|
||||
<property name="use_stock">True</property>
|
||||
</object>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkSeparatorMenuItem">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
</object>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkImageMenuItem">
|
||||
<property name="label">gtk-quit</property>
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<property name="use_underline">True</property>
|
||||
<property name="use_stock">True</property>
|
||||
</object>
|
||||
</child>
|
||||
</object>
|
||||
</child>
|
||||
</object>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkMenuItem">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<property name="label" translatable="yes">_Edit</property>
|
||||
<property name="use_underline">True</property>
|
||||
<child type="submenu">
|
||||
<object class="GtkMenu">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<child>
|
||||
<object class="GtkImageMenuItem">
|
||||
<property name="label">gtk-cut</property>
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<property name="use_underline">True</property>
|
||||
<property name="use_stock">True</property>
|
||||
</object>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkImageMenuItem">
|
||||
<property name="label">gtk-copy</property>
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<property name="use_underline">True</property>
|
||||
<property name="use_stock">True</property>
|
||||
</object>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkImageMenuItem">
|
||||
<property name="label">gtk-paste</property>
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<property name="use_underline">True</property>
|
||||
<property name="use_stock">True</property>
|
||||
</object>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkImageMenuItem">
|
||||
<property name="label">gtk-delete</property>
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<property name="use_underline">True</property>
|
||||
<property name="use_stock">True</property>
|
||||
</object>
|
||||
</child>
|
||||
</object>
|
||||
</child>
|
||||
</object>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkMenuItem" id="menu_bar_view">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<property name="label" translatable="yes">_View</property>
|
||||
<property name="use_underline">True</property>
|
||||
<child type="submenu">
|
||||
<object class="GtkMenu">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<child>
|
||||
<object class="GtkCheckMenuItem" id="advanced_view_toggle">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<property name="label" translatable="yes">Advanced View</property>
|
||||
<property name="use_underline">True</property>
|
||||
<signal name="toggled" handler="advanced_view_toggled_func" swapped="no"/>
|
||||
</object>
|
||||
</child>
|
||||
</object>
|
||||
</child>
|
||||
</object>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkMenuItem">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<property name="label" translatable="yes">_Help</property>
|
||||
<property name="use_underline">True</property>
|
||||
<child type="submenu">
|
||||
<object class="GtkMenu">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<child>
|
||||
<object class="GtkImageMenuItem">
|
||||
<property name="label">gtk-about</property>
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">False</property>
|
||||
<property name="use_underline">True</property>
|
||||
<property name="use_stock">True</property>
|
||||
</object>
|
||||
</child>
|
||||
</object>
|
||||
</child>
|
||||
</object>
|
||||
</child>
|
||||
</object>
|
||||
<packing>
|
||||
<property name="expand">False</property>
|
||||
<property name="fill">True</property>
|
||||
<property name="position">0</property>
|
||||
</packing>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkPaned" id="outer_paned">
|
||||
<property name="width_request">200</property>
|
||||
<property name="height_request">500</property>
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">True</property>
|
||||
<property name="wide_handle">True</property>
|
||||
<child>
|
||||
<object class="GtkTreeView" id="containers_view">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">True</property>
|
||||
<property name="model">containers_model_filter</property>
|
||||
<child internal-child="selection">
|
||||
<object class="GtkTreeSelection">
|
||||
<signal name="changed" handler="containers_selection_changed_func" swapped="no"/>
|
||||
</object>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkTreeViewColumn">
|
||||
<property name="title" translatable="yes">Name</property>
|
||||
<child>
|
||||
<object class="GtkCellRendererText"/>
|
||||
<attributes>
|
||||
<attribute name="text">1</attribute>
|
||||
</attributes>
|
||||
</child>
|
||||
</object>
|
||||
</child>
|
||||
</object>
|
||||
<packing>
|
||||
<property name="resize">False</property>
|
||||
<property name="shrink">True</property>
|
||||
</packing>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkPaned" id="inner_paned">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">True</property>
|
||||
<property name="wide_handle">True</property>
|
||||
<child>
|
||||
<object class="GtkTreeView" id="contents_view">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">True</property>
|
||||
<property name="model">contents_model_filter</property>
|
||||
<child internal-child="selection">
|
||||
<object class="GtkTreeSelection">
|
||||
<signal name="changed" handler="contents_selection_changed_func" swapped="no"/>
|
||||
</object>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkTreeViewColumn">
|
||||
<property name="title" translatable="yes">Name</property>
|
||||
<child>
|
||||
<object class="GtkCellRendererText"/>
|
||||
<attributes>
|
||||
<attribute name="text">1</attribute>
|
||||
</attributes>
|
||||
</child>
|
||||
</object>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkTreeViewColumn">
|
||||
<property name="title" translatable="yes">Type</property>
|
||||
<child>
|
||||
<object class="GtkCellRendererText"/>
|
||||
<attributes>
|
||||
<attribute name="text">2</attribute>
|
||||
</attributes>
|
||||
</child>
|
||||
</object>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkTreeViewColumn">
|
||||
<property name="title" translatable="yes">Description</property>
|
||||
<child>
|
||||
<object class="GtkCellRendererText"/>
|
||||
<attributes>
|
||||
<attribute name="text">3</attribute>
|
||||
</attributes>
|
||||
</child>
|
||||
</object>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkTreeViewColumn">
|
||||
<property name="title" translatable="yes">DN</property>
|
||||
</object>
|
||||
</child>
|
||||
</object>
|
||||
<packing>
|
||||
<property name="resize">False</property>
|
||||
<property name="shrink">True</property>
|
||||
</packing>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkTreeView" id="attributes_view">
|
||||
<property name="visible">True</property>
|
||||
<property name="can_focus">True</property>
|
||||
<property name="model">attributes_model</property>
|
||||
<child internal-child="selection">
|
||||
<object class="GtkTreeSelection"/>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkTreeViewColumn">
|
||||
<property name="title" translatable="yes">Name</property>
|
||||
<child>
|
||||
<object class="GtkCellRendererText"/>
|
||||
<attributes>
|
||||
<attribute name="text">0</attribute>
|
||||
</attributes>
|
||||
</child>
|
||||
</object>
|
||||
</child>
|
||||
<child>
|
||||
<object class="GtkTreeViewColumn">
|
||||
<property name="title" translatable="yes">Value</property>
|
||||
<child>
|
||||
<object class="GtkCellRendererText">
|
||||
<property name="editable">True</property>
|
||||
</object>
|
||||
<attributes>
|
||||
<attribute name="text">1</attribute>
|
||||
</attributes>
|
||||
</child>
|
||||
</object>
|
||||
</child>
|
||||
</object>
|
||||
<packing>
|
||||
<property name="resize">True</property>
|
||||
<property name="shrink">True</property>
|
||||
</packing>
|
||||
</child>
|
||||
</object>
|
||||
<packing>
|
||||
<property name="resize">True</property>
|
||||
<property name="shrink">True</property>
|
||||
</packing>
|
||||
</child>
|
||||
</object>
|
||||
<packing>
|
||||
<property name="expand">True</property>
|
||||
<property name="fill">True</property>
|
||||
<property name="position">1</property>
|
||||
</packing>
|
||||
</child>
|
||||
<child>
|
||||
<placeholder/>
|
||||
</child>
|
||||
</object>
|
||||
</child>
|
||||
</object>
|
||||
</interface>
|
@ -1,6 +0,0 @@
|
||||
#pragma once
|
||||
|
||||
#include <gtk/gtk.h>
|
||||
|
||||
GtkWidget* attributes_init();
|
||||
void attributes_update_model(const char* new_root_dn);
|
@ -1,5 +1,5 @@
|
||||
|
||||
#include "attributes_pane.h"
|
||||
#include "attributes_view.h"
|
||||
|
||||
#include "constants.h"
|
||||
#include "utils.h"
|
||||
@ -14,7 +14,7 @@ enum {
|
||||
ATTRIBUTES_COLUMN_COUNT
|
||||
};
|
||||
|
||||
GtkWidget* attributes_view = NULL;
|
||||
GtkTreeView* attributes_view = NULL;
|
||||
char selected_dn[DN_LENGTH_MAX];
|
||||
|
||||
// Lists attributes of last selected entry in contents pane
|
||||
@ -27,8 +27,7 @@ void attributes_value_edited_func(
|
||||
gchar* new_text,
|
||||
gpointer user_data)
|
||||
{
|
||||
GtkTreeView* view = GTK_TREE_VIEW(attributes_view);
|
||||
GtkTreeModel* model = gtk_tree_view_get_model(view);
|
||||
GtkTreeModel* model = gtk_tree_view_get_model(attributes_view);
|
||||
|
||||
GtkTreeIter iter;
|
||||
gtk_tree_model_get_iter_from_string(model, &iter, path_string);
|
||||
@ -54,31 +53,10 @@ void attributes_value_edited_func(
|
||||
free(old_value);
|
||||
}
|
||||
|
||||
GtkWidget* attributes_init() {
|
||||
// NOTE: model is set when an entry is selected in contents pane
|
||||
GtkTreeStore* model = gtk_tree_store_new(ATTRIBUTES_COLUMN_COUNT, G_TYPE_STRING, G_TYPE_STRING);
|
||||
attributes_view = gtk_tree_view_new_with_model(GTK_TREE_MODEL(model));
|
||||
|
||||
// Name column
|
||||
GtkTreeViewColumn* name_column = gtk_tree_view_column_new_with_attributes("Name", gtk_cell_renderer_text_new(), "text", ATTRIBUTES_COLUMN_NAME, NULL);
|
||||
gtk_tree_view_append_column(GTK_TREE_VIEW(attributes_view), name_column);
|
||||
|
||||
// Value column, editable
|
||||
|
||||
// Create special editable renderer for value column
|
||||
GtkCellRenderer* value_renderer = gtk_cell_renderer_text_new();
|
||||
g_object_set(value_renderer, "editable", TRUE, NULL);
|
||||
g_signal_connect(value_renderer, "edited", (GCallback) attributes_value_edited_func, NULL);
|
||||
|
||||
GtkTreeViewColumn* value_column = gtk_tree_view_column_new_with_attributes("Value", value_renderer, "text", ATTRIBUTES_COLUMN_VALUE, NULL);
|
||||
gtk_tree_view_append_column(GTK_TREE_VIEW(attributes_view), value_column);
|
||||
|
||||
return attributes_view;
|
||||
}
|
||||
|
||||
void attributes_update_model(const char* new_root_dn) {
|
||||
GtkTreeStore* model = gtk_tree_store_new(ATTRIBUTES_COLUMN_COUNT, G_TYPE_STRING, G_TYPE_STRING);
|
||||
// entry* e = shget(entries, new_root_dn);
|
||||
// NOTE: model is set when an entry is selected in contents pane
|
||||
void attributes_populate_model(const char* new_root_dn) {
|
||||
GtkTreeStore* model = GTK_TREE_STORE(gtk_tree_view_get_model(attributes_view));
|
||||
gtk_tree_store_clear(model);
|
||||
|
||||
// Populate model
|
||||
// List all key->value pairs in order
|
||||
@ -101,8 +79,9 @@ void attributes_update_model(const char* new_root_dn) {
|
||||
}
|
||||
}
|
||||
|
||||
gtk_tree_view_set_model(GTK_TREE_VIEW(attributes_view), GTK_TREE_MODEL(model));
|
||||
g_object_unref(model);
|
||||
|
||||
strncpy(selected_dn, new_root_dn, DN_LENGTH_MAX);
|
||||
}
|
||||
|
||||
void attributes_init(GtkBuilder* builder) {
|
||||
attributes_view = GTK_TREE_VIEW(gtk_builder_get_object(builder, "attributes_view"));
|
||||
}
|
6
src/attributes_view.h
Normal file
6
src/attributes_view.h
Normal file
@ -0,0 +1,6 @@
|
||||
#pragma once
|
||||
|
||||
#include <gtk/gtk.h>
|
||||
|
||||
void attributes_init(GtkBuilder* builder);
|
||||
void attributes_populate_model(const char* new_root_dn);
|
@ -1,127 +0,0 @@
|
||||
|
||||
#include "containers_pane.h"
|
||||
|
||||
#include "contents_pane.h"
|
||||
#include "menubar.h"
|
||||
#include "constants.h"
|
||||
#include "utils.h"
|
||||
#include "entry.h"
|
||||
|
||||
#include "stb_ds.h"
|
||||
#include <string.h>
|
||||
#include <stdbool.h>
|
||||
#include <gtk/gtk.h>
|
||||
|
||||
enum {
|
||||
CONTAINERS_COLUMN_DN,
|
||||
CONTAINERS_COLUMN_NAME,
|
||||
CONTAINERS_COLUMN_COUNT
|
||||
};
|
||||
|
||||
GtkWidget* containers_view = NULL;
|
||||
|
||||
void containers_refilter_model() {
|
||||
GtkTreeModel* model_filter = gtk_tree_view_get_model(GTK_TREE_VIEW(containers_view));
|
||||
gtk_tree_model_filter_refilter(GTK_TREE_MODEL_FILTER(model_filter));
|
||||
}
|
||||
|
||||
void containers_populate_model(GtkTreeStore* model, char* node_dn, GtkTreeIter* parent) {
|
||||
// Populate model with name's of entries
|
||||
|
||||
entry* e = shget(entries, node_dn);
|
||||
|
||||
// Skip if entry is not a container
|
||||
if (!entry_is_container(e)) {
|
||||
return;
|
||||
}
|
||||
|
||||
// TODO: handle no name?
|
||||
STR_ARRAY name = entry_get_attribute(e, "name");
|
||||
|
||||
GtkTreeIter this_node;
|
||||
gtk_tree_store_append(model, &this_node, parent);
|
||||
gtk_tree_store_set(model, &this_node, CONTAINERS_COLUMN_DN, node_dn, -1);
|
||||
gtk_tree_store_set(model, &this_node, CONTAINERS_COLUMN_NAME, name[0], -1);
|
||||
|
||||
// Recurse into entry's children
|
||||
for (int i = 0; i < arrlen(e->children); i++) {
|
||||
char* child_dn = e->children[i];
|
||||
|
||||
containers_populate_model(model, child_dn, &this_node);
|
||||
}
|
||||
}
|
||||
|
||||
void containers_selection_changed_func(GtkTreeSelection* selection, gpointer user_data) {
|
||||
// Get selected iter
|
||||
GtkTreeView* view = gtk_tree_selection_get_tree_view(selection);
|
||||
GtkTreeModel* model = gtk_tree_view_get_model(view);
|
||||
GtkTreeIter iter;
|
||||
gboolean any_selected = gtk_tree_selection_get_selected(selection, &model, &iter);
|
||||
if (!any_selected) {
|
||||
return;
|
||||
}
|
||||
|
||||
// Get dn of selected iter
|
||||
char* dn;
|
||||
gtk_tree_model_get(model, &iter, CONTAINERS_COLUMN_DN, &dn, -1);
|
||||
|
||||
// Update contents model
|
||||
contents_update_model(dn);
|
||||
|
||||
free(dn);
|
||||
}
|
||||
|
||||
gboolean containers_filter_func(
|
||||
GtkTreeModel *model,
|
||||
GtkTreeIter *iter,
|
||||
gpointer data)
|
||||
{
|
||||
// Filter out entries with "showInAdvancedViewOnly" set to TRUE
|
||||
gboolean visible = TRUE;
|
||||
|
||||
char* dn;
|
||||
gtk_tree_model_get(model, iter, CONTAINERS_COLUMN_DN, &dn, -1);
|
||||
|
||||
entry* e = shget(entries, dn);
|
||||
STR_ARRAY showInAdvancedViewOnly = entry_get_attribute(e, "showInAdvancedViewOnly");
|
||||
if (!advanced_view_is_on() && showInAdvancedViewOnly != NULL && streql(showInAdvancedViewOnly[0], "TRUE")) {
|
||||
visible = FALSE;
|
||||
}
|
||||
|
||||
g_free(dn);
|
||||
|
||||
return visible;
|
||||
}
|
||||
|
||||
GtkWidget* containers_init() {
|
||||
// 2 columns: name and dn
|
||||
// only name is shown, dn is used for identification in control
|
||||
|
||||
// Create and populate child model
|
||||
GtkTreeStore* child_model = gtk_tree_store_new(CONTAINERS_COLUMN_COUNT, G_TYPE_STRING, G_TYPE_STRING);
|
||||
containers_populate_model(child_model, HEAD_DN, NULL);
|
||||
|
||||
// Create model filter
|
||||
GtkTreeModel* model = gtk_tree_model_filter_new(GTK_TREE_MODEL(child_model), NULL);
|
||||
gtk_tree_model_filter_set_visible_func(GTK_TREE_MODEL_FILTER(model), containers_filter_func, NULL, NULL);
|
||||
|
||||
containers_view = gtk_tree_view_new_with_model(GTK_TREE_MODEL(model));
|
||||
g_object_unref(model);
|
||||
|
||||
// DN column, invisible, only for identification
|
||||
GtkTreeViewColumn* dn_column = gtk_tree_view_column_new_with_attributes("DN", gtk_cell_renderer_text_new(), "text", CONTAINERS_COLUMN_DN, NULL);
|
||||
gtk_tree_view_append_column(GTK_TREE_VIEW(containers_view), dn_column);
|
||||
gtk_tree_view_column_set_visible(dn_column, FALSE);
|
||||
|
||||
// Name column
|
||||
GtkTreeViewColumn* name_column = gtk_tree_view_column_new_with_attributes("Name", gtk_cell_renderer_text_new(), "text", CONTAINERS_COLUMN_NAME, NULL);
|
||||
gtk_tree_view_append_column(GTK_TREE_VIEW(containers_view), name_column);
|
||||
gtk_tree_view_column_set_sizing(name_column, GTK_TREE_VIEW_COLUMN_FIXED);
|
||||
gtk_tree_view_column_set_fixed_width(name_column, 300);
|
||||
|
||||
// Selection changed callback
|
||||
GtkTreeSelection* tree_selection = gtk_tree_view_get_selection(GTK_TREE_VIEW(containers_view));
|
||||
g_signal_connect(tree_selection, "changed", G_CALLBACK(containers_selection_changed_func), NULL);
|
||||
|
||||
return containers_view;
|
||||
}
|
@ -1,6 +0,0 @@
|
||||
#pragma once
|
||||
|
||||
#include <gtk/gtk.h>
|
||||
|
||||
GtkWidget* containers_init();
|
||||
void containers_refilter_model();
|
109
src/containers_view.c
Normal file
109
src/containers_view.c
Normal file
@ -0,0 +1,109 @@
|
||||
|
||||
#include "containers_view.h"
|
||||
|
||||
#include "contents_view.h"
|
||||
#include "constants.h"
|
||||
#include "utils.h"
|
||||
#include "entry.h"
|
||||
#include "menu_bar.h"
|
||||
|
||||
#include "stb_ds.h"
|
||||
#include <string.h>
|
||||
#include <stdbool.h>
|
||||
#include <gtk/gtk.h>
|
||||
|
||||
enum {
|
||||
CONTAINERS_COLUMN_DN,
|
||||
CONTAINERS_COLUMN_NAME,
|
||||
};
|
||||
|
||||
GtkTreeView* containers_view = NULL;
|
||||
|
||||
void containers_refilter() {
|
||||
GtkTreeModelFilter* model_filter = GTK_TREE_MODEL_FILTER(gtk_tree_view_get_model(containers_view));
|
||||
gtk_tree_model_filter_refilter(model_filter);
|
||||
}
|
||||
|
||||
void containers_selection_changed_func(GtkTreeSelection* selection, gpointer user_data) {
|
||||
// Get selected iter
|
||||
GtkTreeView* view = gtk_tree_selection_get_tree_view(selection);
|
||||
GtkTreeModel* model = gtk_tree_view_get_model(view);
|
||||
GtkTreeIter iter;
|
||||
gboolean any_selected = gtk_tree_selection_get_selected(selection, &model, &iter);
|
||||
if (!any_selected) {
|
||||
return;
|
||||
}
|
||||
|
||||
// Get dn of selected iter
|
||||
char* dn;
|
||||
gtk_tree_model_get(model, &iter, CONTAINERS_COLUMN_DN, &dn, -1);
|
||||
|
||||
// Update contents model
|
||||
contents_populate_model(dn);
|
||||
|
||||
free(dn);
|
||||
}
|
||||
|
||||
gboolean containers_filter_func(
|
||||
GtkTreeModel *model,
|
||||
GtkTreeIter *iter,
|
||||
gpointer data)
|
||||
{
|
||||
// Filter out entries with "showInAdvancedViewOnly" set to TRUE
|
||||
gboolean visible = TRUE;
|
||||
|
||||
char* dn;
|
||||
gtk_tree_model_get(model, iter, CONTAINERS_COLUMN_DN, &dn, -1);
|
||||
|
||||
entry* e = shget(entries, dn);
|
||||
STR_ARRAY showInAdvancedViewOnly = entry_get_attribute(e, "showInAdvancedViewOnly");
|
||||
if (!advanced_view_is_on() && showInAdvancedViewOnly != NULL && streql(showInAdvancedViewOnly[0], "TRUE")) {
|
||||
visible = FALSE;
|
||||
}
|
||||
|
||||
g_free(dn);
|
||||
|
||||
return visible;
|
||||
}
|
||||
|
||||
void containers_populate_model_recursive(GtkTreeStore* model, char* node_dn, GtkTreeIter* parent) {
|
||||
// Populate model with name's of entries
|
||||
|
||||
entry* e = shget(entries, node_dn);
|
||||
|
||||
// Skip if entry is not a container
|
||||
// TODO: move this to filter?
|
||||
// TODO: make containers and contents share model?
|
||||
// contents can use "gtk_tree_path_is_descendant()"
|
||||
if (!entry_is_container(e)) {
|
||||
return;
|
||||
}
|
||||
|
||||
// TODO: handle no name?
|
||||
STR_ARRAY name = entry_get_attribute(e, "name");
|
||||
|
||||
GtkTreeIter this_node;
|
||||
gtk_tree_store_append(model, &this_node, parent);
|
||||
gtk_tree_store_set(model, &this_node, CONTAINERS_COLUMN_DN, node_dn, -1);
|
||||
gtk_tree_store_set(model, &this_node, CONTAINERS_COLUMN_NAME, name[0], -1);
|
||||
|
||||
// Recurse into entry's children
|
||||
for (int i = 0; i < arrlen(e->children); i++) {
|
||||
char* child_dn = e->children[i];
|
||||
|
||||
containers_populate_model_recursive(model, child_dn, &this_node);
|
||||
}
|
||||
}
|
||||
|
||||
void containers_init(GtkBuilder* builder) {
|
||||
containers_view = GTK_TREE_VIEW(gtk_builder_get_object(builder, "containers_view"));
|
||||
|
||||
// Populate model
|
||||
GtkTreeStore* model = GTK_TREE_STORE(gtk_builder_get_object(builder, "containers_model"));
|
||||
containers_populate_model_recursive(model, HEAD_DN, NULL);
|
||||
|
||||
// Set filter func
|
||||
GtkTreeModelFilter* model_filter = GTK_TREE_MODEL_FILTER((gtk_tree_view_get_model(containers_view)));
|
||||
gtk_tree_model_filter_set_visible_func(model_filter, containers_filter_func, NULL, NULL);
|
||||
gtk_tree_model_filter_refilter(model_filter);
|
||||
}
|
6
src/containers_view.h
Normal file
6
src/containers_view.h
Normal file
@ -0,0 +1,6 @@
|
||||
#pragma once
|
||||
|
||||
#include <gtk/gtk.h>
|
||||
|
||||
void containers_init(GtkBuilder* builder);
|
||||
void containers_refilter();
|
@ -1,113 +0,0 @@
|
||||
|
||||
#include "contents_pane.h"
|
||||
|
||||
#include "attributes_pane.h"
|
||||
#include "entry.h"
|
||||
#include "constants.h"
|
||||
|
||||
#include "stb_ds.h"
|
||||
#include <gtk/gtk.h>
|
||||
|
||||
enum {
|
||||
CONTENTS_COLUMN_DN,
|
||||
CONTENTS_COLUMN_NAME,
|
||||
CONTENTS_COLUMN_CATEGORY,
|
||||
CONTENTS_COLUMN_DESCRIPTION,
|
||||
CONTENTS_COLUMN_COUNT
|
||||
};
|
||||
|
||||
GtkWidget* contents_view = NULL;
|
||||
|
||||
void contents_selection_changed_func(GtkTreeSelection* selection, gpointer user_data) {
|
||||
GtkTreeView* view = gtk_tree_selection_get_tree_view(selection);
|
||||
GtkTreeModel* model = gtk_tree_view_get_model(view);
|
||||
|
||||
GtkTreeIter iter;
|
||||
|
||||
gboolean any_selected = gtk_tree_selection_get_selected(selection, &model, &iter);
|
||||
if (!any_selected) {
|
||||
return;
|
||||
}
|
||||
|
||||
// Get dn of selected iter
|
||||
char* dn;
|
||||
gtk_tree_model_get(model, &iter, CONTENTS_COLUMN_DN, &dn, -1);
|
||||
|
||||
// Update contents model
|
||||
attributes_update_model(dn);
|
||||
|
||||
free(dn);
|
||||
}
|
||||
|
||||
void contents_update_model(const char* new_root_dn) {
|
||||
GtkTreeStore* model = gtk_tree_store_new(CONTENTS_COLUMN_COUNT, G_TYPE_STRING, G_TYPE_STRING, G_TYPE_STRING, G_TYPE_STRING);
|
||||
|
||||
entry* e = shget(entries, new_root_dn);
|
||||
|
||||
// Populate model
|
||||
for (int i = 0; i < arrlen(e->children); i++) {
|
||||
char* child_dn = e->children[i];
|
||||
entry* child = shget(entries, child_dn);
|
||||
|
||||
GtkTreeIter this_node;
|
||||
gtk_tree_store_append(model, &this_node, NULL);
|
||||
|
||||
// DN
|
||||
gtk_tree_store_set(model, &this_node, CONTENTS_COLUMN_DN, child->dn, -1);
|
||||
|
||||
// Name
|
||||
STR_ARRAY name = entry_get_attribute(child, "name");
|
||||
gtk_tree_store_set(model, &this_node, CONTENTS_COLUMN_NAME, name[0], -1);
|
||||
|
||||
// Category
|
||||
STR_ARRAY category_dn = entry_get_attribute(child, "objectCategory");
|
||||
if (category_dn == NULL) {
|
||||
gtk_tree_store_set(model, &this_node, CONTENTS_COLUMN_DESCRIPTION, "none", -1);
|
||||
} else {
|
||||
char short_category[DN_LENGTH_MAX];
|
||||
first_element_in_dn(short_category, category_dn[0], DN_LENGTH_MAX);
|
||||
gtk_tree_store_set(model, &this_node, CONTENTS_COLUMN_CATEGORY, short_category, -1);
|
||||
}
|
||||
|
||||
// Description
|
||||
STR_ARRAY description = entry_get_attribute(child, "description");
|
||||
if (description == NULL) {
|
||||
gtk_tree_store_set(model, &this_node, CONTENTS_COLUMN_DESCRIPTION, "none", -1);
|
||||
} else {
|
||||
gtk_tree_store_set(model, &this_node, CONTENTS_COLUMN_DESCRIPTION, description[0], -1);
|
||||
}
|
||||
}
|
||||
|
||||
gtk_tree_view_set_model(GTK_TREE_VIEW(contents_view), GTK_TREE_MODEL(model));
|
||||
g_object_unref(model);
|
||||
}
|
||||
|
||||
GtkWidget* contents_init() {
|
||||
// NOTE: contents model is populated when a container in containers panel is selected
|
||||
contents_view = gtk_tree_view_new();
|
||||
|
||||
GtkTreeViewColumn* dn_column = gtk_tree_view_column_new_with_attributes("DN", gtk_cell_renderer_text_new(), "text", CONTENTS_COLUMN_DN, NULL);
|
||||
gtk_tree_view_append_column(GTK_TREE_VIEW(contents_view), dn_column);
|
||||
gtk_tree_view_column_set_visible(dn_column, FALSE);
|
||||
|
||||
GtkTreeViewColumn* name_column = gtk_tree_view_column_new_with_attributes("Name", gtk_cell_renderer_text_new(), "text", CONTENTS_COLUMN_NAME, NULL);
|
||||
gtk_tree_view_append_column(GTK_TREE_VIEW(contents_view), name_column);
|
||||
gtk_tree_view_column_set_sizing(name_column, GTK_TREE_VIEW_COLUMN_FIXED);
|
||||
gtk_tree_view_column_set_fixed_width(name_column, 200);
|
||||
|
||||
GtkTreeViewColumn* category_column = gtk_tree_view_column_new_with_attributes("Category", gtk_cell_renderer_text_new(), "text", CONTENTS_COLUMN_CATEGORY, NULL);
|
||||
gtk_tree_view_append_column(GTK_TREE_VIEW(contents_view), category_column);
|
||||
gtk_tree_view_column_set_sizing(category_column, GTK_TREE_VIEW_COLUMN_FIXED);
|
||||
gtk_tree_view_column_set_fixed_width(category_column, 200);
|
||||
|
||||
GtkTreeViewColumn* description_column = gtk_tree_view_column_new_with_attributes("Description", gtk_cell_renderer_text_new(), "text", CONTENTS_COLUMN_DESCRIPTION, NULL);
|
||||
gtk_tree_view_append_column(GTK_TREE_VIEW(contents_view), description_column);
|
||||
gtk_tree_view_column_set_sizing(description_column, GTK_TREE_VIEW_COLUMN_FIXED);
|
||||
gtk_tree_view_column_set_fixed_width(description_column, 300);
|
||||
|
||||
// Selection changed callback
|
||||
GtkTreeSelection* tree_selection = gtk_tree_view_get_selection(GTK_TREE_VIEW(contents_view));
|
||||
g_signal_connect(tree_selection, "changed", G_CALLBACK(contents_selection_changed_func), NULL);
|
||||
|
||||
return contents_view;
|
||||
}
|
@ -1,6 +0,0 @@
|
||||
#pragma once
|
||||
|
||||
#include <gtk/gtk.h>
|
||||
|
||||
GtkWidget* contents_init();
|
||||
void contents_update_model(const char* new_root);
|
122
src/contents_view.c
Normal file
122
src/contents_view.c
Normal file
@ -0,0 +1,122 @@
|
||||
|
||||
#include "contents_view.h"
|
||||
|
||||
#include "attributes_view.h"
|
||||
#include "entry.h"
|
||||
#include "constants.h"
|
||||
#include "menu_bar.h"
|
||||
#include "utils.h"
|
||||
|
||||
#include "stb_ds.h"
|
||||
#include <gtk/gtk.h>
|
||||
|
||||
enum {
|
||||
CONTENTS_COLUMN_DN,
|
||||
CONTENTS_COLUMN_NAME,
|
||||
CONTENTS_COLUMN_CATEGORY,
|
||||
CONTENTS_COLUMN_DESCRIPTION,
|
||||
CONTENTS_COLUMN_COUNT
|
||||
};
|
||||
|
||||
GtkTreeView* contents_view = NULL;
|
||||
|
||||
void contents_refilter() {
|
||||
GtkTreeModelFilter* model_filter = GTK_TREE_MODEL_FILTER(gtk_tree_view_get_model(contents_view));
|
||||
gtk_tree_model_filter_refilter(model_filter);
|
||||
}
|
||||
|
||||
gboolean contents_filter_func(
|
||||
GtkTreeModel *model,
|
||||
GtkTreeIter *iter,
|
||||
gpointer data)
|
||||
{
|
||||
// Filter out entries with "showInAdvancedViewOnly" set to TRUE
|
||||
gboolean visible = TRUE;
|
||||
|
||||
char* dn;
|
||||
gtk_tree_model_get(model, iter, CONTENTS_COLUMN_DN, &dn, -1);
|
||||
if (dn != NULL) {
|
||||
entry* e = shget(entries, dn);
|
||||
STR_ARRAY showInAdvancedViewOnly = entry_get_attribute(e, "showInAdvancedViewOnly");
|
||||
if (!advanced_view_is_on() && showInAdvancedViewOnly != NULL && streql(showInAdvancedViewOnly[0], "TRUE")) {
|
||||
visible = FALSE;
|
||||
}
|
||||
|
||||
g_free(dn);
|
||||
}
|
||||
|
||||
return visible;
|
||||
}
|
||||
|
||||
void contents_selection_changed_func(GtkTreeSelection* selection, gpointer user_data) {
|
||||
GtkTreeView* view = gtk_tree_selection_get_tree_view(selection);
|
||||
GtkTreeModel* model = gtk_tree_view_get_model(view);
|
||||
|
||||
GtkTreeIter iter;
|
||||
|
||||
gboolean any_selected = gtk_tree_selection_get_selected(selection, &model, &iter);
|
||||
if (!any_selected) {
|
||||
return;
|
||||
}
|
||||
|
||||
// Get dn of selected iter
|
||||
char* dn;
|
||||
gtk_tree_model_get(model, &iter, CONTENTS_COLUMN_DN, &dn, -1);
|
||||
|
||||
// Update contents model
|
||||
attributes_populate_model(dn);
|
||||
|
||||
free(dn);
|
||||
}
|
||||
|
||||
// NOTE: contents model is repopulated everytime a new container is selected
|
||||
void contents_populate_model(const char* new_root_dn) {
|
||||
GtkTreeModelFilter* model_filter = GTK_TREE_MODEL_FILTER(gtk_tree_view_get_model(contents_view));
|
||||
GtkTreeStore* model = GTK_TREE_STORE(gtk_tree_model_filter_get_model(model_filter));
|
||||
gtk_tree_store_clear(model);
|
||||
|
||||
entry* e = shget(entries, new_root_dn);
|
||||
|
||||
// Populate model
|
||||
for (int i = 0; i < arrlen(e->children); i++) {
|
||||
char* child_dn = e->children[i];
|
||||
entry* child = shget(entries, child_dn);
|
||||
|
||||
GtkTreeIter this_node;
|
||||
gtk_tree_store_append(model, &this_node, NULL);
|
||||
|
||||
// DN
|
||||
gtk_tree_store_set(model, &this_node, CONTENTS_COLUMN_DN, child->dn, -1);
|
||||
|
||||
// Name
|
||||
STR_ARRAY name = entry_get_attribute(child, "name");
|
||||
gtk_tree_store_set(model, &this_node, CONTENTS_COLUMN_NAME, name[0], -1);
|
||||
|
||||
// Category
|
||||
STR_ARRAY category_dn = entry_get_attribute(child, "objectCategory");
|
||||
if (category_dn == NULL) {
|
||||
gtk_tree_store_set(model, &this_node, CONTENTS_COLUMN_DESCRIPTION, "none", -1);
|
||||
} else {
|
||||
char short_category[DN_LENGTH_MAX];
|
||||
first_element_in_dn(short_category, category_dn[0], DN_LENGTH_MAX);
|
||||
gtk_tree_store_set(model, &this_node, CONTENTS_COLUMN_CATEGORY, short_category, -1);
|
||||
}
|
||||
|
||||
// Description
|
||||
STR_ARRAY description = entry_get_attribute(child, "description");
|
||||
if (description == NULL) {
|
||||
gtk_tree_store_set(model, &this_node, CONTENTS_COLUMN_DESCRIPTION, "none", -1);
|
||||
} else {
|
||||
gtk_tree_store_set(model, &this_node, CONTENTS_COLUMN_DESCRIPTION, description[0], -1);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void contents_init(GtkBuilder* builder) {
|
||||
contents_view = GTK_TREE_VIEW(gtk_builder_get_object(builder, "contents_view"));
|
||||
|
||||
// Set filter func
|
||||
GtkTreeModelFilter* model_filter = GTK_TREE_MODEL_FILTER((gtk_tree_view_get_model(contents_view)));
|
||||
gtk_tree_model_filter_set_visible_func(model_filter, contents_filter_func, NULL, NULL);
|
||||
gtk_tree_model_filter_refilter(model_filter);
|
||||
}
|
7
src/contents_view.h
Normal file
7
src/contents_view.h
Normal file
@ -0,0 +1,7 @@
|
||||
#pragma once
|
||||
|
||||
#include <gtk/gtk.h>
|
||||
|
||||
void contents_init(GtkBuilder* builder);
|
||||
void contents_populate_model(const char* new_root);
|
||||
void contents_refilter();
|
31
src/entry.c
31
src/entry.c
@ -257,20 +257,31 @@ void entry_init_fake() {
|
||||
|
||||
// Load entries recursively
|
||||
entry_load(HEAD_DN);
|
||||
|
||||
|
||||
// HEAD_DN= "DC=domain,DC=alt"
|
||||
entry* head = make_fake_entry(HEAD_DN, NULL, true, "Person");
|
||||
|
||||
entry* dave = make_fake_entry("dave", head, true, "Person");
|
||||
entry* daves_dog = make_fake_entry("daves_dog", dave, false, "Robot");
|
||||
entry* daves_car = make_fake_entry("daves_car", dave, false, "Robot");
|
||||
|
||||
entry* alice = make_fake_entry("alice", head, true, "Person");
|
||||
entry* alices_child = make_fake_entry("alices_child", alice, false, "Robot");
|
||||
entry* alices_son = make_fake_entry("alices_son", alice, false, "Person");
|
||||
entry* alices_second_son = make_fake_entry("alices_second_son", alice, false, "Person");
|
||||
make_fake_entry("daves_dog", dave, false, "Robot");
|
||||
make_fake_entry("daves_car", dave, false, "Robot");
|
||||
|
||||
entry* mark = make_fake_entry("mark", head, true, "Person");
|
||||
entry* marks_son = make_fake_entry("marks_son", mark, false, "Robot");
|
||||
entry* marks_daughter = make_fake_entry("marks_daughter", mark, false, "Robot");
|
||||
make_fake_entry("marks_son", mark, false, "Robot");
|
||||
make_fake_entry("marks_daughter", mark, false, "Robot");
|
||||
|
||||
entry* alice = make_fake_entry("alice", head, true, "Person");
|
||||
make_fake_entry("alices_child", alice, false, "Robot");
|
||||
make_fake_entry("alices_son", alice, false, "Person");
|
||||
make_fake_entry("alices_second_son", alice, false, "Person");
|
||||
|
||||
entry* advanced_bob = make_fake_entry("advanced_bob", head, true, "Person");
|
||||
make_fake_entry("advanced_bobs_son", advanced_bob, false, "Robot");
|
||||
make_fake_entry("advanced_bobs_daughter", advanced_bob, false, "Robot");
|
||||
add_fake_attribute(advanced_bob, "showInAdvancedViewOnly", "TRUE");
|
||||
|
||||
entry* advanced_klaren = make_fake_entry("advanced_klaren", head, true, "Person");
|
||||
make_fake_entry("advanced_klarens_son", advanced_klaren, false, "Robot");
|
||||
make_fake_entry("advanced_klarens_daughter", advanced_klaren, false, "Robot");
|
||||
add_fake_attribute(advanced_klaren, "showInAdvancedViewOnly", "TRUE");
|
||||
|
||||
}
|
||||
|
33
src/main.c
33
src/main.c
@ -1,5 +1,8 @@
|
||||
|
||||
#include "mainwindow.h"
|
||||
// #include "mainwindow.h"
|
||||
#include "containers_view.h"
|
||||
#include "contents_view.h"
|
||||
#include "attributes_view.h"
|
||||
#include "entry.h"
|
||||
|
||||
#include "active_directory.h"
|
||||
@ -32,8 +35,32 @@ int main(int argc, char** argv) {
|
||||
|
||||
// Setup UI
|
||||
gtk_init(&argc, &argv);
|
||||
GtkWidget* window = mainwindow_init();
|
||||
gtk_widget_show_all(window);
|
||||
|
||||
// Load builder
|
||||
GtkBuilder *builder = gtk_builder_new_from_file("data/adtool.glade");
|
||||
if (builder == NULL) {
|
||||
printf("Failed to load glade file\n");
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
containers_init(builder);
|
||||
contents_init(builder);
|
||||
attributes_init(builder);
|
||||
|
||||
gtk_builder_connect_signals(builder, NULL);
|
||||
|
||||
// Get window object from builder
|
||||
GtkWidget* window = GTK_WIDGET(gtk_builder_get_object(builder, "window"));
|
||||
if (window == NULL) {
|
||||
printf("Failed to get window widget\n");
|
||||
|
||||
return 0;
|
||||
}
|
||||
gtk_widget_show(window);
|
||||
|
||||
g_object_unref(G_OBJECT(builder));
|
||||
|
||||
gtk_main();
|
||||
|
||||
return 0;
|
||||
|
@ -1,65 +0,0 @@
|
||||
|
||||
#include "mainwindow.h"
|
||||
|
||||
#include "menubar.h"
|
||||
#include "containers_pane.h"
|
||||
#include "contents_pane.h"
|
||||
#include "attributes_pane.h"
|
||||
|
||||
#include <gtk/gtk.h>
|
||||
|
||||
// TODO: good behavior would be 3 panes, border adjustable between each
|
||||
// none of them auto-resize, start out at reasonable widths for each column
|
||||
GtkWidget* mainwindow_init() {
|
||||
GtkWidget* menubar = menubar_init();
|
||||
GtkWidget* containers_view = containers_init();
|
||||
GtkWidget* contents_view = contents_init();
|
||||
GtkWidget* attributes_view = attributes_init();
|
||||
|
||||
// Horizontal box containing panes
|
||||
// Expand and fill each pane
|
||||
GtkWidget* panes = gtk_paned_new(GTK_ORIENTATION_HORIZONTAL);
|
||||
{
|
||||
GtkWidget* frame1 = gtk_frame_new("Containers");
|
||||
GtkWidget* frame2 = gtk_frame_new("Contents");
|
||||
gtk_frame_set_shadow_type(GTK_FRAME(frame1), GTK_SHADOW_IN);
|
||||
gtk_frame_set_shadow_type(GTK_FRAME(frame2), GTK_SHADOW_IN);
|
||||
|
||||
gtk_widget_set_size_request(panes, 200, -1);
|
||||
|
||||
// gtk_paned_pack1(GTK_PANED(panes), frame1, true, false);
|
||||
// gtk_widget_set_size_request(frame1, 50, -1);
|
||||
gtk_container_add(GTK_CONTAINER(frame1), containers_view);
|
||||
|
||||
// gtk_paned_pack2(GTK_PANED(panes), frame2, true, FALSE);
|
||||
// gtk_widget_set_size_request(frame2, 50, -1);
|
||||
gtk_container_add(GTK_CONTAINER(frame2), contents_view);
|
||||
|
||||
gtk_paned_add1(panes, frame1);
|
||||
gtk_paned_add2(panes, frame2);
|
||||
gtk_paned_set_wide_handle(panes, true);
|
||||
}
|
||||
|
||||
// int box_spacing = 0;
|
||||
// GtkWidget* box_for_panes = gtk_box_new(GTK_ORIENTATION_HORIZONTAL, box_spacing);
|
||||
// gtk_box_pack_start(GTK_BOX(box_for_panes), panes, false, false, 0);
|
||||
// gtk_box_pack_start(GTK_BOX(box_for_panes), attributes_view, true, true, 0);
|
||||
|
||||
// // Scrolled window
|
||||
// GtkWidget* scrolled_window = gtk_scrolled_window_new(NULL, NULL);
|
||||
// gtk_container_add(GTK_CONTAINER(scrolled_window), box_for_panes);
|
||||
|
||||
// Window
|
||||
GtkWidget* window = gtk_window_new(GTK_WINDOW_TOPLEVEL);
|
||||
gtk_container_add(GTK_CONTAINER(window), panes);
|
||||
|
||||
gtk_window_set_title(GTK_WINDOW(window), "Adtool");
|
||||
|
||||
// Set starting window size
|
||||
gtk_window_set_default_size(GTK_WINDOW(window), 1700, 900);
|
||||
|
||||
// Set minimum window size
|
||||
gtk_widget_set_size_request(window, 1500, 900);
|
||||
|
||||
return window;
|
||||
}
|
@ -1,5 +0,0 @@
|
||||
#pragma once
|
||||
|
||||
#include <gtk/gtk.h>
|
||||
|
||||
GtkWidget* mainwindow_init();
|
19
src/menu_bar.c
Normal file
19
src/menu_bar.c
Normal file
@ -0,0 +1,19 @@
|
||||
|
||||
#include "menu_bar.h"
|
||||
#include "containers_view.h"
|
||||
#include "contents_view.h"
|
||||
|
||||
#include <gtk/gtk.h>
|
||||
|
||||
bool advanced_view = false;
|
||||
|
||||
bool advanced_view_is_on() {
|
||||
return advanced_view;
|
||||
}
|
||||
|
||||
void advanced_view_toggled_func(GtkWidget *widget, gpointer statusbar) {
|
||||
advanced_view = gtk_check_menu_item_get_active(GTK_CHECK_MENU_ITEM(widget));
|
||||
|
||||
containers_refilter();
|
||||
contents_refilter();
|
||||
}
|
@ -1,7 +1,5 @@
|
||||
#pragma once
|
||||
|
||||
#include <stdbool.h>
|
||||
#include <gtk/gtk.h>
|
||||
|
||||
GtkWidget* menubar_init();
|
||||
bool advanced_view_is_on();
|
@ -1,57 +0,0 @@
|
||||
|
||||
#include "menubar.h"
|
||||
|
||||
#include "containers_pane.h"
|
||||
|
||||
#include <gtk/gtk.h>
|
||||
|
||||
bool advanced_view = false;
|
||||
bool advanced_view_is_on() {
|
||||
return advanced_view;
|
||||
}
|
||||
|
||||
void File_item_New_func(GtkMenuItem *menuitem, gpointer data) {
|
||||
printf("New!\n");
|
||||
}
|
||||
|
||||
void toggle_advanced_view_func(GtkWidget *widget, gpointer statusbar) {
|
||||
if (gtk_check_menu_item_get_active(GTK_CHECK_MENU_ITEM(widget))) {
|
||||
advanced_view = true;
|
||||
} else {
|
||||
advanced_view = false;
|
||||
}
|
||||
|
||||
containers_refilter_model();
|
||||
}
|
||||
|
||||
// TODO: should do this layout in xml/glade
|
||||
GtkWidget* menubar_init() {
|
||||
GtkWidget* menubar = gtk_menu_bar_new();
|
||||
|
||||
// NOTE: this item/menu/item stuff is dumb
|
||||
// Create top level "File" menu item
|
||||
GtkWidget* File_item = gtk_menu_item_new_with_label("File");
|
||||
gtk_menu_shell_append(GTK_MENU_SHELL(menubar), File_item);
|
||||
// Add drop-down menu to "File" item
|
||||
GtkWidget* File_menu = gtk_menu_new();
|
||||
gtk_menu_item_set_submenu(GTK_MENU_ITEM(File_item), File_menu);
|
||||
|
||||
// New item
|
||||
GtkWidget* File_item_New = gtk_menu_item_new_with_label("New");
|
||||
g_signal_connect(G_OBJECT(File_item_New), "activate", G_CALLBACK(File_item_New_func), NULL);
|
||||
gtk_menu_shell_append(GTK_MENU_SHELL(File_menu), File_item_New);
|
||||
|
||||
// Advanced view toggle
|
||||
// TODO: menu is closed when this is toggled, which feels weird, find a way to keep it open
|
||||
GtkWidget* toggle_advanced_view = gtk_check_menu_item_new_with_label("Advanced view");
|
||||
gtk_check_menu_item_set_active(GTK_CHECK_MENU_ITEM(toggle_advanced_view), advanced_view);
|
||||
g_signal_connect(G_OBJECT(toggle_advanced_view), "activate", G_CALLBACK(toggle_advanced_view_func), NULL);
|
||||
gtk_menu_shell_append(GTK_MENU_SHELL(File_menu), toggle_advanced_view);
|
||||
|
||||
// Quit item
|
||||
GtkWidget* File_item_Quit = gtk_menu_item_new_with_label("Quit");
|
||||
g_signal_connect(G_OBJECT(File_item_Quit), "activate", G_CALLBACK(gtk_main_quit), NULL);
|
||||
gtk_menu_shell_append(GTK_MENU_SHELL(File_menu), File_item_Quit);
|
||||
|
||||
return menubar;
|
||||
}
|
Loading…
Reference in New Issue
Block a user