#define WIN32_LEAN_AND_MEAN 1
#define WIN32_EXTRA_LEAN 1
#include <objbase.h>
#include <commdlg.h>
#include <ocidl.h>
#include <stdio.h>
#pragma comment(linker,"/ENTRY:mainCRTStartup")
#pragma comment(linker,"/SUBSYSTEM:CONSOLE")
#pragma comment(lib,"rpcrt4") // UUIDFromString()
// This was compiled with DirectX8 (DirectShow8)
// and Microsoft Visual C/C++ 6.00
#define PLAYWAVE 1
#if PLAYWAVE
#include <dshow.h>
#include <uuids.h>
#pragma comment(lib,"strmiids")
static IGraphBuilder* waveGraph = 0;
static char waveName[1024];
void LoadWave( void )
{
OPENFILENAME ofn = {sizeof(ofn)};
ofn.lpstrFile = waveName;
ofn.nMaxFile = sizeof(waveName);
GetOpenFileName( &ofn );
}
void PlayStop( void )
{
if( waveGraph )
{
IMediaControl *mc = 0;
if( waveGraph->QueryInterface( IID_IMediaControl, (void **)&mc ) == S_OK && mc )
{
mc->Stop();
mc->Release();
}
waveGraph->Release();
waveGraph = 0;
}
}
void PlayWave( IUnknown *filter )
{
WCHAR wPath[1024];
HRESULT hr;
PlayStop();
waveGraph = 0;
hr = CoCreateInstance(CLSID_FilterGraph, NULL, CLSCTX_INPROC_SERVER, IID_IGraphBuilder, (LPVOID *)&waveGraph);
MultiByteToWideChar(CP_ACP, 0, waveName, -1, wPath, sizeof(wPath)/sizeof(wPath[0]));
if( filter )
{
IBaseFilter *baseFilter;
hr = filter->QueryInterface( IID_IBaseFilter, (void **)&baseFilter);
hr = waveGraph->AddFilter( (IBaseFilter *) baseFilter, L"Filter" );
baseFilter->Release();
}
hr = waveGraph->RenderFile(wPath, NULL);
if( waveGraph )
{
IMediaControl *mc = 0;
if( waveGraph->QueryInterface(IID_IMediaControl, (void **)&mc) == S_OK && mc )
{
mc->Run();
mc->Release();
}
}
}
#endif
/* code - malkia@mindless.com */
static struct FILTER {
char *name;
UUID uuid;
} filters[ 1024 ];
static int n_filters;
static int FilterNameSortFunc( const void *a, const void *b )
{
return strcmp( ((FILTER *)a)->name, ((FILTER *)b)->name );
}
static void EnumFilters( void )
{
HKEY hKeyFilter;
HKEY hKeyCLSID;
char keyVal[1024];
DWORD keySize;
DWORD keyType;
FILETIME keyTime;
int index;
if( RegOpenKeyEx(HKEY_CLASSES_ROOT,"filter",0,KEY_READ,&hKeyFilter)==S_OK )
{
for( index=0; RegEnumKeyEx(hKeyFilter,index,keyVal,&(keySize=sizeof(keyVal)),0,NULL,NULL,&keyTime)==S_OK; index++ )
{
char clsidKey[1024];
char name[1024];
sprintf( (char*)clsidKey, "CLSID\\%s", keyVal );
if( RegOpenKeyEx(HKEY_CLASSES_ROOT, (char*)clsidKey, 0, KEY_READ, &hKeyCLSID) == S_OK )
{
if(RegQueryValueEx(hKeyCLSID,"",0,&(keyType=REG_SZ),(LPBYTE)name,&(keySize=sizeof(name)))==S_OK)
{
if(keyVal[0]=='{') strcpy( keyVal, keyVal + 1 );
if(keyVal[strlen(keyVal)-1]=='}') keyVal[strlen(keyVal)-1]=0;
if(UuidFromString( (LPBYTE)keyVal, &filters[n_filters].uuid )==S_OK)
{
filters[n_filters].name = strdup( name );
if(++n_filters == sizeof(filters)/sizeof(filters[0]))
break;
}
}
RegCloseKey(hKeyCLSID);
}
}
}
qsort(filters,n_filters,sizeof(filters[0]),FilterNameSortFunc);
}
enum { // These are our ids inside the dialog
ID_Null,
ID_FiltersListBox,
ID_OkButton,
ID_CancelButton,
ID_PlayButton,
ID_LoadButton,
};
// Resizes a window to fit a client area size(width,height)
static void windowSize( HWND wnd, int width, int height )
{
RECT crect, wrect;
int screenWidth, screenHeight;
int windowWidth, windowHeight;
GetWindowRect( wnd, &wrect );
GetClientRect( wnd, &crect );
screenWidth = GetSystemMetrics( SM_CXSCREEN );
screenHeight = GetSystemMetrics( SM_CYSCREEN );
windowWidth = wrect.right - wrect.left - crect.right + width,
windowHeight = wrect.bottom - wrect.top - crect.bottom + height;
MoveWindow( wnd, (screenWidth - windowWidth)/2, (screenHeight - windowHeight)/2, windowWidth, windowHeight, TRUE );
}
static void dialogFit( HWND dlg, int propPageWidth, int propPageHeight, RECT *rect )
{
enum {
MinDialogHeight = 50, //400,
ListBoxWidth = 200,
ButtonWidth = 60,
ButtonHeight = 20,
ButtonOffset = 4,
MinDialogWidth = ListBoxWidth + ButtonOffset + 4*(ButtonOffset + ButtonWidth),
};
HWND listBox, button1, button2, button3, button4;
int screenWidth, screenHeight;
int dialogWidth, dialogHeight;
screenWidth = GetSystemMetrics( SM_CXSCREEN );
screenHeight = GetSystemMetrics( SM_CYSCREEN );
listBox = GetDlgItem( dlg, ID_FiltersListBox );
button1 = GetDlgItem( dlg, ID_CancelButton );
button2 = GetDlgItem( dlg, ID_OkButton );
button3 = GetDlgItem( dlg, ID_LoadButton );
button4 = GetDlgItem( dlg, ID_PlayButton );
dialogWidth = ListBoxWidth + propPageWidth;
dialogHeight = propPageHeight + ButtonOffset*2 + ButtonHeight;
if( dialogWidth < MinDialogWidth )
dialogWidth = MinDialogWidth;
if( dialogHeight < MinDialogHeight )
dialogHeight = MinDialogHeight;
windowSize( dlg, dialogWidth, dialogHeight );
MoveWindow( listBox, 0, 0, ListBoxWidth, dialogHeight, TRUE );
MoveWindow( button1, dialogWidth - 1*(ButtonOffset + ButtonWidth), dialogHeight - ButtonOffset - ButtonHeight, ButtonWidth, ButtonHeight, TRUE );
MoveWindow( button2, dialogWidth - 2*(ButtonOffset + ButtonWidth), dialogHeight - ButtonOffset - ButtonHeight, ButtonWidth, ButtonHeight, TRUE );
MoveWindow( button3, dialogWidth - 3*(ButtonOffset + ButtonWidth), dialogHeight - ButtonOffset - ButtonHeight, ButtonWidth, ButtonHeight, TRUE );
MoveWindow( button4, dialogWidth - 4*(ButtonOffset + ButtonWidth), dialogHeight - ButtonOffset - ButtonHeight, ButtonWidth, ButtonHeight, TRUE );
if( rect )
{
rect->left = ListBoxWidth;
rect->top = 0;
rect->right = rect->left + propPageWidth;
rect->bottom = rect->top + propPageHeight;
}
}
static struct {
IUnknown *filter;
IPropertyPage *propPage;
int propWidth, propHeight;
} activeFilter;
static void SetActiveFilter( HWND wnd, int item )
{
CAUUID caGUID={0};
ISpecifyPropertyPages *pSpecProp=0;
try
{
HRESULT hr;
PROPPAGEINFO pPageInfo;
if( activeFilter.propPage )
{
activeFilter.propPage->Deactivate();
activeFilter.propPage->Release();
activeFilter.propPage=0;
}
if( activeFilter.filter )
{
activeFilter.filter->Release();
activeFilter.filter = 0;
}
if( (hr=CoCreateInstance(filters[item].uuid,NULL,CLSCTX_INPROC_SERVER,IID_IUnknown,(void**)&activeFilter.filter))==S_OK
&& (hr=activeFilter.filter->QueryInterface(IID_ISpecifyPropertyPages,(void**)&pSpecProp))==S_OK
&& (hr=pSpecProp->GetPages(&caGUID))==S_OK
&& (caGUID.cElems >= 1) // but actually we are showing only the first page
&& (hr=CoCreateInstance(caGUID.pElems[0],NULL,CLSCTX_INPROC_SERVER,IID_IPropertyPage,(void**)&activeFilter.propPage))==S_OK
&& (hr=activeFilter.propPage->SetObjects(1,(IUnknown **)&activeFilter.filter))==S_OK
&& (hr=activeFilter.propPage->GetPageInfo(&pPageInfo))==S_OK)
{
RECT rect;
dialogFit( wnd, pPageInfo.size.cx, pPageInfo.size.cy, &rect );
activeFilter.propWidth = pPageInfo.size.cx;
activeFilter.propHeight = pPageInfo.size.cy;
activeFilter.propPage->Activate( wnd, &rect, FALSE );
activeFilter.propPage->Show( SW_SHOW );
}
else
{
dialogFit( wnd, 0, 400, NULL );
}
}
catch( ... )
{
}
if( pSpecProp ) pSpecProp->Release();
if( caGUID.pElems ) CoTaskMemFree(caGUID.pElems);
}
static INT_PTR CALLBACK dialogProc( HWND dlg, UINT uMsg, WPARAM wParam, LPARAM lParam )
{
switch( uMsg )
{
HGDIOBJ font;
int i;
case WM_INITDIALOG:
SetWindowText( dlg, "DirectX audio plug-ins viewer 0.10 - " __DATE__ "/" __TIME__ " malkia@mindless.com");
font = GetStockObject( DEFAULT_GUI_FONT );
SendDlgItemMessage( dlg, ID_FiltersListBox, WM_SETFONT, (WPARAM)font, FALSE );
SendDlgItemMessage( dlg, ID_OkButton, WM_SETFONT, (WPARAM)font, FALSE );
SendDlgItemMessage( dlg, ID_CancelButton, WM_SETFONT, (WPARAM)font, FALSE );
SendDlgItemMessage( dlg, ID_PlayButton, WM_SETFONT, (WPARAM)font, FALSE );
SendDlgItemMessage( dlg, ID_LoadButton, WM_SETFONT, (WPARAM)font, FALSE );
SetDlgItemText( dlg, ID_OkButton, "Ok" );
SetDlgItemText( dlg, ID_CancelButton, "Cancel" );
SetDlgItemText( dlg, ID_PlayButton, "Play" );
SetDlgItemText( dlg, ID_LoadButton, "Load" );
for( i=0; i<n_filters; i++ )
SendDlgItemMessage( dlg, ID_FiltersListBox, LB_ADDSTRING, 0, (LPARAM)filters[i].name);
dialogFit( dlg, 0, 400, NULL );
return FALSE;
case WM_COMMAND:
switch(LOWORD(wParam))
{
case ID_LoadButton:
#if PLAYWAVE
EnableWindow(dlg,FALSE);
LoadWave();
EnableWindow(dlg,TRUE);
SetForegroundWindow( dlg );
#endif
break;
case ID_PlayButton:
#if PLAYWAVE
EnableWindow(dlg,FALSE);
PlayWave(activeFilter.filter);
EnableWindow(dlg,TRUE);
#endif
break;
case ID_OkButton:
EndDialog( dlg, 1 );
break;
case ID_CancelButton:
EndDialog( dlg, 0 );
break;
case ID_FiltersListBox:
switch(HIWORD(wParam))
{
case LBN_DBLCLK:
i = SendDlgItemMessage(dlg, ID_FiltersListBox,LB_GETCURSEL,0,0);
if( i != LB_ERR )
{
// Some DEMO versions of various plugin are displaying a MessageBox before
// inializing the object - Enable/DisableWindow is for them.
// Example: FASOFT.COM n-Track trial version plug-ins
EnableWindow( dlg, FALSE );
SetActiveFilter(dlg, i );
EnableWindow( dlg, TRUE );
SetForegroundWindow( dlg );
}
break;
}
break;
}
return TRUE;
}
return FALSE;
}
#define DLG_ITEM(type,id,style,styleEx,x,y,cx,cy) style,styleEx,x,y,cx,cy,id,0xFFFF,type,0,0,0
#define DLG_BUTTON( id,style,styleEx,x,y,cx,cy) DLG_ITEM(0x0080,id,style,styleEx,x,y,cx,cy)
#define DLG_EDIT( id,style,styleEx,x,y,cx,cy) DLG_ITEM(0x0081,id,style,styleEx,x,y,cx,cy)
#define DLG_STATIC( id,style,styleEx,x,y,cx,cy) DLG_ITEM(0x0082,id,style,styleEx,x,y,cx,cy)
#define DLG_LISTBOX( id,style,styleEx,x,y,cx,cy) DLG_ITEM(0x0083,id,style,styleEx,x,y,cx,cy)
#define DLG_SCROLLBAR(id,style,styleEx,x,y,cx,cy) DLG_ITEM(0x0084,id,style,styleEx,x,y,cx,cy)
#define DLG_COMBOBOX( id,style,styleEx,x,y,cx,cy) DLG_ITEM(0x0085,id,style,styleEx,x,y,cx,cy)
typedef struct {
DLGITEMTEMPLATE item;
WORD _0xFFFF;
WORD type;
WORD _zero0;
WORD _zero1;
WORD _zero2;
} DIALOG_ITEM;
typedef struct {
DLGTEMPLATE dialogTemplate;
WORD _zer0,_zero1, zero2;
DIALOG_ITEM items[5];
} DIALOG;
static DIALOG dialogRes =
{
{ WS_CAPTION|DS_CENTER,0,sizeof(dialogRes.items)/sizeof(dialogRes.items[0]),0,0,0,0 }, 0,0, 0,
{
DLG_LISTBOX(ID_FiltersListBox, WS_BORDER|WS_CHILD|WS_VISIBLE|WS_VSCROLL|LBS_NOINTEGRALHEIGHT|LBS_NOTIFY,0,0,0,0,0),
DLG_BUTTON( ID_OkButton, WS_CHILD|WS_VISIBLE|BS_TEXT|BS_CENTER|BS_DEFPUSHBUTTON,0,0,0,0,0),
DLG_BUTTON( ID_CancelButton, WS_CHILD|WS_VISIBLE|BS_TEXT|BS_CENTER|BS_PUSHBUTTON,0,0,0,0,0),
DLG_BUTTON( ID_LoadButton, WS_CHILD|WS_VISIBLE|BS_TEXT|BS_CENTER|BS_PUSHBUTTON,0,0,0,0,0),
DLG_BUTTON( ID_PlayButton, WS_CHILD|WS_VISIBLE|BS_TEXT|BS_CENTER|BS_PUSHBUTTON,0,0,0,0,0),
}
};
void main( int argc, char *argv[])
{
CoInitialize(NULL);
EnumFilters();
DialogBoxIndirect( NULL, &dialogRes.dialogTemplate, NULL, dialogProc );
CoUninitialize();
}
|