1 /* -*- Mode: C; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
2 /*
3  *  Copyright (C) 2007-2009  Kouhei Sutou <kou@clear-code.com>
4  *
5  *  This library is free software: you can redistribute it and/or modify
6  *  it under the terms of the GNU Lesser General Public License as published by
7  *  the Free Software Foundation, either version 3 of the License, or
8  *  (at your option) any later version.
9  *
10  *  This library is distributed in the hope that it will be useful,
11  *  but WITHOUT ANY WARRANTY; without even the implied warranty of
12  *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
13  *  GNU Lesser General Public License for more details.
14  *
15  *  You should have received a copy of the GNU Lesser General Public License
16  *  along with this program.  If not, see <http://www.gnu.org/licenses/>.
17  *
18  */
19 
20 #ifdef HAVE_CONFIG_H
21 #  include <config.h>
22 #endif /* HAVE_CONFIG_H */
23 
24 #include <glib.h>
25 #include <glib/gi18n-lib.h>
26 
27 #include "cut-utils.h"
28 #include "cut-ui-factory-builder.h"
29 #include "cut-module-factory.h"
30 #include "cut-module-factory-utils.h"
31 
32 static gchar *ui_name = NULL;
33 static CutUIFactoryBuilder *the_builder = NULL;
34 #ifdef G_OS_WIN32
35 static gchar *win32_ui_factory_module_dir = NULL;
36 #endif
37 
38 
39 static GObject *constructor  (GType                  type,
40                               guint                  n_props,
41                               GObjectConstructParam *props);
42 
43 static void         set_option_context (CutFactoryBuilder *builder,
44                                         GOptionContext    *context);
45 static GList       *build              (CutFactoryBuilder *builder);
46 static GList       *build_all          (CutFactoryBuilder *builder);
47 static const gchar *get_type_name      (CutFactoryBuilder *builder);
48 
G_DEFINE_TYPE(CutUIFactoryBuilder,cut_ui_factory_builder,CUT_TYPE_FACTORY_BUILDER)49 G_DEFINE_TYPE(CutUIFactoryBuilder, cut_ui_factory_builder, CUT_TYPE_FACTORY_BUILDER)
50 
51 static void
52 cut_ui_factory_builder_class_init (CutUIFactoryBuilderClass *klass)
53 {
54     GObjectClass *gobject_class;
55     CutFactoryBuilderClass *builder_class;
56 
57     gobject_class = G_OBJECT_CLASS(klass);
58     builder_class = CUT_FACTORY_BUILDER_CLASS(klass);
59 
60     gobject_class->constructor = constructor;
61 
62     builder_class->set_option_context = set_option_context;
63     builder_class->build              = build;
64     builder_class->build_all          = build_all;
65     builder_class->get_type_name      = get_type_name;
66 }
67 
68 static GObject *
constructor(GType type,guint n_props,GObjectConstructParam * props)69 constructor (GType type, guint n_props, GObjectConstructParam *props)
70 {
71     GObject *object;
72 
73     if (!the_builder) {
74         GObjectClass *klass;
75 
76         klass = G_OBJECT_CLASS(cut_ui_factory_builder_parent_class);
77         object = klass->constructor(type, n_props, props);
78         the_builder = CUT_UI_FACTORY_BUILDER(object);
79     } else {
80         object = g_object_ref(the_builder);
81     }
82 
83     return object;
84 }
85 
86 static void
cut_ui_factory_builder_init(CutUIFactoryBuilder * builder)87 cut_ui_factory_builder_init (CutUIFactoryBuilder *builder)
88 {
89     const gchar *dir;
90 
91     dir = g_getenv("CUT_UI_FACTORY_MODULE_DIR");
92     if (!dir) {
93 #ifdef G_OS_WIN32
94         if (!win32_ui_factory_module_dir)
95             win32_ui_factory_module_dir =
96                 cut_win32_build_factory_module_dir_name("ui");
97         dir = win32_ui_factory_module_dir;
98 #else
99         dir = UI_FACTORY_MODULE_DIR;
100 #endif
101     }
102 
103     g_object_set(G_OBJECT(builder),
104                  "module-dir", dir,
105                  NULL);
106 }
107 
108 static void
set_option_context(CutFactoryBuilder * builder,GOptionContext * context)109 set_option_context (CutFactoryBuilder *builder, GOptionContext *context)
110 {
111     static gchar *arg_description = NULL;
112     GOptionGroup *group;
113     GOptionEntry entries[] = {
114         {"ui", 'u', 0, G_OPTION_ARG_STRING, &ui_name,
115          N_("Specify UI"), NULL},
116         {NULL}
117     };
118 
119     if (!arg_description) {
120         GString *available_uis;
121         GList *names, *node;
122 
123         available_uis = g_string_new("[");
124         names = cut_module_factory_get_names("ui");
125         for (node = names; node; node = g_list_next(node)) {
126             const gchar *name = node->data;
127             g_string_append(available_uis, name);
128             if (g_list_next(node))
129                 g_string_append(available_uis, "|");
130         }
131         g_string_append(available_uis, "]");
132         arg_description = g_string_free(available_uis, FALSE);
133 
134         g_list_foreach(names, (GFunc)g_free, NULL);
135         g_list_free(names);
136     }
137     entries[0].arg_description = arg_description;
138 
139     group = g_option_group_new(("ui"),
140                                _("UI Options"),
141                                _("Show UI options"),
142                                builder, NULL);
143     g_option_group_add_entries(group, entries);
144     g_option_group_set_translation_domain(group, GETTEXT_PACKAGE);
145     g_option_context_add_group(context, group);
146 }
147 
148 static GList *
build(CutFactoryBuilder * builder)149 build (CutFactoryBuilder *builder)
150 {
151     GList *factories = NULL;
152     CutModuleFactory *module_factory;
153 
154     if (!ui_name)
155         ui_name = "console";
156 
157     if (cut_module_factory_exist_module("ui", ui_name)) {
158         GOptionContext *option_context;
159         module_factory = cut_module_factory_new("ui", ui_name, NULL);
160         g_object_get(builder,
161                      "option-context", &option_context,
162                      NULL);
163         cut_module_factory_set_option_group(module_factory,
164                                             option_context);
165         factories = g_list_prepend(factories, module_factory);
166     }
167 
168     return g_list_reverse(factories);
169 }
170 
171 static GList *
build_all(CutFactoryBuilder * builder)172 build_all (CutFactoryBuilder *builder)
173 {
174     GList *factories = NULL, *node;
175     GList *factory_names;
176 
177     factory_names = cut_module_factory_get_names("ui");
178 
179     for (node = factory_names; node; node = g_list_next(node)) {
180         CutModuleFactory *module_factory;
181         GOptionContext *option_context;
182         module_factory = cut_module_factory_new("ui", node->data, NULL);
183         g_object_get(builder,
184                      "option-context", &option_context,
185                      NULL);
186         cut_module_factory_set_option_group(module_factory,
187                                             option_context);
188         factories = g_list_prepend(factories, module_factory);
189     }
190 
191     g_list_foreach(factory_names, (GFunc)g_free, NULL);
192     g_list_free(factory_names);
193 
194     return g_list_reverse(factories);
195 }
196 
197 static const gchar *
get_type_name(CutFactoryBuilder * builder)198 get_type_name (CutFactoryBuilder *builder)
199 {
200     return "ui";
201 }
202 
203 /*
204 vi:ts=4:nowrap:ai:expandtab:sw=4
205 */
206