2 * Copyright 2006, 2011, Stephan Aßmus <superstippi@gmx.de>.
3 * Distributed under the terms of the MIT License.
7 #include "IconEditorApp.h"
15 #include <FilePanel.h>
16 #include <FindDirectory.h>
17 #include <IconEditorProtocol.h>
23 #include "support_settings.h"
25 #include "AutoLocker.h"
27 #include "MainWindow.h"
28 #include "SavePanel.h"
31 #undef B_TRANSLATION_CONTEXT
32 #define B_TRANSLATION_CONTEXT "Icon-O-Matic-Main"
37 static const char* kAppSig
= "application/x-vnd.haiku-icon_o_matic";
39 static const float kWindowOffset
= 20;
42 IconEditorApp::IconEditorApp()
44 BApplication(kAppSig
),
46 fLastWindowFrame(50, 50, 900, 750),
56 BMessenger
messenger(this, this);
57 BMessage
message(B_REFS_RECEIVED
);
58 fOpenPanel
= new BFilePanel(B_OPEN_PANEL
, &messenger
, NULL
, B_FILE_NODE
,
61 message
.what
= MSG_SAVE_AS
;
62 fSavePanel
= new SavePanel("save panel", &messenger
, NULL
, B_FILE_NODE
63 | B_DIRECTORY_NODE
| B_SYMLINK_NODE
, false, &message
);
69 IconEditorApp::~IconEditorApp()
80 IconEditorApp::QuitRequested()
82 // Run the QuitRequested() hook in each window's own thread. Otherwise
83 // the BAlert which a window shows when an icon is not saved will not
84 // repaint the window. (BAlerts check which thread is running Go() and
85 // will repaint windows when it's a BWindow.)
87 for (int32 i
= 0; BWindow
* window
= WindowAt(i
); i
++) {
90 // Try to cast the window while the pointer must be valid.
91 MainWindow
* mainWindow
= dynamic_cast<MainWindow
*>(window
);
93 if (mainWindow
== NULL
)
95 BMessenger
messenger(window
, window
);
97 if (messenger
.SendMessage(B_QUIT_REQUESTED
, &reply
) != B_OK
)
100 if (reply
.FindBool("result", &result
) == B_OK
&& !result
)
114 IconEditorApp::MessageReceived(BMessage
* message
)
116 switch (message
->what
) {
118 _NewWindow()->Show();
122 BMessage
openMessage(B_REFS_RECEIVED
);
124 if (message
->FindPointer("window", (void**)&window
) == B_OK
)
125 openMessage
.AddPointer("window", window
);
126 fOpenPanel
->SetMessage(&openMessage
);
133 if (message
->FindPointer("window", (void**)&window
) != B_OK
)
135 BMessage
openMessage(B_REFS_RECEIVED
);
136 openMessage
.AddBool("append", true);
137 openMessage
.AddPointer("window", window
);
138 fOpenPanel
->SetMessage(&openMessage
);
142 case B_EDIT_ICON_DATA
:
144 BMessenger messenger
;
145 if (message
->FindMessenger("reply to", &messenger
) < B_OK
) {
151 if (message
->FindData("icon data", B_VECTOR_ICON_TYPE
,
152 (const void**)&data
, &size
) < B_OK
) {
153 // optional (new icon will be created)
157 MainWindow
* window
= _NewWindow();
158 window
->Open(messenger
, data
, size
);
165 BMessenger messenger
;
166 if (message
->FindMessenger("target", &messenger
) != B_OK
)
169 fSavePanel
->SetExportMode(message
->what
== MSG_EXPORT_AS
);
170 // fSavePanel->Refresh();
171 const char* saveText
;
172 if (message
->FindString("save text", &saveText
) == B_OK
)
173 fSavePanel
->SetSaveText(saveText
);
174 fSavePanel
->SetTarget(messenger
);
179 case MSG_WINDOW_CLOSED
:
182 if (fWindowCount
== 0)
183 PostMessage(B_QUIT_REQUESTED
);
185 if (message
->FindMessage("settings", &settings
) == B_OK
)
186 fLastWindowSettings
= settings
;
188 if (message
->FindRect("window frame", &frame
) == B_OK
) {
189 fLastWindowFrame
= frame
;
190 fLastWindowFrame
.OffsetBy(-kWindowOffset
, -kWindowOffset
);
196 BApplication::MessageReceived(message
);
203 IconEditorApp::ReadyToRun()
205 // create main window
206 if (fWindowCount
== 0)
207 _NewWindow()->Show();
209 _InstallDocumentMimeType();
214 IconEditorApp::RefsReceived(BMessage
* message
)
217 if (message
->FindBool("append", &append
) != B_OK
)
220 if (message
->FindPointer("window", (void**)&window
) != B_OK
)
222 // When appending, we need to know a window.
223 if (append
&& window
== NULL
)
229 for (int32 i
= 0; message
->FindRef("refs", i
, &ref
) == B_OK
; i
++)
230 window
->Open(ref
, true);
233 for (int32 i
= 0; message
->FindRef("refs", i
, &ref
) == B_OK
; i
++) {
234 if (window
!= NULL
&& i
== 0) {
236 window
->Open(ref
, false);
239 window
= _NewWindow();
240 window
->Open(ref
, false);
246 if (fOpenPanel
!= NULL
&& fSavePanel
!= NULL
)
247 _SyncPanels(fOpenPanel
, fSavePanel
);
252 IconEditorApp::ArgvReceived(int32 argc
, char** argv
)
259 for (int32 i
= 1; i
< argc
; i
++) {
260 if (get_ref_for_path(argv
[i
], &ref
) == B_OK
) {
261 MainWindow
* window
= _NewWindow();
273 IconEditorApp::_NewWindow()
275 fLastWindowFrame
.OffsetBy(kWindowOffset
, kWindowOffset
);
276 MainWindow
* window
= new MainWindow(fLastWindowFrame
, this,
277 &fLastWindowSettings
);
284 IconEditorApp::_SyncPanels(BFilePanel
* from
, BFilePanel
* to
)
286 if (from
->Window()->Lock()) {
288 if (to
->Window()->Lock()) {
289 BRect frame
= from
->Window()->Frame();
290 to
->Window()->MoveTo(frame
.left
, frame
.top
);
291 to
->Window()->ResizeTo(frame
.Width(), frame
.Height());
292 to
->Window()->Unlock();
296 from
->GetPanelDirectory(&panelDir
);
297 to
->SetPanelDirectory(&panelDir
);
298 from
->Window()->Unlock();
304 IconEditorApp::_LastFilePath(path_kind which
)
306 const char* path
= NULL
;
310 if (fLastOpenPath
.Length() > 0)
311 path
= fLastOpenPath
.String();
312 else if (fLastSavePath
.Length() > 0)
313 path
= fLastSavePath
.String();
314 else if (fLastExportPath
.Length() > 0)
315 path
= fLastExportPath
.String();
318 if (fLastSavePath
.Length() > 0)
319 path
= fLastSavePath
.String();
320 else if (fLastExportPath
.Length() > 0)
321 path
= fLastExportPath
.String();
322 else if (fLastOpenPath
.Length() > 0)
323 path
= fLastOpenPath
.String();
325 case LAST_PATH_EXPORT
:
326 if (fLastExportPath
.Length() > 0)
327 path
= fLastExportPath
.String();
328 else if (fLastSavePath
.Length() > 0)
329 path
= fLastSavePath
.String();
330 else if (fLastOpenPath
.Length() > 0)
331 path
= fLastOpenPath
.String();
337 if (find_directory(B_USER_DIRECTORY
, &homePath
) == B_OK
)
338 path
= homePath
.Path();
351 IconEditorApp::_StoreSettings()
353 BMessage
settings('stns');
355 settings
.AddRect("window frame", fLastWindowFrame
);
356 settings
.AddMessage("window settings", &fLastWindowSettings
);
357 settings
.AddInt32("export mode", fSavePanel
->ExportMode());
359 save_settings(&settings
, "Icon-O-Matic");
364 IconEditorApp::_RestoreSettings()
366 BMessage
settings('stns');
367 load_settings(&settings
, "Icon-O-Matic");
370 if (settings
.FindRect("window frame", &frame
) == B_OK
) {
371 fLastWindowFrame
= frame
;
372 // Compensate offset for next window...
373 fLastWindowFrame
.OffsetBy(-kWindowOffset
, -kWindowOffset
);
375 BMessage lastSettings
;
376 if (settings
.FindMessage("window settings", &lastSettings
)
378 fLastWindowSettings
= lastSettings
;
382 if (settings
.FindInt32("export mode", &mode
) >= B_OK
)
383 fSavePanel
->SetExportMode(mode
);
388 IconEditorApp::_InstallDocumentMimeType()
390 // install mime type of documents
391 BMimeType
mime(kNativeIconMimeType
);
392 status_t ret
= mime
.InitCheck();
394 fprintf(stderr
, "Could not init native document mime type (%s): %s.\n",
395 kNativeIconMimeType
, strerror(ret
));
399 if (mime
.IsInstalled() && !(modifiers() & B_SHIFT_KEY
)) {
400 // mime is already installed, and the user is not
401 // pressing the shift key to force a re-install
405 ret
= mime
.Install();
407 fprintf(stderr
, "Could not install native document mime type (%s): "
408 "%s.\n", kNativeIconMimeType
, strerror(ret
));
412 ret
= mime
.SetPreferredApp(kAppSig
);
414 fprintf(stderr
, "Could not set native document preferred app: %s\n",
418 ret
= mime
.SetShortDescription("Haiku Icon");
420 fprintf(stderr
, "Could not set short description of mime type: %s\n",
422 ret
= mime
.SetLongDescription("Native Haiku vector icon");
424 fprintf(stderr
, "Could not set long description of mime type: %s\n",
428 BMessage
message('extn');
429 message
.AddString("extensions", "icon");
430 ret
= mime
.SetFileExtensions(&message
);
432 fprintf(stderr
, "Could not set extensions of mime type: %s\n",
436 const char* snifferRule
= "0.9 ('IMSG')";
437 ret
= mime
.SetSnifferRule(snifferRule
);
440 BMimeType::CheckSnifferRule(snifferRule
, &parseError
);
441 fprintf(stderr
, "Could not set sniffer rule of mime type: %s\n",
442 parseError
.String());