Finding+the+application+associated+with+an+extension

//by J.G.Harston, August 2008//

The application associated with a particular file extension (actually, the command used to launch or open a file) is stored in the system registry. This associated command can be found with the following code: code format="bb4w" DEF FNFile_Association(ext$) LOCAL root$,command$,A% root$=FNRegistry_RdStr(&80000000,ext$,"")  :REM No file association command$=FNRegistry_RdStr(&80000000, root$+"\shell\open\command","") IF command$="" THEN =""                    :REM No open command A%=INSTR(command$,"%1"):IF A% THEN command$=LEFT$(command$,A%-1)+MID$(command$,A%+2) A%=INSTR(command$,""""""):IF A% THEN command$=LEFT$(command$,A%-1)+MID$(command$,A%+2) =FNPath_Expand(command$) code So, for example, **FNFile_Association(".txt")** may return **"C:\Program Files\Metapad\metapad.exe"**. If there is no file association, then a null string is returned.

The above code uses the following code from the [|Registry] library and a routine called **FNPath_Expand**: code format="bb4w" DEF FNRegistry_RdInt(hk%,Key$,Item$):LOCAL Want%:Want%=4 DEF FNRegistry_RdBig(hk%,Key$,Item$):LOCAL Want%:Want%=4 DEF FNRegistry_RdStr(hk%,Key$,Item$):LOCAL Want%:Want%=1 DEF FNRegistry_Rd(  hk%,Key$,Item$):LOCAL Want%:Want%=1 LOCAL K%,R%,L%,T%,S$,Buf% SYS "RegOpenKeyEx",hk%,Key$,0,&20001,^K% TO R%     IF R%=0 THEN SYS "RegQueryValueEx",K%,Item$,0,^T%,0,^L%:DIM Buf% LOCAL L%       SYS "RegQueryValueEx",K%,Item$,0,^T%,Buf%,^L% TO R%        SYS "RegCloseKey",K% ENDIF IF Want%=4 :IF R%=0:=0 IF Want%=4 :=!Buf% IF R%:="" IF T%=1:Buf%?(L%-1)=0:=$$Buf% K%=Buf%:WHILE L%:S$+=CHR$?K%:K%+=1:L%-=1:ENDWHILE =S$ DEF FNPath_Expand(S$) LOCAL B%:DIM B% LOCAL 255 SYS "ExpandEnvironmentStrings", S$, B%, 256 =$$B% code

//by Richard Russell, September 2008//

If you prefer not to access the Registry directly, the function below will return the path and name of the executable program which is associated with a particular file:

code format="bb4w" DEF FN_FindExecutable(file$) LOCAL executable{} DIM executable{name&(256)} SYS "FindExecutable", file$, "", executable{} = executable.name& code The main difference from the code listed by Jonathan Harston is that rather than supplying just an extension you must supply the name of an actual file with that extension, which must exist. To overcome that restriction the following function temporarily creates such a file, and in so doing reproduces the functionality of DEFFNFile_Association:

code format="bb4w" DEF FNFile_Association(ext$) LOCAL executable{} DIM executable{name&(256)} OSCLI "SAVE temp"+ext$+" "+STR$~PAGE+" +0" SYS "FindExecutable", "temp"+ext$, "", executable{} OSCLI "DELETE temp"+ext$ = executable.name& code Note that this function relies on the 'current directory' being writable.

//by J.G.Harston, May 2009//

BBC BASIC for Windows version 5.90 introduced the @tmp$ system variable which points to a writable temporary directory. The above code can be rewritten to avoid relying on writing to the current directory:

code format="bb4w" DEF FNFile_Association(ext$) LOCAL executable{} DIM executable{name&(256)} OSCLI "SAVE """+@tmp$+"temp"+ext$+""" "+STR$~PAGE+" +0" SYS "FindExecutable", @tmp$+"temp"+ext$, "", executable{} OSCLI "DELETE """+@tmp$+"temp"+ext$+"""" = executable.name& code