Check for SYS/GL during library init. Reason is that
[AROS.git] / workbench / devs / diskimage / ra_gui / main.c
blob5c7e974b6968c5bdd10e45eedf58a9ebb3be4e9d
1 /* Copyright 2007-2012 Fredrik Wikstrom. All rights reserved.
2 **
3 ** Redistribution and use in source and binary forms, with or without
4 ** modification, are permitted provided that the following conditions
5 ** are met:
6 **
7 ** 1. Redistributions of source code must retain the above copyright
8 ** notice, this list of conditions and the following disclaimer.
9 **
10 ** 2. Redistributions in binary form must reproduce the above copyright
11 ** notice, this list of conditions and the following disclaimer in the
12 ** documentation and/or other materials provided with the distribution.
14 ** THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS `AS IS'
15 ** AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16 ** IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
17 ** ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
18 ** LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
19 ** CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
20 ** SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
21 ** INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
22 ** CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
23 ** ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
24 ** POSSIBILITY OF SUCH DAMAGE.
27 #include "diskimagegui.h"
28 #include <dos/filehandler.h>
29 #include <proto/exec.h>
30 #include <proto/dos.h>
31 #include <proto/utility.h>
32 #include <proto/icon.h>
33 #include <proto/commodities.h>
34 #include <proto/intuition.h>
35 #include <proto/asl.h>
36 #include <proto/wb.h>
37 #include <proto/diskimage.h>
38 #include <proto/expat.h>
39 #include <proto/screennotify.h>
40 #include <clib/alib_protos.h>
41 #include <SDI_compiler.h>
42 #include <string.h>
43 #include "rev/DiskImageGUI_rev.h"
45 #define dbug(x) //Printf x
47 CONST TEXT USED verstag[] = VERSTAG;
48 struct Library *ButtonBase;
49 struct LocaleInfo LocaleInfo;
50 struct DiskObject *Icon;
51 struct Library *ScreenNotifyBase;
52 struct ClassLibrary *TBIBase;
53 struct ClassLibrary *PNGBase;
54 struct MsgPort *NotifyPort;
55 APTR NotifyHandle;
56 struct FileRequester *FileReq;
57 PrefsObject *ApplicationPrefs;
59 struct SignalTaskHook {
60 struct Hook hook;
61 struct Task *task;
62 ULONG sigmask;
65 static ULONG SignalTaskFunc (REG(a0, struct SignalTaskHook *hook),
66 REG(a2, APTR unused1), REG(a1, APTR unused2));
68 int main (int argc, STRPTR *argv) {
69 int rc = RETURN_FAIL;
70 BYTE DiskChangeSignal = -1;
71 struct SignalTaskHook *DiskChangeHook = NULL;
72 BYTE ReloadPluginsSignal = -1;
73 struct SignalTaskHook *ReloadPluginsHook = NULL;
74 struct MsgPort *WBMenuItemPort = NULL;
75 struct AppMenuItem *WBMenuItem = NULL;
76 ULONG sigs;
78 ButtonBase = OpenLibrary("gadgets/button.gadget", 0);
79 if (!ButtonBase) {
80 goto error;
83 InitLocaleInfo(SysBase, &LocaleInfo, PROGNAME".catalog");
85 Icon = GetProgramIcon();
86 if (!Icon) {
87 goto error;
90 dbug(("RegisterCxBroker\n"));
91 if (!RegisterCxBroker()) {
92 goto error;
95 ScreenNotifyBase = OpenLibrary(SCREENNOTIFY_NAME, SCREENNOTIFY_VERSION);
96 TBIBase = (struct ClassLibrary *)OpenLibrary("images/titlebar.image", 0);
97 PNGBase = (struct ClassLibrary *)OpenLibrary("images/png.image", 0);
99 if (ScreenNotifyBase) {
100 NotifyPort = CreateMsgPort();
101 if (!NotifyPort) {
102 goto error;
104 dbug(("NotifyPort: 0x%08lX\n", NotifyPort));
107 dbug(("BeginScreenNotify\n"));
108 BeginScreenNotify();
110 dbug(("AllocAslRequestTags\n"));
111 FileReq = AllocAslRequestTags(ASL_FileRequest,
112 ASLFR_InitialDrawer, TTString(Icon, "FILEDIR", ""),
113 ASLFR_DoSaveMode, FALSE,
114 ASLFR_DoPatterns, TRUE,
115 ASLFR_InitialPattern, TTString(Icon, "PATTERN", "#?"),
116 TAG_END);
117 if (!FileReq) {
118 goto error;
121 ApplicationPrefs = AllocPrefsDictionary();
122 if (!ApplicationPrefs) {
123 goto error;
125 if (!ReadPrefs(ApplicationPrefs, "ENV:"PROGNAME".a500.org.xml")) {
126 ReadPrefs(ApplicationPrefs, "ENVARC:"PROGNAME".a500.org.xml");
129 dbug(("InitExtWindowClass\n"));
130 if (!InitExtWindowClass()) {
131 goto error;
133 dbug(("InitExtScrollerClass\n"));
134 if (!InitExtScrollerClass()) {
135 goto error;
138 dbug(("OpenDiskImageDevice\n"));
139 if (!OpenDiskImageDevice(~0)) {
140 goto error;
143 DiskChangeSignal = AllocSignal(-1);
144 if (DiskChangeSignal == -1) {
145 goto error;
147 DiskChangeHook = CreateExtHook(sizeof(struct SignalTaskHook), SignalTaskFunc, NULL);
148 if (!DiskChangeHook) {
149 goto error;
151 DiskChangeHook->task = FindTask(NULL);
152 DiskChangeHook->sigmask = 1UL << DiskChangeSignal;
153 dbug(("AddDiskChangeHook\n"));
154 AddDiskChangeHook(&DiskChangeHook->hook, TRUE);
156 if (CheckLib(DiskImageBase, 52, 22)) {
157 ReloadPluginsSignal = AllocSignal(-1);
158 if (ReloadPluginsSignal == -1) {
159 goto error;
161 ReloadPluginsHook = CreateExtHook(sizeof(struct SignalTaskHook), SignalTaskFunc, NULL);
162 if (!DiskChangeHook) {
163 goto error;
165 ReloadPluginsHook->task = FindTask(NULL);
166 ReloadPluginsHook->sigmask = 1UL << ReloadPluginsSignal;
167 dbug(("AddReloadPluginsHook\n"));
168 AddReloadPluginsHook(&ReloadPluginsHook->hook, TRUE);
171 if (TTBoolean(Icon, "WBMENUITEM")) {
172 WBMenuItemPort = CreateMsgPort();
173 if (!WBMenuItemPort) {
174 goto error;
176 dbug(("AddAppMenuItemA\n"));
177 WBMenuItem = AddAppMenuItemA(0, 0, PROGNAME, WBMenuItemPort, NULL);
178 if (!WBMenuItem) {
179 goto error;
183 if (TTBoolean(Icon, "CX_POPUP")) {
184 dbug(("ShowWindow(WID_MAIN)\n"));
185 if (!ShowWindow(WID_MAIN)) {
186 goto error;
190 rc = RETURN_OK;
192 dbug(("Entering main loop\n"));
193 while (TRUE) {
194 sigs = GetGUISignals();
195 if (NotifyPort) sigs |= (1UL << NotifyPort->mp_SigBit);
196 sigs |= (1UL << DiskChangeSignal);
197 sigs |= (1UL << ReloadPluginsSignal);
198 sigs |= (1UL << BrokerPort->mp_SigBit);
199 if (WBMenuItemPort) sigs |= (1UL << WBMenuItemPort->mp_SigBit);
200 sigs = Wait(sigs|SIGBREAKF_CTRL_C);
202 if (sigs & SIGBREAKF_CTRL_C) {
203 break;
206 if (NotifyPort && (sigs & (1UL << NotifyPort->mp_SigBit))) {
207 struct ScreenNotifyMessage *msg;
208 while (msg = (struct ScreenNotifyMessage *)GetMsg(NotifyPort)) {
209 dbug(("snm_Type: 0x%08lX\n", msg->snm_Type));
210 dbug(("snm_Value: 0x%08lX\n", msg->snm_Value));
211 if (msg->snm_Type == SCREENNOTIFY_TYPE_WORKBENCH) {
212 if (msg->snm_Value == FALSE) {
213 CleanupGUI();
216 ReplyMsg((struct Message *)msg);
220 if (sigs & (1UL << DiskChangeSignal)) {
221 ScanUnits();
224 if (sigs & (1UL << ReloadPluginsSignal)) {
225 ScanPlugins();
228 if (sigs & (1UL << BrokerPort->mp_SigBit)) {
229 CxMsg *msg;
230 BOOL quit = FALSE;
231 while (msg = (CxMsg *)GetMsg(BrokerPort)) {
232 switch (CxMsgType(msg)) {
233 case CXM_IEVENT:
234 switch (CxMsgID(msg)) {
235 case EVT_POPKEY:
236 ShowWindow(WID_MAIN);
237 break;
239 break;
240 case CXM_COMMAND:
241 switch (CxMsgID(msg)) {
242 case CXCMD_DISABLE:
243 ActivateCxObj(Broker, FALSE);
244 break;
245 case CXCMD_ENABLE:
246 ActivateCxObj(Broker, TRUE);
247 break;
248 case CXCMD_APPEAR:
249 case CXCMD_UNIQUE:
250 ShowWindow(WID_MAIN);
251 break;
252 case CXCMD_DISAPPEAR:
253 HideWindow(WID_MAIN);
254 break;
255 case CXCMD_KILL:
256 quit = TRUE;
257 break;
259 break;
261 ReplyMsg((struct Message *)msg);
263 if (quit) {
264 break;
268 if (WBMenuItemPort && (sigs & (1UL << WBMenuItemPort->mp_SigBit))) {
269 struct AppMessage *msg;
270 while (msg = (struct AppMessage *)GetMsg(WBMenuItemPort)) {
271 if (msg->am_Type == AMTYPE_APPMENUITEM && msg->am_Class == 0) {
272 ShowWindow(WID_MAIN);
274 ReplyMsg((struct Message *)msg);
278 if (Gui.windows[WID_MAIN]) {
279 ULONG res, event;
280 UWORD code;
281 struct Menu *menu;
282 struct MenuItem *item;
283 ULONG mid;
284 BOOL quit = FALSE;
285 while ((res = RA_HandleInput(Gui.windows[WID_MAIN], &code)) != WMHI_LASTMSG) {
286 switch (res & WMHI_CLASSMASK) {
287 case WMHI_CLOSEWINDOW:
288 HideWindow(WID_MAIN);
289 break;
290 case WMHI_ICONIFY:
291 IconifyWindow(WID_MAIN);
292 break;
293 case WMHI_UNICONIFY:
294 ShowWindow(WID_MAIN);
295 break;
296 case WMHI_SNAPSHOT:
297 SaveWindowSize(Gui.windows[WID_MAIN], "main_window", TRUE);
298 break;
299 case WMHI_NEWSIZE:
300 UpdateLBVertScroller(WID_MAIN, GID_DRIVELIST, GID_DRIVELISTVPROP);
301 break;
302 case WMHI_GADGETUP:
303 switch (res & WMHI_GADGETMASK) {
304 case GID_SPEEDBAR:
305 switch (code) {
306 case SBID_INSERT:
307 InsertDisk();
308 break;
309 case SBID_EJECT:
310 EjectDisk();
311 break;
312 case SBID_WRITEPROTECT:
313 ToggleWriteProtect();
314 break;
315 case SBID_SETDEVICETYPE:
316 SetDeviceType();
317 break;
318 case SBID_REFRESH:
319 ScanUnits();
320 break;
322 break;
323 case GID_DRIVELIST:
324 GetAttr(LISTBROWSER_RelEvent, Gui.gadgets[GID_DRIVELIST], &event);
325 switch (event) {
326 case LBRE_NORMAL:
327 UpdateSpeedBar();
328 break;
329 case LBRE_DOUBLECLICK:
330 InsertOrEjectDisk();
331 break;
333 break;
335 break;
336 case WMHI_MENUPICK:
337 menu = Gui.menustrip;
338 while (menu && (item = ItemAddress(menu, code))) {
339 mid = (ULONG)GTMENUITEM_USERDATA(item);
340 code = item->NextSelect;
341 switch (mid) {
342 case MID_QUIT:
343 quit = TRUE;
344 break;
345 case MID_HIDE:
346 HideWindow(WID_MAIN);
347 menu = NULL;
348 break;
349 case MID_ICONIFY:
350 IconifyWindow(WID_MAIN);
351 menu = NULL;
352 break;
353 case MID_SNAPSHOT:
354 SaveWindowSize(Gui.windows[WID_MAIN], "main_window", TRUE);
355 break;
356 case MID_ABOUT:
357 AboutRequester();
358 break;
359 case MID_CHANGETEMPDIR:
360 ChangeTempDir();
361 break;
362 case MID_PLUGINS:
363 ShowWindow(WID_PLUGINS);
364 break;
365 case MID_SAVESETTINGS:
366 SaveSettings();
367 break;
370 break;
373 if (quit) {
374 break;
378 if (Gui.windows[WID_PLUGINS]) {
379 ULONG res, event;
380 UWORD code;
381 while ((res = RA_HandleInput(Gui.windows[WID_PLUGINS], &code)) != WMHI_LASTMSG) {
382 switch (res & WMHI_CLASSMASK) {
383 case WMHI_CLOSEWINDOW:
384 HideWindow(WID_PLUGINS);
385 break;
386 case WMHI_ICONIFY:
387 IconifyWindow(WID_PLUGINS);
388 break;
389 case WMHI_UNICONIFY:
390 ShowWindow(WID_PLUGINS);
391 break;
392 case WMHI_SNAPSHOT:
393 SaveWindowSize(Gui.windows[WID_PLUGINS], "plugins_window", TRUE);
394 break;
395 case WMHI_NEWSIZE:
396 UpdateLBVertScroller(WID_PLUGINS, GID_PLUGINLIST, GID_PLUGINLISTVPROP);
397 break;
403 error:
404 dbug(("Exiting\n"));
405 CleanupGUI();
406 if (WBMenuItemPort) {
407 if (WBMenuItem) {
408 struct Message *msg;
409 RemoveAppMenuItem(WBMenuItem);
410 while (msg = GetMsg(WBMenuItemPort)) ReplyMsg(msg);
412 DeleteMsgPort(WBMenuItemPort);
414 if (ReloadPluginsHook) {
415 AddReloadPluginsHook(&ReloadPluginsHook->hook, FALSE);
416 FreeExtHook(ReloadPluginsHook);
418 FreeSignal(ReloadPluginsSignal);
419 if (DiskChangeHook) {
420 AddDiskChangeHook(&DiskChangeHook->hook, FALSE);
421 FreeExtHook(DiskChangeHook);
423 FreeSignal(DiskChangeSignal);
424 CloseDiskImageDevice();
425 FreeClass(ExtScrollerClass);
426 FreeClass(ExtWindowClass);
427 FreePrefsObject(ApplicationPrefs);
428 FreeAslRequest(FileReq);
429 StopScreenNotify();
430 DeleteMsgPort(NotifyPort);
431 if (PNGBase) CloseLibrary((struct Library *)PNGBase);
432 if (TBIBase) CloseLibrary((struct Library *)TBIBase);
433 if (ScreenNotifyBase) CloseLibrary(ScreenNotifyBase);
434 UnregisterCxBroker();
435 FreeDiskObject(Icon);
436 FreeLocaleInfo(SysBase, &LocaleInfo);
437 if (ButtonBase) CloseLibrary(ButtonBase);
439 return rc;
442 static ULONG SignalTaskFunc (REG(a0, struct SignalTaskHook *hook),
443 REG(a2, APTR unused1), REG(a1, APTR unused2))
445 Signal(hook->task, hook->sigmask);
446 return 0;
449 static ULONG screen_notify_stop_count = 1;
451 struct DiskObject *GetProgramIcon (void) {
452 struct DiskObject *icon;
453 dbug(("GetProgramIcon\n"));
454 icon = GetDiskObjectNew("PROGDIR:"PROGNAME);
455 if (icon) {
456 icon->do_CurrentX = NO_ICON_POSITION;
457 icon->do_CurrentY = NO_ICON_POSITION;
459 dbug(("Icon: 0x%08lX\n", icon));
460 return icon;
463 void BeginScreenNotify (void) {
464 if (ScreenNotifyBase) {
465 if (NotifyHandle) {
466 return;
468 if (screen_notify_stop_count > 0) {
469 screen_notify_stop_count--;
471 if (screen_notify_stop_count == 0) {
472 NotifyHandle = AddWorkbenchClient(NotifyPort, 0);
473 dbug(("NotifyHandle: 0x%08lX\n", NotifyHandle));
478 void StopScreenNotify (void) {
479 if (ScreenNotifyBase) {
480 if (NotifyHandle) {
481 while (!RemWorkbenchClient(NotifyHandle)) Delay(10);
482 NotifyHandle = NULL;
484 screen_notify_stop_count++;
488 LONG GetUnitNumber (struct Node *node) {
489 LONG *unit_num = NULL;
490 GetListBrowserNodeAttrs(node,
491 LBNA_Column, DRIVE_COL_UNIT,
492 LBNCA_Integer, &unit_num,
493 TAG_END);
494 if (unit_num) {
495 return *unit_num;
497 return -1;
500 LONG GetSelectedUnit (void) {
501 struct Node *node = NULL;
502 GetAttr(LISTBROWSER_SelectedNode, Gui.gadgets[GID_DRIVELIST], (Tag *)&node);
503 return GetUnitNumber(node);
506 CONST_STRPTR GetSelectedPlugin (void) {
507 LONG i;
508 struct Node *node;
509 CONST_STRPTR name;
511 i = -1;
512 GetAttr(CHOOSER_Selected, Gui.gadgets[GID_PLUGINCHOOSER], (Tag *)&i);
513 if (i <= 0) return NULL;
515 node = GetHead(Gui.lists[LID_PLUGINCHOOSER]);
516 while (node && i--) node = GetSucc(node);
518 name = NULL;
519 if (node) {
520 GetChooserNodeAttrs(node, CNA_Text, &name, TAG_END);
522 return name;
525 static TEXT drive_buffer[1024];
526 static STRPTR drive_buffer_ptr;
528 void AddDriveNode (struct List *list, struct Node *n1) {
529 struct Node *n2;
530 LONG u1, u2;
531 u1 = GetUnitNumber(n1);
532 n2 = list->lh_TailPred;
533 while (n2->ln_Pred) {
534 u2 = GetUnitNumber(n2);
535 if (u1 >= u2) {
536 Insert(list, n1, n2);
537 return;
539 n2 = n2->ln_Pred;
541 AddHead(list, n1);
544 void ScanUnits (void) {
545 struct Window *window;
546 Object *listbrowser;
547 struct List *list;
548 struct Node *selected_node;
549 LONG selected_unit;
550 ULONG sort_column;
551 const ULONG dosflags = LDF_DEVICES|LDF_READ;
552 struct DosList *dl;
553 TEXT devicename[64];
554 STRPTR device;
555 struct FileSysStartupMsg *fssm;
556 BOOL free_fssm = FALSE;
557 struct Node *node;
558 LONG unit_num;
560 if (!Gui.initialised) {
561 return;
564 window = NULL;
565 GetAttr(WINDOW_Window, Gui.windows[WID_MAIN], (Tag *)&window);
566 listbrowser = Gui.gadgets[GID_DRIVELIST];
567 list = Gui.lists[LID_DRIVELIST];
569 selected_node = NULL;
570 GetAttrs(listbrowser,
571 LISTBROWSER_SelectedNode, &selected_node,
572 TAG_END);
573 selected_unit = GetUnitNumber(selected_node);
575 SetAttrs(listbrowser,
576 LISTBROWSER_Labels, ~0,
577 TAG_END);
578 FreeListBrowserList(list);
580 drive_buffer_ptr = drive_buffer;
581 selected_node = NULL;
582 dl = LockDosList(dosflags);
583 while (dl = NextDosEntry(dl, dosflags)) {
584 if (!dl->dol_Task || !CheckBPTR(dl->dol_Name)) {
585 continue;
587 fssm = (struct FileSysStartupMsg *)DoPkt0(dl->dol_Task, ACTION_GET_DISK_FSSM);
588 if (fssm) {
589 free_fssm = TRUE;
590 } else {
591 free_fssm = FALSE;
592 if (IoErr() == ERROR_ACTION_NOT_KNOWN) {
593 fssm = CheckBPTR(dl->dol_misc.dol_handler.dol_Startup);
596 if (fssm && CheckBPTR(fssm->fssm_Device)) {
597 CopyStringBSTRToC(fssm->fssm_Device, devicename, sizeof(devicename));
598 if (!strcmp(FilePart(devicename), "diskimage.device")) {
599 LONG *unit_ptr;
600 unit_ptr = (LONG *)drive_buffer_ptr;
601 *unit_ptr = fssm->fssm_Unit;
602 drive_buffer_ptr += sizeof(*unit_ptr);
603 CopyStringBSTRToC(dl->dol_Name, devicename, sizeof(devicename));
604 node = AllocListBrowserNode(DRIVE_COL_MAX,
605 LBNA_Column, DRIVE_COL_ICON,
606 LBNCA_Image, Gui.images[IID_LIST_DISK],
607 LBNA_Column, DRIVE_COL_UNIT,
608 LBNCA_HorizJustify, LCJ_RIGHT,
609 LBNCA_Integer, unit_ptr,
610 LBNA_Column, DRIVE_COL_DEVICE,
611 LBNCA_CopyText, TRUE,
612 LBNCA_Text, devicename,
613 LBNA_Column, DRIVE_COL_DISKIMAGE,
614 LBNCA_Text, GetString(&LocaleInfo, MSG_NO_DISK),
615 TAG_END);
616 if (node) {
617 AddDriveNode(list, node);
618 if (fssm->fssm_Unit == selected_unit) {
619 selected_node = node;
624 if (free_fssm && fssm) {
625 DoPkt1(dl->dol_Task, ACTION_FREE_DISK_FSSM, (LONG)fssm);
628 UnLockDosList(dosflags);
630 node = GetHead(list);
631 while (node) {
632 unit_num = GetUnitNumber(node);
633 if (unit_num != -1) {
634 UBYTE device_type = DG_DIRECT_ACCESS;
635 ULONG device_icon = IID_LIST_DISK;
636 STRPTR filename = NULL;
637 BOOL writeprotect = FALSE;
639 UnitControl(unit_num,
640 DITAG_GetDeviceType, &device_type,
641 DITAG_GetWriteProtect, &writeprotect,
642 DITAG_GetImageName, &filename,
643 TAG_END);
645 if (device_type == DG_CDROM) {
646 device_icon = IID_LIST_CDROM;
649 SetListBrowserNodeAttrs(node,
650 LBNA_Column, DRIVE_COL_ICON,
651 LBNCA_Image, Gui.images[device_icon],
652 LBNA_Column, DRIVE_COL_WP,
653 LBNCA_Image, writeprotect ? Gui.images[IID_LIST_WRITEPROTECTED] : NULL,
654 TAG_END);
655 if (filename) {
656 SetListBrowserNodeAttrs(node,
657 LBNA_Column, DRIVE_COL_DISKIMAGE,
658 LBNCA_CopyText, TRUE,
659 LBNCA_Text, filename,
660 TAG_END);
662 FreeVec(filename);
664 node = GetSucc(node);
667 SetGadgetAttrs(GA(listbrowser), window, NULL,
668 LISTBROWSER_Labels, list,
669 LISTBROWSER_SelectedNode, selected_node,
670 TAG_END);
672 UpdateSpeedBar();
675 static TEXT plugin_buffer[1024];
676 static STRPTR plugin_buffer_ptr;
678 static ULONG ChooserPluginHookFunc (REG(a0, struct Hook *hook),
679 REG(a2, struct DiskImagePlugin *plugin),
680 REG(a1, struct List *list))
682 struct Node *node;
683 STRPTR name;
684 if (!(plugin->Flags & PLUGIN_FLAG_USERCHOICE)) {
685 return 0;
687 strcpy(name = plugin_buffer_ptr, plugin->Node.ln_Name);
688 plugin_buffer_ptr += strlen(name) + 1;
689 node = AllocChooserNode(
690 CNA_Text, name,
691 TAG_END);
692 if (node) {
693 AddTail(list, node);
695 return 0;
698 static ULONG ListBrowserPluginHookFunc (REG(a0, struct Hook *hook),
699 REG(a2, struct DiskImagePlugin *plugin),
700 REG(a1, struct List *list))
702 TEXT buffer[40];
703 CONST_STRPTR name;
704 LONG *pri_ptr;
705 struct Node *node;
706 name = plugin->Node.ln_Name;
707 pri_ptr = (LONG *)plugin_buffer_ptr;
708 *pri_ptr = plugin->Node.ln_Pri;
709 plugin_buffer_ptr += sizeof(*pri_ptr);
710 if (plugin->Flags & PLUGIN_FLAG_BUILTIN) {
711 SNPrintf(buffer, sizeof(buffer), "%s (internal)", name);
712 name = buffer;
714 node = AllocListBrowserNode(PLUG_COL_MAX,
715 LBNA_Column, PLUG_COL_ICON,
716 LBNCA_Image, Gui.images[IID_LIST_PLUGIN],
717 LBNA_Column, PLUG_COL_PRI,
718 LBNCA_HorizJustify, LCJ_RIGHT,
719 LBNCA_Integer, pri_ptr,
720 LBNA_Column, PLUG_COL_WRITE,
721 LBNCA_HorizJustify, LCJ_CENTER,
722 LBNCA_Image, plugin->plugin_Write ? Gui.images[IID_LIST_CHECKMARK] : NULL,
723 LBNA_Column, PLUG_COL_NAME,
724 LBNCA_CopyText, TRUE,
725 LBNCA_Text, name,
726 TAG_END);
727 if (node) {
728 AddTail(list, node);
730 return 0;
733 void ScanPlugins (void) {
734 struct Hook *hook;
735 struct Window *main_window = NULL;
736 struct Window *plugin_window = NULL;
737 Object *chooser;
738 Object *listbrowser;
739 struct List *ch_list, *lb_list;
740 struct Node *node, *succ;
742 if (!Gui.initialised) {
743 return;
746 hook = CreateHook(NULL, NULL);
747 if (!hook) {
748 return;
751 GetAttr(WINDOW_Window, Gui.windows[WID_MAIN], (Tag *)&main_window);
752 GetAttr(WINDOW_Window, Gui.windows[WID_PLUGINS], (Tag *)&plugin_window);
753 chooser = Gui.gadgets[GID_PLUGINCHOOSER];
754 listbrowser = Gui.gadgets[GID_PLUGINLIST];
755 ch_list = Gui.lists[LID_PLUGINCHOOSER];
756 lb_list = Gui.lists[LID_PLUGINLIST];
758 SetAttrs(chooser,
759 CHOOSER_Labels, ~0,
760 TAG_END);
761 SetAttrs(listbrowser,
762 LISTBROWSER_Labels, ~0,
763 TAG_END);
764 node = GetSucc(GetHead(ch_list));
765 while (node) {
766 succ = GetSucc(node);
767 Remove(node);
768 FreeChooserNode(node);
769 node = succ;
771 FreeListBrowserList(lb_list);
773 plugin_buffer_ptr = plugin_buffer;
774 hook->h_Entry = ChooserPluginHookFunc;
775 hook->h_Data = ch_list;
776 DoHookPlugins(hook);
777 hook->h_Entry = ListBrowserPluginHookFunc;
778 hook->h_Data = lb_list;
779 DoHookPlugins(hook);
781 SetGadgetAttrs(GA(chooser), main_window, NULL,
782 CHOOSER_Labels, ch_list,
783 CHOOSER_Selected, 0,
784 TAG_END);
785 SetGadgetAttrs(GA(listbrowser), plugin_window, NULL,
786 LISTBROWSER_Labels, lb_list,
787 LISTBROWSER_SelectedNode, NULL,
788 TAG_END);
790 FreeHook(hook);
793 void UpdateSpeedBar (void) {
794 struct Window *window;
795 LONG selected_unit;
796 struct Node *node;
797 ULONG disk_type;
799 if (!Gui.initialised) {
800 return;
803 window = NULL;
804 GetAttr(WINDOW_Window, Gui.windows[WID_MAIN], (Tag *)&window);
806 disk_type = DITYPE_NONE;
807 selected_unit = GetSelectedUnit();
808 if (selected_unit != -1) {
809 if (UnitControl(selected_unit,
810 DITAG_DiskImageType, &disk_type,
811 TAG_END))
813 selected_unit = -1;
817 SetAttrs(Gui.gadgets[GID_SPEEDBAR],
818 SPEEDBAR_Buttons, ~0,
819 TAG_END);
821 node = Gui.lists[LID_SPEEDBAR]->lh_Head;
822 while (node->ln_Succ) {
823 switch (node->ln_Pri) {
824 case SBID_INSERT:
825 case SBID_WRITEPROTECT:
826 case SBID_SETDEVICETYPE:
827 SetSpeedButtonNodeAttrs(node,
828 SBNA_Disabled, selected_unit == -1,
829 TAG_END);
830 break;
831 case SBID_EJECT:
832 SetSpeedButtonNodeAttrs(node,
833 SBNA_Disabled, disk_type == DITYPE_NONE,
834 TAG_END);
835 break;
837 node = node->ln_Succ;
840 SetGadgetAttrs(GA(Gui.gadgets[GID_SPEEDBAR]), window, NULL,
841 SPEEDBAR_Buttons, Gui.lists[LID_SPEEDBAR],
842 TAG_END);
845 void ChangeTempDir (void) {
846 struct Window *window;
847 STRPTR tmpdir;
848 struct FileRequester *freq;
850 window = NULL;
851 GetAttr(WINDOW_Window, Gui.windows[WID_MAIN], (Tag *)&window);
853 tmpdir = GetEnvVar(TEMPDIR_VAR);
854 freq = AllocAslRequestTags(ASL_FileRequest,
855 ASLFR_InitialDrawer, tmpdir ? tmpdir : "T:",
856 ASLFR_DoSaveMode, FALSE,
857 ASLFR_DrawersOnly, TRUE,
858 TAG_END);
859 if (freq) {
860 StopScreenNotify();
861 SetWindowBusy(~0, TRUE);
863 if (AslRequestTags(freq,
864 ASLFR_Screen, Gui.screen,
865 TAG_END))
867 SetEnvVar(TEMPDIR_VAR, freq->fr_Drawer, FALSE);
870 SetWindowBusy(~0, FALSE);
871 BeginScreenNotify();
873 FreeAslRequest(freq);
875 FreeVec(tmpdir);
878 void SaveSettings (void) {
879 STRPTR tmpdir;
880 tmpdir = GetEnvVar(TEMPDIR_VAR);
881 SetEnvVar(TEMPDIR_VAR, tmpdir, TRUE);
882 FreeVec(tmpdir);