1/*
2 * filepanel.cpp - a command line tool to open a BFilePanel and get the result
3 * copyright 2003, Francois Revol, revol@free.fr
4 * LDFLAGS="-lbe -ltracker" make filepanel
5 * return:
6 * 0: the user has selected something,
7 * 1: the user canceled/closed the panel,
8 * 2: an error occured.
9 */
10
11//#define USE_FNMATCH
12
13#ifdef USE_FNMATCH
14#include <fnmatch.h>
15#endif
16#include <stdio.h>
17#include <stdlib.h>
18#include <strings.h>
19#include <Application.h>
20#include <Catalog.h>
21#include <Locale.h>
22#include <Messenger.h>
23#include <Window.h>
24#include <storage/Entry.h>
25#include <storage/FilePanel.h>
26#include <storage/Path.h>
27
28#define APP_SIG "application/x-vnd.mmu_man.filepanel"
29
30#undef B_TRANSLATION_CONTEXT
31#define B_TRANSLATION_CONTEXT "FilePanelApp"
32
33
34volatile int return_code = 0;
35
36class FilePanelApp : public BApplication
37{
38public:
39	FilePanelApp();
40
41	virtual void MessageReceived(BMessage *message);
42	virtual void RefsReceived(BMessage *message);
43};
44
45
46FilePanelApp::FilePanelApp()
47	:BApplication(APP_SIG)
48{
49}
50
51
52void
53FilePanelApp::MessageReceived(BMessage *message)
54{
55	entry_ref e;
56	const char *name;
57	BEntry entry;
58	BPath p;
59
60	//message->PrintToStream();
61	switch (message->what) {
62	case B_SAVE_REQUESTED:
63		message->FindRef("directory", &e);
64		message->FindString("name", &name);
65		entry.SetTo(&e);
66		entry.GetPath(&p);
67		printf("%s/%s\n", p.Path(), name);
68		be_app_messenger.SendMessage(B_QUIT_REQUESTED);
69		break;
70	case B_CANCEL:
71		return_code = 1;
72		be_app_messenger.SendMessage(B_QUIT_REQUESTED);
73		break;
74	default:
75		BApplication::MessageReceived(message);
76	}
77}
78
79
80void
81FilePanelApp::RefsReceived(BMessage *message)
82{
83	entry_ref e;
84	BEntry entry;
85	int i;
86	BPath p;
87//	message->PrintToStream();
88	for (i = 0; message->FindRef("refs", i, &e) == B_OK; i++) {
89		entry.SetTo(&e);
90		entry.GetPath(&p);
91		puts(p.Path());
92	}
93	be_app_messenger.SendMessage(B_QUIT_REQUESTED);
94}
95
96
97int
98usage(char *pname, int error)
99{
100	fprintf(stderr, B_TRANSLATE("display a load/save file panel\n"));
101	fprintf(stderr, B_TRANSLATE("usage: %s [--help] [--directory folder] "
102		"[--load|--save] [--title ttl] [--single] [--modal] [--allow pattern] "
103		"[--forbid pattern]\n"), pname);
104	fprintf(stderr, B_TRANSLATE("usage: %s [-h]     [-d folder]              "
105		"[-l|-s]     [-t ttl]      [-1]       [-m]      [-a pattern]      "
106		"[-f pattern]\n"), pname);
107	fprintf(stderr, B_TRANSLATE("options:\n"));
108	fprintf(stderr, B_TRANSLATE("short\tlong\tdescription\n"));
109	fprintf(stderr, B_TRANSLATE("-h\t--help\tdisplay usage\n"));
110	fprintf(stderr, B_TRANSLATE("-d\t--directory\topen at <folder>\n"));
111	fprintf(stderr, B_TRANSLATE("-l\t--load\tuse a load FilePanel "
112		"(default)\n"));
113	fprintf(stderr, B_TRANSLATE("-s\t--save\tuse a save FilePanel\n"));
114	fprintf(stderr, B_TRANSLATE("-n\t--name\tset the default name for "
115		"saving\n"));
116	fprintf(stderr, B_TRANSLATE("-k\t--kind\tkind of entries that can be "
117		"opened (flavour): any combination of f, d, s (file (default), "
118		"directory, symlink)\n"));
119	fprintf(stderr, B_TRANSLATE("-t\t--title\tset the FilePanel window "
120		"title\n"));
121	fprintf(stderr, B_TRANSLATE("-1\t--single\tallow only 1 file to be "
122		"selected\n"));
123	fprintf(stderr, B_TRANSLATE("-m\t--modal\tmakes the FilePanel modal\n"));
124#ifndef USE_FNMATCH
125	fprintf(stderr, B_TRANSLATE("-a\t--allow\tunimplemented\n"));
126	fprintf(stderr, B_TRANSLATE("-f\t--forbid\tunimplemented\n"));
127#else
128	fprintf(stderr, B_TRANSLATE("-a\t--allow\tunimplemented\n"));
129	fprintf(stderr, B_TRANSLATE("-f\t--forbid\tunimplemented\n"));
130#endif
131	return error;
132}
133
134
135int
136main(int argc, char **argv)
137{
138	int i;
139	file_panel_mode fpMode = B_OPEN_PANEL;
140	uint32 nodeFlavour = 0;
141	char *openAt = NULL;
142	char *windowTitle = NULL;
143	bool allowMultiSelect = true;
144	bool makeModal = false;
145	const char *defaultName = NULL;
146
147	for (i = 1; i < argc; i++) {
148		if (strncmp(argv[i], "--", 2) && ((*(argv[i]) == '-' &&
149			strlen(argv[i]) != 2) || *(argv[i]) != '-')) {
150			fprintf(stderr, B_TRANSLATE("%s not a valid option\n"), argv[i]);
151			return usage(argv[0], 2);
152		}
153		if (!strcmp(argv[i], "--help") || !strcmp(argv[i], "-h")) {
154			return usage(argv[0], 0);
155		} else if (!strcmp(argv[i], "--directory") || !strcmp(argv[i], "-d")) {
156			if (++i >= argc) {
157				fprintf(stderr, B_TRANSLATE("%s: this option requires a "
158					"parameter\n"), argv[i-1]);
159				return usage(argv[0], 2);
160			}
161			openAt = argv[i];
162		} else if (!strcmp(argv[i], "--load") || !strcmp(argv[i], "-l")) {
163			fpMode = B_OPEN_PANEL;
164		} else if (!strcmp(argv[i], "--save") || !strcmp(argv[i], "-s")) {
165			fpMode = B_SAVE_PANEL;
166		} else if (!strcmp(argv[i], "--name") || !strcmp(argv[i], "-n")) {
167			if (++i >= argc) {
168				fprintf(stderr, B_TRANSLATE("%s: this option requires a "
169					"parameter\n"), argv[i-1]);
170				return usage(argv[0], 2);
171			}
172			defaultName = (const char *)argv[i];
173		} else if (!strcmp(argv[i], "--kind") || !strcmp(argv[i], "-k")) {
174			if (++i >= argc) {
175				fprintf(stderr, B_TRANSLATE("%s: this option requires a "
176					"parameter\n"), argv[i-1]);
177				return usage(argv[0], 2);
178			}
179			if (strchr(argv[i], 'f')) nodeFlavour |= B_FILE_NODE;
180			if (strchr(argv[i], 'd')) nodeFlavour |= B_DIRECTORY_NODE;
181			if (strchr(argv[i], 's')) nodeFlavour |= B_SYMLINK_NODE;
182		} else if (!strcmp(argv[i], "--title") || !strcmp(argv[i], "-t")) {
183			if (++i >= argc) {
184				fprintf(stderr, B_TRANSLATE("%s: this option requires a "
185					"parameter\n"), argv[i-1]);
186				return usage(argv[0], 2);
187			}
188			windowTitle = argv[i];
189		} else if (!strcmp(argv[i], "--single") || !strcmp(argv[i], "-1")) {
190			allowMultiSelect = false;
191		} else if (!strcmp(argv[i], "--modal") || !strcmp(argv[i], "-m")) {
192			makeModal = true;
193		} else if (!strcmp(argv[i], "--allow") || !strcmp(argv[i], "-a")) {
194			if (++i >= argc) {
195				fprintf(stderr, B_TRANSLATE("%s: this option requires a "
196					"parameter\n"), argv[i-1]);
197				return usage(argv[0], 2);
198			}
199			fprintf(stderr, B_TRANSLATE("%s: UNIMPLEMENTED\n"), argv[i-1]);
200		} else if (!strcmp(argv[i], "--forbid") || !strcmp(argv[i], "-f")) {
201			if (++i >= argc) {
202				fprintf(stderr, B_TRANSLATE("%s: this option requires a "
203					"parameter\n"), argv[i-1]);
204				return usage(argv[0], 2);
205			}
206			fprintf(stderr, B_TRANSLATE("%s: UNIMPLEMENTED\n"), argv[i-1]);
207		} else {
208			fprintf(stderr, B_TRANSLATE("%s not a valid option\n"), argv[i]);
209			return usage(argv[0], 2);
210		}
211	}
212	new FilePanelApp;
213	entry_ref panelDir;
214// THIS LINE makes main() return always 0 no matter which value on return of
215// exit() ???
216	BFilePanel *fPanel = new BFilePanel(fpMode, NULL, NULL, nodeFlavour,
217		allowMultiSelect, NULL, NULL, makeModal);
218/**/
219	if (openAt)
220		fPanel->SetPanelDirectory(openAt);
221	if (windowTitle)
222		fPanel->Window()->SetTitle(windowTitle);
223	if (fpMode == B_SAVE_PANEL && defaultName)
224		fPanel->SetSaveText(defaultName);
225
226	fPanel->Show();
227/**/
228	be_app->Run();
229	delete be_app;
230//	printf("rc = %d\n", return_code);
231// WTF ??
232//return 2;
233//	exit(2);
234	exit(return_code);
235	return return_code;
236}
237
238