home *** CD-ROM | disk | FTP | other *** search
Wrap
/* Super-Hotlist Directory Opus 5.5 by Leo 'Nudel' Davidson for Gods'Gift Utilities email: leo.davidson@keble.oxford.ac.uk www: http://users.ox.ac.uk/~kebl0364 $VER: Hotlist.dopus5 1.7 (7.7.96) Huge thanks to Jonathan Potter for adding the commands to Opus which were required to do this properly. Thanks to Edmund Vermeulen who always seems to have a better way of writting something in ARexx and whose ArcDir script proved a good source of source. ------------------------------------------------------------------------------- This ARexx module adds a "Hotlist" command to Opus which behaves just like the internal "Devicelist" command (including the "NEW" switch). To install just put this file (Hotlist.dopus5) in your DOpus5:modules/ directory. The Hotlist command will then be added (you don't even have to reboot!). Then just put it on a button or your double-click script instead of DeviceList, ScanDir, or whatever you have at the moment to open new listers! -- You might want to add it to your lister toolbar, too. Maybe I'll convert this to 'C' once I've learnt it, it'd speed things up quite a bit. (I'm certainly not writting /this/ in assembler!) Arguments: (*** ORDER IS IMPORTANT! ***) NEW/S Force a new hotlist to be openned even if there is a source lister available. CONFIG/K Specify a hotlist file to use if you don't want to use the default (DOpus5:System/hotlist.config). You can use this to have different hotlists on different buttons. e.g. "Hotlist NEW Ram Disk:NewHotListFile" (Note that quotes should not be put around the config name even if it does contain a space). If you just use "Hotlist" it'll behave pretty much like the internal DOpus DeviceList command. Usage (Adding entries): The first time you run the hotlist will be empty: just drag'n'drop directories to the hotlist to have them added! You'll be asked what name you want to give the entry (if you want it different to the path's name), and what colour you want it in the list. (Sorry, you can't control what order things are in at this time). You can also click your normal "MakeDir" lister toolbar icon to create a new entry just by typing its path in. If you add a file to the list (instead of a directory or device), double-clicking the file will perform whatever the doubleclick action is for that filetype. You can use this to put your favourate programs, pictures, or whatever in a hotlist. Usage (Jumping to entries): To jump to an entry in the hotlist just double-click on it. If you hold shift (or MMB if you're running MMBShift and have a 3-button mouse) the entry will be read into a new lister. You can also drop entries onto other listers to have them read them in and keep the hotlist open. Usage (Removing entries): Select all the entries you want removed and press your normal delete button in the lister toolbar. Notes: *) You can 'Snapshot' Hotlist listers. Of course, the snapshot position is only used when a new lister is openned, not when an existing lister it turned into a Hotlist. 'UnSnapshot' also works. *) You can do all of the above using pop-up menus over items if you have "Name mode PopUp" turned on in Environment/Lister Options. *) Dragging stuff between Hotlists isn't supported and can cause strange things (only sometimes). You can usually just close both listers, though. I doubt that dragging between OpusFTP, ArcDir, or any other handler will work, either, but so what? */ /*--------------------------------------------------------------------------------*/ I'm a little ashamed of this long-pasta code. Perhaps I'll tidy things up sometime. /*--------------------------------------------------------------------------------*/ options results options failat 99 parse arg portname function source dest arguments address value portname If ~Show('L','rexxsupport.library') then call addlib('rexxsupport.library',0,-30,0) CR = '0a'x If function='init' then do dopus command "Hotlist" program "Hotlist" desc "'Show user defined path hotlist'" template "NEW/S,CONFIG/K" "source" exit end If function~='Hotlist' then Exit /*--------------------------------------------------------------------------------*/ If Strip(Upper(Word(arguments,1))) = "NEW" then do New_Switch = 1 Arguments = DelWord(Arguments,1,1) end else New_Switch = 0 /* Remove the "CONFIG" keyword if it was given. */ If Strip(Upper(Word(arguments,1))) = "CONFIG" then arguments = DelWord(arguments,1,1) def_hotlist_file = "DOpus5:System/hotlist.config" If Arguments = "" then do hotlist_file = def_hotlist_file HL_Header = "(default)" HL_Label = "Hotlist" end Else do hotlist_file = strip(arguments) HL_Header = hotlist_file HL_Label = "Hotlist <"hotlist_file">" end /*=============*/ Call ParseConfig /*=============*/ If New_Switch = 1 then do /* If "NEW" argument given we must still check the "source" argument as Opus may have automatically busied the source lister for us and it should be unbusied. */ If source~=0 then lister set source busy off lister new snapshot source = RESULT End Else Do /* If not launched from a toolbar (source given as argument), find the source lister and if none open a new lister */ If source=0 then do lister query 'source' stem source_handle. If source_handle.count ~= 0 Then source = source_handle.0 Else do lister new snapshot source = RESULT End End End /* Setup the lister */ lister set source busy 1 lister set source off lister set source namelength 50 lister set source separate dirsfirst lister set source display name comment lister set source lock state on format on lister clear source lister set source path "" lister set source title "Hotlist" lister set source header HL_Header lister set source field 0 Name 4 Path lister set source label HL_Label lister refresh source full Call AddConfigEntries /*--------------------------------------------------------------------------------*/ myportname = "hotlisthd_"source about_string = '"Super-Hotlist for Directory Opus 5'CR'Written by Leo '"'"'Nudel'"'"' Davidson for Gods'"'"'Gift Utils.'CR||CR'Read '"'"'dopus5:modules/Hotlist.dopus5'"'"' for more info." OK' /* Open a port to talk to the lister with. Make sure there isn't already one! */ Call Forbid() If Show("P",myportname) then do Call Permit() dopus request '"Hotlist error: multiple handlers!" OK' Exit End If ~openport(myportname) then do Call Permit() dopus request '"Hotlist error: could not open port" OK' Exit End Call Permit() lister set source handler myportname quotes fullpath Wanted = "Delete MakeDir ScanDir" TrapAndKill = Wanted "Hotlist PrintDir DiskInfo Copy CopyAs Move MoveAs Rename Parent Root Comment Protect Read HexRead Show Play Assign GetSizes DateStamp" do while TrapAndKill ~= "" parse var TrapAndKill FluffyRabbit TrapAndKill dopus addtrap FluffyRabbit myportname end do forever call waitpkt(myportname) packet=getpkt(myportname) if packet~='00000000'x then do arg0=getarg(packet,0) arg1=getarg(packet,1) arg2=getarg(packet,2) arg3=getarg(packet,3) arg4=getarg(packet,4) arg5=getarg(packet,5) arg6=getarg(packet,6) end else arg0="spam" call reply(packet,0) Rereadconfig = 0 /* If we get scandir, re-read the config file. */ if Arg0 = "ScanDir" then Rereadconfig = 1 /* If they type in a path of their own, just read it in (removes us). */ If Arg0 = "path" then if arg2 ~= "" then lister read source arg2 /* If they've used one of the pop-up menu items do that funky stuff... **** MUST BE ABOVE "MakeDir" SECTION!!! **** (Spaghetti code ;-) ) */ If (Arg0 = "menu" & Arg4 = "file") then do if arg5 = totents + 1 then lister request source '"Hotlist error: bad entry! (Too long?)" OK' else do if type.arg5 = "FILE" then do if Arg3 = file_open then command doubleclick Path.arg5 if Arg3 = file_remove then do DelennNeedsIt.Count = 1 DelennNeedsIt.0 = Name.arg5 Call DeleteEntryRoutine end if Arg3 = file_add then Arg0 = "MakeDir" if Arg3 = file_about then lister request source about_string end if type.arg5 = "PATH" then do if Arg3 = path_read then lister read source '"'Path.arg5'"' if Arg3 = path_new then lister new Path.arg5 if Arg3 = path_remove then do DelennNeedsIt.Count = 1 DelennNeedsIt.0 = Name.arg5 Call DeleteEntryRoutine end if Arg3 = path_add then Arg0 = "MakeDir" if Arg3 = path_about then lister request source about_string end if type.arg5 = "INFO" then do if Arg3 = info_about then lister request source about_string end end end /* If something gets dropped on us we should add it to the config file and refresh the display -- Ooow this bit's so wide it hurts! I'm sure Edmund the ARexx-Guru knows a better way to do this and I'm also sure I could think of one, but it's not that bad so WTF... :) */ If Arg0 = "MakeDir" Then Arg2 = "Can you say Kludge?" If (Arg0 = "drop" | Arg0 = "MakeDir") then do while Arg2 ~= "" If Arg0 = "drop" then parse var Arg2 '"'NewPath'"' Arg2 If Arg0 = "MakeDir" then do RESULT = "" lister getstring source '"Enter path for new entry" 100 "" Okay|Cancel' NewPath = RESULT If DOPUSRC = 0 Then NewPath = "" Arg2="" End If NewPath ~= "" Then Do NewPath_U = Upper(NewPath) Do i=0 to totents while (NewPath_U ~= Upper(Path.i)) End If i ~= totents + 1 Then lister request source '"'NewPath||CR'is already in the hotlist!" OK' Else do RESULT = "" lister getstring source '"Enter name for'CR||NewPath'" 50 "'NewPath'" Okay|Cancel' If (DOPUSRC ~= 0 & RESULT ~= "") Then Do NewName = RESULT NewName_U = Upper(NewName) Do i=0 to totents while (NewName_U ~= Upper(Name.i)) End If i ~= totents + 1 then lister request source '"'NewName||CR'is already used in the hotlist!" OK' Else do If Word(StateF(NewPath),1) = "FILE" Then NewType = "FILE" Else NewType = "PATH" lister request source '"Select type-colour for'CR||NewPath'" Device|Dir|File|Assign|Cancel' If RC ~= 0 Then do If RC = 1 then NewColour = "DEV" If RC = 2 then NewColour = "DIR" If RC = 3 then NewColour = "FIL" If RC = 4 then NewColour = "ASS" lister request source '"Plain or Bold?" Plain|Bold' If RC = 0 then NewColour = "B"||Left(NewColour,2) If Exists(hotlist_file) then ncfg_mode = "A" Else ncfg_mode = "W" If ~Open(ncfg,hotlist_file,ncfg_mode) then lister request source '"Could not write to hotlist!" OK' Else do If NewName = NewPath then Call Writeln(ncfg,NewColour NewType '"'NewPath'"') Else Call Writeln(ncfg,NewColour NewType '"'NewPath'"' '"'NewName'"') Call Close(ncfg) Rereadconfig = 1 end End End End end end end /* Wheeee it's a slide! */ /* If they've clicked on an entry, read it in. (Will read into a new buffer and close us down). Unless it's a file, then do doubleclick on it. */ If Arg0 = "doubleclick" then do if arg5 = totents + 1 then lister request source '"Hotlist error: bad entry! (Too long?)" OK' else do If type.arg5 = "INFO" Then lister request source about_string If Type.arg5 = "FILE" Then command doubleclick Path.arg5 If Type.arg5 = "PATH" then do if arg6 = "shift" Then lister new Path.arg5 else lister read source '"'Path.arg5'"' end end end /* If they've dropped one of our entries on another lister tell it that it had better read it or there will be trouble from da boyez... */ If Arg0 = "dropfrom" then do /* I don't know if it's a bug or not but under Opus 5.1226 droping on things which are not other listers returns our lister handle instead of zero! */ If (Arg3=0 | Arg3=source) Then lister request source '"You can only drop entries on other listers." OK' Else do /* Just take the first entry if more than one, and strip quotes, too */ parse var arg2 '"'arg2'"' junk do i=0 to totents while (arg2 ~= Name.i) end selecent = i if selecent = totents + 1 then lister request source '"Hotlist error: bad entry! (Too long?)" OK' else do If Type.selecent = "INFO" then lister request source '"Uhh, no, you can'"'"'t drop that anywhere..." Oh, silly me' If Type.selecent = "FILE" then lister request source '"Drag-n-drop of files doesn'"'"'t'CR'do anything right now." OK' If Type.selecent = "PATH" then lister read arg3 '"'Path.selecent'"' end end end /* Inactive message means close down. No need to check the lister handle as we only deal with one per script */ If Arg0 = "inactive" then do lister set source lock state off format off Call closeport(myportname) Exit End /* The complete pain-in-the-butt Delete routine. I guess I have to write it sooner or later, let's get it over with... Oh, that wasn't too bad. */ If Arg0 = "Delete" then do lister query source selentries stem DelennNeedsIt. Call DeleteEntryRoutine End /* Snapshot & UnSnapshot */ If Arg0 = "snapshot" then do lister query source position snapshot = RESULT Call SaveConfigRoutine end If Arg0 = "unsnapshot" then do snapshot = "" Call SaveConfigRoutine end If Rereadconfig = 1 then do lister set source busy 1 lister refresh source full Call ParseConfig Call AddConfigEntries Rereadconfig = 0 end end EXIT /* Just in case forever comes ;-) */ /*--------------------------------------------------------------------------------*/ /* Read and parse the config file and add items to the lister. *** SHOULD BE CALLED WITH LISTER IN BUSY STATE! *** */ ParseConfig: /* Read and parse the config */ pathmenu.COUNT = 8 pathmenu.0 = "Read Path" pathmenu.1 = "Read Into New Lister" pathmenu.2 = "---" pathmenu.3 = "Remove from Hotlist" pathmenu.4 = "---" pathmenu.5 = "New Item" pathmenu.6 = "---" pathmenu.7 = "About Hotlist" path_read = 0 path_new = 1 path_remove = 3 path_add = 5 path_about = 7 filemenu.COUNT = 7 filemenu.0 = "Open" filemenu.1 = "---" filemenu.2 = "Remove from Hotlist" filemenu.3 = "---" filemenu.4 = "New Item" filemenu.5 = "---" filemenu.6 = "About Hotlist" file_open = 0 file_remove = 2 file_add = 4 file_about = 6 infomenu.COUNT = 1 infomenu.0 = "About Hotlist" info_about = 0 /* Initialise... */ i = -1 badents = 0 snapshot = "" If open(hl,hotlist_file,"R") then do Do until EOF(hl) erp = readln(hl) if length(erp) > 0 then do if word(erp,1) = "SNAPSHOT:" then snapshot = word(erp,2) else do i=i+1 parse var erp Colour.i " " Type.i ' "'Path.i'"' " " '"'Name.i'"' If Path.i ~= "" Then do If Type.i = "" Then Type.i = "PATH" OrgColour.i = Colour.i select when Colour.i = "DEV" then Colour.i = -2 /* Device */ when Colour.i = "DIR" then Colour.i = 1 /* Dir */ when Colour.i = "FIL" then Colour.i = -1 /* File */ when Colour.i = "ASS" then Colour.i = 2 /* Assign */ when Colour.i = "BDE" then Colour.i = -4 /* Bold device */ when Colour.i = "BDI" then Colour.i = 3 /* Bold dir */ when Colour.i = "BFI" then Colour.i = -3 /* Bold file */ when Colour.i = "BAS" then Colour.i = 4 /* Bold assign */ otherwise Colour.i = 2 end end else do lister request source '"Bad entry on line' (i+badents+1) 'of config file" OK' i=i-1 badents = badents + 1 end end end end Call close(hl) end totents = i If totents = -1 then do totents = 0 Name.0 = "" Path.0 = "« Empty Hotlist : Click for info »" Colour.0 = -2 Type.0 = "INFO" End return /*--------------------------------------------------------------------------------*/ /* Add the entries */ AddConfigEntries: lister clear source do i=0 to totents If Name.i = "" Then do Name.i = Path.i /* This is important! */ Morden.COMMENT = "" end Else Morden.COMMENT = "(" || Path.i || ")" Morden.NAME = Name.i Morden.TYPE = Colour.i /* The userdata field (returned in arg5 for doubleclick, drop, and menu events) is used to quickly identify which entry DOpus is talking about. */ Morden.USERDATA = i If Type.i = "INFO" Then Morden.MENU = infomenu. If Type.i = "FILE" Then Morden.MENU = filemenu. If Type.i = "PATH" then Morden.MENU = pathmenu. lister addstem source Morden. end lister refresh source full lister set source busy 0 return /* ========================================================================= */ DeleteEntryRoutine: If DelennNeedsIt.Count > 0 then do If DelennNeedsIt.Count = 1 then plural = "y" else plural = "ies" lister request source '"Warning: you cannot get back'CR'what you delete! OK to delete:'CR||CR||DelennNeedsIt.Count 'entr'plural' from the hotlist?" Proceed|Cancel' If RC ~= 0 Then do If ~Open(ncfg,hotlist_file,"W") then lister request source '"Could not write to hotlist!" OK' Else do If snapshot ~= "" then Writeln(ncfg,"SNAPSHOT:" snapshot) Do i=0 to totents Do x=0 to DelennNeedsIt.Count While (Name.i ~= DelennNeedsIt.x) End If x = ( DelennNeedsIt.Count + 1 ) Then do If Name.i = Path.i then Call Writeln(ncfg,OrgColour.i Type.i '"'Path.i'"') Else Call Writeln(ncfg,OrgColour.i Type.i '"'Path.i'"' '"'Name.i'"') End End Call Close(ncfg) Rereadconfig = 1 End End End Return /* ========================================================================= */ SaveConfigRoutine: /* Does *not* cause config to be re-read! */ If ~Open(ncfg,hotlist_file,"W") then lister request source '"Could not write to hotlist!" OK' Else do If snapshot ~= "" then Writeln(ncfg,"SNAPSHOT:" snapshot) Do i=0 to totents If Name.i = Path.i then Call Writeln(ncfg,OrgColour.i Type.i '"'Path.i'"') Else Call Writeln(ncfg,OrgColour.i Type.i '"'Path.i'"' '"'Name.i'"') End Call Close(ncfg) End Return /* ========================================================================= */ /* Dum tee dumm... Just got ta put another Pizza in the oven... */