Initial commit: ROW Client source code

Game client codebase including:
- CharacterActionControl: Character and creature management
- GlobalScript: Network, items, skills, quests, utilities
- RYLClient: Main client application with GUI and event handlers
- Engine: 3D rendering engine (RYLGL)
- MemoryManager: Custom memory allocation
- Library: Third-party dependencies (DirectX, boost, etc.)
- Tools: Development utilities

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
This commit is contained in:
2025-11-29 16:24:34 +09:00
commit e067522598
5135 changed files with 1745744 additions and 0 deletions

View File

@@ -0,0 +1,428 @@
//------------------------------------------------------------------------------
// File: Demonstration.CPP
//
// Desc: DirectShow sample code
// Implementation of CDemonstration,
// "special effects" module to represent capabilities of VMR.
// This class is called from CVMRMixDlg by "Play" button.
// CDemonstration contains CVMRCore member (VMR engine) through which
// it performs initialization of the graph builder and presentation.
//
// Copyright (c) 2000-2001 Microsoft Corporation. All rights reserved.
//------------------------------------------------------------------------------
#include "stdafx.h"
#include "Demonstration.h"
#include <math.h>
#define DO_NOT_RUN_YET true
//------------------------------------------------------------------------------
// Perform
// Desc: Performs presentation. Just call it from the 'parent' dialog
// Return HRESULT
//------------------------------------------------------------------------------
HRESULT CDemonstration::Perform()
{
HRESULT hr = S_OK;
clock_t tStart;
clock_t tCurrent;
clock_t tUpdate;
if( false == m_bInitialized )
{
hr = Initialize();
}
if( FAILED(hr) )
{
return hr;
}
try
{
hr = m_pCore->Play();
if( FAILED(hr) )
{
sprintf( m_szMsg, "Failed to run VMR, method returned %s\n", hresultNameLookup(hr));
OutputDebugString(m_szMsg);
return hr;
}
}
catch(...)
{
OutputDebugString("Unhandled exception in CDemonstration::Perform()\n");
ShellAbort(m_pCore);
return E_POINTER;
}
tStart = clock();
tCurrent = clock();
tUpdate = clock();
// presentation loop: wait until presentation is over
// or user closed the window and VMRCore is inactive
while( (tCurrent - tStart) / CLOCKS_PER_SEC < m_MList.GetAvgDuration() / 10000000L &&
m_pCore->IsActive() )
{
Sleep(10);
UpdateStreams(tStart);
tCurrent = clock();
}// while
return S_OK;
}
//------------------------------------------------------------------------------
// Initialize()
// Desc: Initializes demonstration; fills start parameters,
// creates the graph for VMR; renders files
// Return: HRESULT
//------------------------------------------------------------------------------
HRESULT CDemonstration::Initialize()
{
HRESULT hr = S_OK;
LONGLONG llCurrent = 0L;
LONGLONG llStop = 0L;
LONGLONG llDelay = 0L;
clock_t tStart;
// calculate playback time
m_MList.AdjustDuration();
m_MList.SetInitialParameters();
// create VMRCore
m_pCore = new CVMRCore(m_pDlg, &m_MList );
tStart = clock();
if( !m_pCore)
{
return E_OUTOFMEMORY;
}
// here, VMRCore creates the graph and if successfully, runs IMediaControl
// for the first file from the media list
hr = m_pCore->Play(DO_NOT_RUN_YET);
if(FAILED(hr))
{
return hr;
}
// if user selected "show bitmap" option, load the bitmap
// from the resource and apply color key
if( m_pDlg->IsBitmapToUse())
{
hr = SetAlphaBitmapColorKey(IDB_BITMAP_LOGO);
if(FAILED(hr))
{
OutputDebugString("Failed to SetAlphaBitmapColorKey() in CDemonstration::Initialize()\n");
return E_INVALIDARG;
}
}
m_bInitialized = true;
return S_OK;
}
//------------------------------------------------------------------------------
// SetAlphaBitmapColorKey
// Desc: initializes proper members of VMRALPHABITMAP for solor key support
// Parameters: [in] UINT ImageID - resource ID
// Return: HRESULT
//------------------------------------------------------------------------------
HRESULT CDemonstration::SetAlphaBitmapColorKey(UINT ImageID)
{
HRESULT hr;
if( ! m_pCore )
{
OutputDebugString("Function SetAlphaBitmapColorKey() is called before initializing m_pCore\n");
return E_INVALIDARG;
}
// prepare the valid default bitmap
if (GetValidVMRBitmap(ImageID) != FNS_PASS)
{
OutputDebugString("Unable to get a valid VMRALPHABITMAP\n");
return E_INVALIDARG;
}
m_sBmpParams.fAlpha = 1.0f;
m_sBmpParams.clrSrcKey = RGB(255,255,255);
m_sBmpParams.dwFlags |= VMRBITMAP_SRCCOLORKEY;
try
{
hr = m_pCore->GetMixerBitmap()->SetAlphaBitmap(&m_sBmpParams);
if( FAILED(hr) )
{
return hr;
}
} // try
catch(...)
{
return ShellAbort(m_pCore);
}
return S_OK;
}
//------------------------------------------------------------------------------
// GetValidVMRBitmap
// Desc: creates bitmap compatible with VMR
// Parameters: [in] UINT ImageID - resource ID
// [out] VMRALPHABITMAP * vmrBmp - what IVMRMixerBitmap uses
// Return: HRESULT
//------------------------------------------------------------------------------
HRESULT CDemonstration::GetValidVMRBitmap(UINT ImageID)
{
HRESULT hr = S_OK;
long cx, cy;
HDC hdc;
HBITMAP hbmpVmr;
BITMAP bmp;
hr = m_pCore->GetVMRWndless()->GetNativeVideoSize(&cx, &cy, NULL, NULL);
if( FAILED(hr) )
{
OutputDebugString("Failed in GetNativeVideoSize()\n");
return hr;
}
// get compatible DC
hdc = GetDC(m_pCore->GetClientHwnd());
m_hbmp = CreateCompatibleBitmap(hdc, cx, cy); /*** RELEASE ***/
hbmpVmr = (HBITMAP)LoadImage(AfxGetInstanceHandle(),MAKEINTRESOURCE(ImageID),IMAGE_BITMAP,0,0,/*LR_LOADFROMFILE|*/LR_CREATEDIBSECTION);
if( !hbmpVmr )
{
OutputDebugString("Failed to load resource\n");
DeleteObject(m_hbmp);
return E_INVALIDARG;
}
// Get size of the bitmap
GetObject( hbmpVmr, sizeof(bmp), &bmp );
HDC hdcBmp = CreateCompatibleDC(hdc); /*** RELEASE ***/
HDC hdcVMR = CreateCompatibleDC(hdc);
ReleaseDC(m_pCore->GetClientHwnd(), hdc);
HBITMAP hbmpold = (HBITMAP)SelectObject(hdcBmp, m_hbmp);// in hdcBmp, select hbmp
hbmpVmr = (HBITMAP)SelectObject(hdcVMR, hbmpVmr);// in hdcVmr, select hbmpVmr (the pic we loaded)
BitBlt(hdcBmp, 0, 0, bmp.bmWidth, bmp.bmHeight, hdcVMR, 0, 0, SRCPAINT);// put loaded pic from hdcVmr to hdcBmp
DeleteObject(SelectObject(hdcVMR, hbmpVmr));// ok, we do not need hbmpVmr any more
DeleteDC(hdcVMR);
RECT rc;
ZeroMemory(&m_sBmpParams, sizeof(VMRALPHABITMAP) );
m_sBmpParams.dwFlags = VMRBITMAP_HDC;
m_sBmpParams.hdc = hdcBmp;
// set source rectangle (entire original bitmap)
SetRect(&rc, 0, 0, bmp.bmWidth, bmp.bmHeight);
m_sBmpParams.rSrc = rc;
float fCoeff = 0.2f + 1.7f * (float)rand()/RAND_MAX;
// set destination rectangle (keeping aspect ratio of the original image)
// please note that normalized rect is always in [0.0, 1.0] range for
// all its members
m_sBmpParams.rDest.left = 0.f;
m_sBmpParams.rDest.top = 0.f;
m_sBmpParams.rDest.right = 0.9f*(float)bmp.bmWidth / (float)cx;
m_sBmpParams.rDest.bottom = 0.9f*(float)bmp.bmHeight / (float)cy;
m_sBmpParams.fAlpha = 0.5f;
// quite important, otherwise VMR would give error
m_sBmpParams.pDDS = NULL;
// Note: this demo uses bitmap directly, but often it is better to create
// DirectDrawSurface of appropriate format and set m_sBmpParams.pDDS to it
// (especially if you experience performance issues)
return S_OK;
}
//------------------------------------------------------------------------------
// UpdateStreams
// Desc: updates presentation parameters (destination rectangles and alpha level)
// for each media file
// Parameters: clock_t tStart -- presentation start; used as a 'time' variable
// in calculations
// Return: HRESULT
//------------------------------------------------------------------------------
HRESULT CDemonstration::UpdateStreams(clock_t tStart)
{
HRESULT hr = S_OK;
int i;
clock_t tCurrent;
NORMALIZEDRECT rectD0;
NORMALIZEDRECT rectD;
NORMALIZEDRECT rectDRes;
double Alpha0;
double Alpha;
ASSERT( tStart >0 );
for( i=0; i< this->m_MList.Size(); i++)
{
if( false == m_MList.GetItem(i)->m_bInUse)
continue;
tCurrent = clock() - tStart;
rectD0 = m_MList.GetItem(i)->m_rD;
Alpha0 = m_MList.GetItem(i)->m_fAlpha;
Alpha = 1.f;
rectD.left = rectD.top = 0.f;
rectD.right = rectD.bottom = 1.f;
FountainPath( tCurrent,
(long)(m_MList.GetAvgDuration() / 10000000 * CLOCKS_PER_SEC),
i,
rectD0,
Alpha0,
&rectD,
&Alpha);
hr = m_pCore->GetMixerControl()->SetAlpha(i, (float)Alpha);
if( !SUCCEEDED(hr))
{
sprintf( m_szMsg, "Failure in CDemonstration::UpdateStreams, GetMixerControl()->SetAlpha, method returned %s\n",
hresultNameLookup(hr));
OutputDebugString(m_szMsg);
}
hr = m_pCore->GetMixerControl()->SetOutputRect(i, &rectD);
if( !SUCCEEDED(hr))
{
sprintf( m_szMsg, "Failure in CDemonstration::UpdateStreams, GetMixerControl()->SetOutputRect, method returned %s\n",
hresultNameLookup(hr));
OutputDebugString(m_szMsg);
}
hr = m_pCore->GetMixerControl()->GetOutputRect(i, &rectDRes);
if( !SUCCEEDED(hr))
{
sprintf( m_szMsg, "Failure in CDemonstration::UpdateStreams, GetMixerControl()->GetOutputRect, method returned %s\n",
hresultNameLookup(hr));
OutputDebugString(m_szMsg);
}
else
{
if( fabs(rectD.top - rectDRes.top) > 0.01 ||
fabs(rectD.bottom - rectDRes.bottom) > 0.01 ||
fabs(rectD.left - rectDRes.left) > 0.01 ||
fabs(rectD.right - rectDRes.right) > 0.01 )
{
sprintf( m_szMsg, "Failed invalidation of SetOutputRect(): required [l,t,r,b] = [%f,%f,%f,%f] and returned [%f,%f,%f,%f]\n",
rectD.left, rectD.top, rectD.right, rectD.bottom,
rectDRes.left, rectDRes.top, rectDRes.right, rectDRes.bottom );
OutputDebugString(m_szMsg);
}
}// else
}// for
return hr;
}
//------------------------------------------------------------------------------
// Name: FountainPath
// Purpose: creates 'movie fountain' effect; for each stream, center point
// moves by a random ellipse around the center of a playback window;
// size and alpha-level of stream's output rect changes by cosine with
// some random initial delay (to desynchronize streams)
// Parameters:
// [IN] long t - current timestamp (any units, we use relative time)
// [IN] long T - expected total playback time (in the same units as t)
// [IN] int n - id of particular stream we want to set
// [IN] NORMALIZEDRECT r0 - original OutputRect of the stream
// [IN] double A0 - original alpha level (used as a parameter for smoothly
// changing alpha level)
// [OUT] NORMALIZEDRECT * pR - dest. part of playback window
// [OUT] double * pA - new alpha level
//------------------------------------------------------------------------------
void CDemonstration::FountainPath( long t,
long T,
int n,
NORMALIZEDRECT r0,
double A0,
NORMALIZEDRECT * pR,
double * pA)
{
double cx0; // original center of the output rect, in normalized coordinates
double cy0;
double cx; // new center of the output rect, in normalized coordinates
double cy;
double cx1; // auxiliary center of the output rect, in normalized coordinates
double cy1;
double L0; // original half-diagonal measure of the rectangle
double w; // orig. rect width
double h; // orig. rect height
double beta; // shift in cosine for L(t). see below
double L; // new half-diagonal measure of the rectangle
double tau; // time in relative units
double gamma; // shift in sine for A(t). see below
double coeff; // coefficient that is used to create 'mirror-flip' effect
double dx; // new half-width
double dy; // new half-heights
// relative time, to have about 3 periods over the total playtime
tau = 18.0 * (double)t / T;
// alpha level, A = 0.2 + 0.8 sin( tau + gamma) where gamma is such that A(0)=A0
gamma = (A0 - 0.2)/0.8;
gamma = (gamma < -1.) ? -1. : gamma;
gamma = (gamma > 1. ) ? 1. : gamma;
gamma = asin( gamma);
*pA = 0.6 + 0.4 * sin(tau + gamma + A0);
cx0 = (r0.left + r0.right)/2.;
cy0 = (r0.top + r0.bottom)/2.;
w = r0.right - r0.left;
h = r0.bottom - r0.top;
L0 = 0.5 * sqrt(w*w + h*h);
L0 = (L0 < 0.0001) ? 0.1 : L0;
// now rectangle. Its half-diagonal measure L = 0.1 + 0.7 cos( tau + beta)
// where beta is such that L(0) = LO;
beta = (L0 - 0.1)/0.7;
beta = (beta < -1.) ? -1. : beta;
beta = (beta > 1.) ? 1. : beta;
beta = acos( beta);
L = 0.35 + 0.45 * cos( tau + beta + 3.*A0);
// center of the rectangle is moving by ellips
// cx = cx0 + (-1)^n 0.1 sin(tau);
// cy = cy0 - 0.2 + 0.2 cos( tau);
// and turn it buy... say, theta = 7.85 A0 - 1.57;
coeff = (n%2) ? -1. : 1.;
cx1 = cx0 + coeff * 0.2 * sin(tau + A0);
cy1 = cy0 - 0.05 + 0.2 * cos( tau + A0);
// the lines below are unnecessary, but we could want some
// additional transformation here, like turn trajectory ellipse
// by some angle
cx = cx1;
cy = cy1;
dx = L * w / L0;
dy = L * h / L0;
pR->left = (float)(cx - dx);
pR->right = (float)(cx + dx);
pR->top = (float)(cy - dy);
pR->bottom = (float)(cy + dy);
}

View File

@@ -0,0 +1,95 @@
//------------------------------------------------------------------------------
// File: Demonstration.h
//
// Desc: DirectShow sample code
// Header file and class description for CDemonstration,
// "special effects" module to represent capabilities of VMR.
// This class is called from CVMRMixDlg by the "Play" button.
// CDemonstration contains CVMRCore member (VMR engine), through which
// it performs initialization of the graph builder and presentation.
//
// Copyright (c) 2000-2001 Microsoft Corporation. All rights reserved.
//------------------------------------------------------------------------------
#ifndef HDR_DEMONSTRATION
#define HDR_DEMONSTRATION
#include "stdafx.h"
class CVMRMixDlg;
class CDemonstration
{
private:
CVMRMixDlg * m_pDlg; // 'parent' dialog
char m_szMsg[MAX_PATH]; // auxiliary string for debug messages
bool m_bInitialized; // true if graph is build and files are rendered;
// false otherwise
CMediaList m_MList; // media list to be played
CVMRCore * m_pCore; // 'main' class that implements VMR management
VMRALPHABITMAP m_sBmpParams; // used in IVMRMixerBitmap; parameters
// of the bitmap overlapping the video
HBITMAP m_hbmp; // handle to the bitmap overlapping the video
HRESULT SetAlphaBitmapColorKey(UINT ImageID); // set color key for overlapping bitmap
HRESULT GetValidVMRBitmap(UINT ImageID); // create bitmap compatible with renderer's settings
public:
CDemonstration( CVMRMixDlg * pDlg, // 'parent' dialog
CMediaList * pMajorList,// media list to play
int nSize, // size of pMajorList
HRESULT *phr) :
m_pDlg(pDlg),
m_hbmp(NULL),
m_pCore(NULL),
m_bInitialized(false)
{
ASSERT(phr);
ASSERT( nSize > 0);
strcpy( m_szMsg, "");
*phr = S_OK;
ZeroMemory( &m_sBmpParams, sizeof(VMRALPHABITMAP));
srand( clock());
pMajorList->Shuffle();
if( false == pMajorList->Clone(nSize, &m_MList))
{
*phr = E_INVALIDARG;
return;
}
};
virtual ~CDemonstration()
{
if( m_pCore )
{
delete m_pCore;
}
if( m_hbmp)
{
DeleteObject( m_hbmp );
}
if( m_sBmpParams.hdc )
{
DeleteDC( m_sBmpParams.hdc );
}
m_MList.Clean();
};
HRESULT Initialize();
HRESULT UpdateStreams(clock_t tStart);
virtual HRESULT Perform();
// this function calculates parameters for the 'swirling windows' effect
void FountainPath( long t,
long T,
int n,
NORMALIZEDRECT r0,
double A0,
NORMALIZEDRECT * pR,
double * pA);
};
#endif

View File

@@ -0,0 +1,64 @@
//------------------------------------------------------------------------------
// File: DlgWait.cpp
//
// Desc: DirectShow sample code
// Progress bar 'wait' dialog
//
// Copyright (c) 2000-2001 Microsoft Corporation. All rights reserved.
//------------------------------------------------------------------------------
#include "stdafx.h"
#include "VMRMix.h"
#include "DlgWait.h"
#ifdef _DEBUG
#define new DEBUG_NEW
#undef THIS_FILE
static char THIS_FILE[] = __FILE__;
#endif
/////////////////////////////////////////////////////////////////////////////
// CDlgWait dialog
CDlgWait::CDlgWait(int nMax, CWnd* pParent /*=NULL*/)
: CDialog(CDlgWait::IDD, pParent)
{
m_Max = nMax;
//{{AFX_DATA_INIT(CDlgWait)
// NOTE: the ClassWizard will add member initialization here
//}}AFX_DATA_INIT
}
void CDlgWait::DoDataExchange(CDataExchange* pDX)
{
CDialog::DoDataExchange(pDX);
//{{AFX_DATA_MAP(CDlgWait)
DDX_Control(pDX, IDC_PROGRESS, m_Progress);
//}}AFX_DATA_MAP
}
BEGIN_MESSAGE_MAP(CDlgWait, CDialog)
//{{AFX_MSG_MAP(CDlgWait)
//}}AFX_MSG_MAP
END_MESSAGE_MAP()
/////////////////////////////////////////////////////////////////////////////
// CDlgWait message handlers
BOOL CDlgWait::OnInitDialog()
{
CDialog::OnInitDialog();
m_Progress.SetRange(0, (WORD) m_Max);
return TRUE; // return TRUE unless you set the focus to a control
// EXCEPTION: OCX Property Pages should return FALSE
}
void CDlgWait::SetPos( int n)
{
m_Progress.SetPos( n);
}

View File

@@ -0,0 +1,63 @@
//------------------------------------------------------------------------------
// File: DlgWait.h
//
// Desc: DirectShow sample code
//
// Copyright (c) 2000-2001 Microsoft Corporation. All rights reserved.
//------------------------------------------------------------------------------
#if !defined(AFX_DLGWAIT_H__E66757E7_0C93_448B_B402_50E8111FCD7E__INCLUDED_)
#define AFX_DLGWAIT_H__E66757E7_0C93_448B_B402_50E8111FCD7E__INCLUDED_
#if _MSC_VER > 1000
#pragma once
#endif // _MSC_VER > 1000
// DlgWait.h : header file
//
/////////////////////////////////////////////////////////////////////////////
// CDlgWait dialog
class CDlgWait : public CDialog
{
// Construction
public:
CDlgWait(int nMax, CWnd* pParent = NULL); // standard constructor
virtual ~CDlgWait()
{
DestroyWindow();
};
void SetPos( int n);
// Dialog Data
//{{AFX_DATA(CDlgWait)
enum { IDD = IDD_DIALOG_PROGRESS };
CProgressCtrl m_Progress;
//}}AFX_DATA
// Overrides
// ClassWizard generated virtual function overrides
//{{AFX_VIRTUAL(CDlgWait)
protected:
virtual void DoDataExchange(CDataExchange* pDX); // DDX/DDV support
//}}AFX_VIRTUAL
// Implementation
protected:
// Generated message map functions
//{{AFX_MSG(CDlgWait)
virtual BOOL OnInitDialog();
//}}AFX_MSG
DECLARE_MESSAGE_MAP()
private:
int m_Max;
};
//{{AFX_INSERT_LOCATION}}
// Microsoft Visual C++ will insert additional declarations immediately before the previous line.
#endif // !defined(AFX_DLGWAIT_H__E66757E7_0C93_448B_B402_50E8111FCD7E__INCLUDED_)

View File

@@ -0,0 +1,30 @@
Windows XP DirectShow Sample -- VMRMix
--------------------------------------
Description: This application shows capabilities of the new
video mixing renderer (VMR) that is the default video
renderer in Windows XP. In particular, it demonstrates
how to use the VMR in a mixing mode with several sources,
how to apply a bitmap image with a color key over the video,
and how to take advantage of the IVMRMixerControl interface
to manage source and destination rectangles and alpha-level
for each media stream.
Usage:
Upon initialization, VMRMix asks the user to specify a
media folder that contains at least two valid media files,
after which it loads media settings from that folder.
The user is asked to specify playback options:
number of source files, size of the playback window, and
whether to display a static bitmap image. When the user
clicks on the 'Play' button, a new window appears to mix
the selected streams. The demonstration lasts until the
longest media file reaches the end. You can interrupt the
demonstration by closing the playback window.
Troubleshooting:
This application was originally created as a stress test,
so it uses more system resources when displaying a maximum
number of streams and when using "full-screen" mode. If
video is freezing or slows down, try selecting fewer sources
and turn off the "full-screen" option.

View File

@@ -0,0 +1,293 @@
//------------------------------------------------------------------------------
// File: SourceInfo.cpp
//
// Desc: DirectShow sample code
// Implementation of CMediaList, play-list of media files
//
// Copyright (c) 2000-2001 Microsoft Corporation. All rights reserved.
//------------------------------------------------------------------------------
#include "stdafx.h"
#include "SourceInfo.h"
//////////////////////////////////////////////////////////////////////
// Construction/Destruction
//////////////////////////////////////////////////////////////////////
CMediaList::CMediaList() :
m_avgDuration(0L),
m_N(0),
m_ppSI(NULL)
{
}
CMediaList::~CMediaList()
{
Clean();
}
//------------------------------------------------------------------------------
void CMediaList::Clean()
{
for( int i=0; i<m_N; i++)
{
delete m_ppSI[i];
m_ppSI[i] = NULL;
}// for
delete[] m_ppSI;
m_ppSI = NULL;
m_N = 0;
}
//------------------------------------------------------------------------------
// CMediaList::Add
// Desc: adds a new source to the media list
// return: true if success, false otherwise
//------------------------------------------------------------------------------
bool CMediaList::Add( SourceInfo * pSI)
{
SourceInfo ** ppSInew = NULL;
ppSInew = new SourceInfo*[m_N+1];
if( !ppSInew )
return false;
for( int i=0; i<m_N; i++)
{
ppSInew[i] = m_ppSI[i];
}// for
ppSInew[m_N] = pSI;
delete[] m_ppSI;
m_ppSI = ppSInew;
m_N++;
return true;
}
//------------------------------------------------------------------------------
// CMediaList::Shuffle()
// Desc: randomly shuffles media list content to
// have different playback settings every time
//------------------------------------------------------------------------------
void CMediaList::Shuffle()
{
SourceInfo *pSIaux = NULL;
int n1;
int n2;
for(int i=0; i< m_N; i++)
{
n1 = rand() * (m_N+1) / RAND_MAX;
n2 = rand() * (m_N+1) / RAND_MAX;
n1 = ( n1<0) ? 0 : n1;
n2 = ( n2<0) ? 0 : n2;
n1 = ( n1>m_N-1) ? m_N-1 : n1;
n2 = ( n2>m_N-1) ? m_N-1 : n2;
if( n1 == n2 )
continue;
pSIaux = m_ppSI[n1];
m_ppSI[n1] = m_ppSI[n2];
m_ppSI[n2] = pSIaux;
}
}
//------------------------------------------------------------------------------
// Name: SetInitialParameters
// Purpose: calculates initial demonstration parameters for each media file --
// destination rectangles and alpha levels
// Note that these values are used as parameters in CDemonstration and
// that changing them can cause different appearence of the demonstration
//------------------------------------------------------------------------------
void CMediaList::SetInitialParameters()
{
NORMALIZEDRECT rectD;
double Alpha;
int i;
// set alpha levels and destination rectangles here
for( i=0; i< m_N; i++)
{
Alpha = 0.3 + 0.68 * (double)rand() / RAND_MAX; // random in [0.3; 0.98]
rectD.left = rectD.top = 0.1f;
rectD.right = rectD.bottom = 0.9f;
this->GetItem(i)->m_fAlpha = Alpha;
this->GetItem(i)->m_rD = rectD;
}// for
}
//------------------------------------------------------------------------------
// Name: Initialize
// Purpose: go through m_szMediaFolder and retrieve all media files into
// Parameters: none
// Return: true if folder contains at least one valid file;
// false otherewise
//------------------------------------------------------------------------------
bool CMediaList::Initialize(char *szFolder)
{
struct _finddata_t fileinfo;
long filehandle = -1L;
int nRes;
int nCounter = 0; // to prevent loading huge number of files,
// let's restrict it to 50
char szMask[MAX_PATH];
char szExt[] = "*.AVI;*.MOV;*.MPG;*.MPEG;*.VOB;*.QT;";
char szCurExt[MAX_PATH];
char szFilePath[MAX_PATH];
char *psz = NULL;
// clean the list
Clean();
if( !_strcmpi(szFolder,""))
return false;
do
{
strcpy(szCurExt,szExt);
psz = strstr(szCurExt,";");
if( psz)
{
*psz = 0;
psz = NULL;
psz = strstr( szExt, ";");
if( psz )
{
strcpy( szExt, psz+1);
}
}
else
{
strcpy( szExt, "");
}
sprintf(szMask, "%s%s", szFolder, szCurExt);
filehandle = _findfirst(szMask, &fileinfo);
if( filehandle == -1L)
continue;
SourceInfo * pSI = NULL;
pSI = new SourceInfo;
if( !pSI )
{
return false;
}
sprintf( szFilePath, "%s%s", szFolder, fileinfo.name);
strcpy( pSI->m_szPath, (const char*)szFilePath);
MultiByteToWideChar(CP_ACP, 0, (const char*)szFilePath, -1, pSI->m_wszPath, _MAX_PATH);
Add( pSI );
nCounter++;
nRes = _findnext(filehandle, &fileinfo);
while( -1L != nRes )
{
pSI = NULL;
pSI = new SourceInfo;
if( !pSI )
{
return false;
}
sprintf( szFilePath, "%s%s", szFolder,fileinfo.name);
strcpy( pSI->m_szPath, (const char*)szFilePath);
MultiByteToWideChar(CP_ACP, 0, (const char*)szFilePath, -1, pSI->m_wszPath, _MAX_PATH);
Add( pSI );
nCounter++;
nRes = _findnext(filehandle, &fileinfo);
}// while
} while( _strcmpi(szExt, "") && nCounter < 50 );
if( 0 == Size() )
{
return false;
}
else
{
return true;
}
}
//------------------------------------------------------------------------------
// Name: Clone
// Purpose: copies elements (nStart; nStart+n) to the list pML
// Parameters: n - number of elements
// pML - cloned media list
// nStart - start position in (this) list; default: 0
// Return: true if success;
// false otherewise
//------------------------------------------------------------------------------
bool CMediaList::Clone(int n, CMediaList *pML, int nStart /* = 0 */)
{
bool bRes = true;
if( n < 1 || nStart < 0 || nStart + n > m_N)
return false;
pML->Clean();
for(int i = nStart; i< nStart + n; i++)
{
SourceInfo *pSI = NULL;
pSI = new SourceInfo;
if( !pSI )
goto cleanup;
bRes = bRes && GetItem(i)->CopyTo( pSI);
if( false == bRes)
{
delete pSI;
goto cleanup;
}
pSI->m_bInUse = false;
bRes = bRes && pML->Add(pSI);
if( false == bRes)
goto cleanup;
}// for
return true;
cleanup:
pML->Clean();
return false;
}
//------------------------------------------------------------------------------
// Name: AdjustDuration
// Purpose: calculates demonstration time. Here, it is duration of the longest file
// Change this function to set a fixed time, average time etc.
//------------------------------------------------------------------------------
void CMediaList::AdjustDuration()
{
m_avgDuration = 0L;
if( 0 == m_N )
{
return;
}
for( int i=0; i<m_N; i++)
{
m_avgDuration = (this->GetItem(i)->m_llDuration > m_avgDuration) ?
this->GetItem(i)->m_llDuration :
m_avgDuration;
}// for
}

View File

@@ -0,0 +1,112 @@
//------------------------------------------------------------------------------
// File: SourceInfo.h
//
// Desc: DirectShow sample code
// Header file and class description for CMediaList,
// play-list of media files
//
// Copyright (c) 2000-2001 Microsoft Corporation. All rights reserved.
//------------------------------------------------------------------------------
#if !defined(AFX_SOURCEINFO_H__707CCC42_D3CC_40F1_B722_4E3ED3D7EAFF__INCLUDED_)
#define AFX_SOURCEINFO_H__707CCC42_D3CC_40F1_B722_4E3ED3D7EAFF__INCLUDED_
#if _MSC_VER > 1000
#pragma once
#endif // _MSC_VER > 1000
//////////////////////////////////////////////////////////////////////////////////////////
// Name: SourceInfo
// Purpose: this class describes properties of media file to be played by VMR
//////////////////////////////////////////////////////////////////////////////////////////
typedef struct SourceInfo
{
SourceInfo::SourceInfo() :
m_fAlpha(0.5f),
m_dwSeekingFlags(NULL),
m_fRate(1.0f),
m_llDuration(NULL)
{
m_rD.top = m_rD.left = 0.f;
m_rD.right = m_rD.bottom = 1.f;
strcpy( m_szPath, "");
MultiByteToWideChar(CP_ACP, 0, (const char*)m_szPath, -1, m_wszPath, _MAX_PATH);
};
SourceInfo::~SourceInfo()
{
};
bool CopyTo( SourceInfo* pSI)
{
if( !pSI )
{
return false;
}
strcpy( pSI->m_szPath, m_szPath);
MultiByteToWideChar(CP_ACP, 0, (const char*)m_szPath, -1, pSI->m_wszPath, _MAX_PATH);
pSI->m_dwSeekingFlags = m_dwSeekingFlags;
pSI->m_fAlpha = m_fAlpha;
pSI->m_fRate = m_fRate;
pSI->m_llDuration = m_llDuration;
pSI->m_rD = m_rD;
return true;
};
bool m_bInUse;
char m_szPath[MAX_PATH];
WCHAR m_wszPath[_MAX_PATH];
DWORD m_dwSeekingFlags;
double m_fAlpha;
double m_fRate;
LONGLONG m_llDuration;
NORMALIZEDRECT m_rD;
} SourceInfo;
//////////////////////////////////////////////////////////////////////////////////////////
// Name: CMediaList
// Purpose: List of SourceInfo objects; a storage of available media files
// to be played by VMR
//////////////////////////////////////////////////////////////////////////////////////////
class CMediaList
{
public:
CMediaList();
virtual ~CMediaList();
int Size(){ return m_N; };
SourceInfo * GetItem( int n)
{
return (n<0 || n>m_N-1) ? NULL : m_ppSI[n];
};
LONGLONG GetAvgDuration()
{
return (m_avgDuration);
};
const WCHAR * GetFileNameW( int n)
{
return (n>=0 && n<m_N) ? m_ppSI[n]->m_wszPath : NULL;
};
bool Add( SourceInfo * pSI);
bool Initialize(char *szFolder);
bool Clone(int n, CMediaList *pML, int nStart=0 );
void Clean();
void Shuffle();
void AdjustDuration();
void SetInitialParameters();
private:
int m_N;
SourceInfo ** m_ppSI;
LONGLONG m_avgDuration;
};
#endif // !defined(AFX_SOURCEINFO_H__707CCC42_D3CC_40F1_B722_4E3ED3D7EAFF__INCLUDED_)

View File

@@ -0,0 +1,8 @@
// stdafx.cpp : source file that includes just the standard includes
// VMRMix.pch will be the pre-compiled header
// stdafx.obj will contain the pre-compiled type information
#include "stdafx.h"

View File

@@ -0,0 +1,72 @@
//------------------------------------------------------------------------------
// File: Stdafx.h
//
// Desc: DirectShow sample code
// Include file for standard system include files or project-specific
// include files that are used frequently, but are changed infrequently.
//
// Copyright (c) 2000-2001 Microsoft Corporation. All rights reserved.
//------------------------------------------------------------------------------
#if !defined(AFX_STDAFX_H__62FCB452_013F_45F5_ADDE_C3314ACD44C9__INCLUDED_)
#define AFX_STDAFX_H__62FCB452_013F_45F5_ADDE_C3314ACD44C9__INCLUDED_
#if _MSC_VER > 1000
#pragma once
#endif // _MSC_VER > 1000
#define VC_EXTRALEAN // Exclude rarely-used stuff from Windows headers
#include <afxwin.h> // MFC core and standard components
#ifndef _AFX_NO_AFXCMN_SUPPORT
#include <afxcmn.h> // MFC support for Windows Common Controls
#endif // _AFX_NO_AFXCMN_SUPPORT
#if !defined(_WIN32_WINNT)
#define _WIN32_WINNT 0x0400
#endif
#define D3D_OVERLOADS
// included files
#pragma warning(push,3)
#include <streams.h>
#include <commdlg.h>
#include <stdlib.h>
#include <stdio.h>
#include <commctrl.h>
#include <strmif.h>
#include <combase.h>
#include <stdarg.h>
#include <stdio.h>
#include <io.h>
#include <uuids.h>
#pragma warning(pop)
#pragma warning(disable:4100 4189)
#include "resource.h"
#include "sourceinfo.h"
#include "VMRMixDlg.h"
#include "vmrcore.h"
#include "utils.h"
#define DllImport __declspec( dllimport )
// needed for the surface tests
DEFINE_GUID(IID_IDirectDraw7,
0x15e65ec0,0x3b9c,0x11d2,0xb9,0x2f,0x00,0x60,0x97,0x97,0xea,0x5b);
// various constants
const ULONG MAXFILTERS = 128;
#define FNS_PASS 0
#define FNS_FAIL 1
// macros
#define SAFERELEASE(punk) if (NULL != punk) (punk)->Release(), (punk) = NULL; else
//{{AFX_INSERT_LOCATION}}
// Microsoft Visual C++ will insert additional declarations immediately before the previous line.
#endif // !defined(AFX_STDAFX_H__62FCB452_013F_45F5_ADDE_C3314ACD44C9__INCLUDED_)

View File

@@ -0,0 +1,370 @@
//------------------------------------------------------------------------------
// File: Utils.h
//
// Desc: DirectShow sample code
// Helper functions
//
// Copyright (c) 2000-2001 Microsoft Corporation. All rights reserved.
//------------------------------------------------------------------------------
#include "stdafx.h"
#include "utils.h"
//-----------------------------------------------------------------------------------------
// Function: MyMessage
// Purpose: Displays a quick message box
// Arguments: Input strings that will be displayed
// Returns: button pushed in box
//-----------------------------------------------------------------------------------------*/
DWORD MyMessage(char *sQuestion, char *sTitle)
{
int iReturn = AfxMessageBox( sQuestion, MB_YESNO | MB_ICONQUESTION | MB_DEFBUTTON1);
return iReturn == IDYES ? FNS_PASS : FNS_FAIL;
}
//-----------------------------------------------------------------------------------------
// Function: hresultNameLookup
// Purpose: returns a string value for the given hresult
// Arguments: HRESULT that needs verifying
// Returns: string
//-----------------------------------------------------------------------------------------*/
const char * hresultNameLookup(HRESULT hres)
{
switch(hres)
{
case VFW_E_CANNOT_RENDER:
return "VFW_E_CANNOT_RENDER";
break;
case VFW_E_INVALID_FILE_FORMAT:
return "VFW_E_INVALID_FILE_FORMAT";
break;
case VFW_E_NOT_FOUND:
return "VFW_E_NOT_FOUND";
break;
case VFW_E_NOT_IN_GRAPH:
return "VFW_E_NOT_IN_GRAPH";
break;
case VFW_E_UNKNOWN_FILE_TYPE:
return "VFW_E_UNKNOWN_FILE_TYPE";
break;
case VFW_E_UNSUPPORTED_STREAM:
return "VFW_E_UNSUPPORTED_STREAM";
break;
case VFW_E_CANNOT_CONNECT:
return "VFW_E_CANNOT_CONNECT";
break;
case VFW_E_CANNOT_LOAD_SOURCE_FILTER:
return "VFW_E_CANNOT_LOAD_SOURCE_FILTER";
break;
case VFW_S_PARTIAL_RENDER:
return "VFW_S_PARTIAL_RENDER";
break;
case VFW_S_VIDEO_NOT_RENDERED:
return "VFW_S_VIDEO_NOT_RENDERED";
break;
case VFW_S_AUDIO_NOT_RENDERED:
return "VFW_S_AUDIO_NOT_RENDERED";
break;
case VFW_S_DUPLICATE_NAME:
return "VFW_S_DUPLICATE_NAME";
break;
case VFW_S_MEDIA_TYPE_IGNORED:
return "VFW_S_MEDIA_TYPE_IGNORED";
break;
case E_INVALIDARG:
return "E_INVALIDARG";
break;
case DDERR_INCOMPATIBLEPRIMARY:
return "DDERR_INCOMPATIBLEPRIMARY";
break;
case DDERR_INVALIDCAPS:
return "DDERR_INVALIDCAPS";
break;
case DDERR_INVALIDOBJECT :
return "DDERR_INVALIDOBJECT";
break;
case DDERR_INVALIDPIXELFORMAT:
return "DDERR_INVALIDPIXELFORMAT";
break;
case DDERR_NOALPHAHW :
return "DDERR_NOALPHAHW";
break;
case DDERR_NOCOOPERATIVELEVELSET :
return "DDERR_NOCOOPERATIVELEVELSET";
break;
case DDERR_NODIRECTDRAWHW :
return "DDERR_NODIRECTDRAWHW";
break;
case DDERR_NOEMULATION :
return "DDERR_NOEMULATION";
break;
case VFW_E_BUFFERS_OUTSTANDING:
return "VFW_E_BUFFERS_OUTSTANDING";
break;
case DDERR_NOEXCLUSIVEMODE :
return "DDERR_NOEXCLUSIVEMODE ";
break;
case DDERR_NOFLIPHW:
return "DDERR_NOFLIPHW";
break;
case DDERR_NOMIPMAPHW:
return "DDERR_NOMIPMAPHW";
break;
case DDERR_NOOVERLAYHW :
return "DDERR_NOOVERLAYHW ";
break;
case E_OUTOFMEMORY:
return "E_OUTOFMEMORY";
break;
case VFW_E_NO_DISPLAY_PALETTE:
return "VFW_E_NO_DISPLAY_PALETTE";
break;
case VFW_E_NO_COLOR_KEY_FOUND:
return "VFW_E_NO_COLOR_KEY_FOUND";
break;
case VFW_E_PALETTE_SET:
return "VFW_E_PALETTE_SET";
break;
case DDERR_NOZBUFFERHW :
return "DDERR_NOZBUFFERHW ";
break;
case DDERR_OUTOFVIDEOMEMORY :
return "DDERR_OUTOFVIDEOMEMORY";
break;
case DDERR_PRIMARYSURFACEALREADYEXISTS:
return "DDERR_PRIMARYSURFACEALREADYEXISTS ";
break;
case DDERR_UNSUPPORTEDMODE:
return "DDERR_UNSUPPORTEDMODE";
break;
case VFW_E_NO_ADVISE_SET:
return "VFW_E_NO_ADVISE_SET";
break;
case S_OK:
return "S_OK";
break;
case S_FALSE:
return "S_FALSE";
break;
case VFW_S_CONNECTIONS_DEFERRED:
return "VFW_S_CONNECTIONS_DEFERRED";
break;
case 0x80040154:
return "Class not registered";
break;
case E_FAIL:
return "E_FAIL";
break;
case VFW_E_DVD_OPERATION_INHIBITED:
return "VFW_E_DVD_OPERATION_INHIBITED";
break;
case VFW_E_DVD_INVALIDDOMAIN:
return "VFW_E_DVD_INVALIDDOMAIN";
break;
case E_NOTIMPL:
return "E_NOTIMPL";
break;
case VFW_E_WRONG_STATE:
return "VFW_E_WRONG_STATE";
break;
case E_PROP_SET_UNSUPPORTED:
return "E_PROP_SET_UNSUPPORTED";
break;
case VFW_E_NO_PALETTE_AVAILABLE:
return "VFW_E_NO_PALETTE_AVAILABLE";
break;
case E_UNEXPECTED:
return "E_UNEXPECTED";
break;
case VFW_E_DVD_NO_BUTTON:
return "VFW_E_DVD_NO_BUTTON";
break;
case VFW_E_DVD_GRAPHNOTREADY:
return "VFW_E_DVD_GRAPHNOTREADY";
break;
case VFW_E_NOT_OVERLAY_CONNECTION:
return "VFW_E_NOT_OVERLAY_CONNECTION";
break;
case VFW_E_DVD_RENDERFAIL:
return "VFW_E_DVD_RENDERFAIL";
break;
case VFW_E_NOT_CONNECTED:
return "VFW_E_NOT_CONNECTED";
break;
case E_NOINTERFACE:
return "E_NOINTERFACE";
break;
case VFW_E_NO_COLOR_KEY_SET :
return "VFW_E_NO_COLOR_KEY_SET ";
break;
case VFW_E_NO_INTERFACE:
return "VFW_E_NO_INTERFACE";
break;
case 0x8004020c:
return "VFW_E_BUFFER_NOTSET";
break;
case 0x80040225:
return "VFW_E_NOT_PAUSED";
case 0x80070002:
return "System cannot find the file specified";
break;
case 0x80070003:
return "System cannot find the path specified";
break;
case VFW_E_DVD_DECNOTENOUGH:
return "VFW_E_DVD_DECNOTENOUGH";
break;
case VFW_E_ADVISE_ALREADY_SET:
return "VFW_E_ADVISE_ALREADY_SET";
break;
case VFW_E_DVD_CMD_CANCELLED:
return "VFW_E_DVD_CMD_CANCELLED";
break;
case VFW_E_DVD_MENU_DOES_NOT_EXIST:
return "VFW_E_DVD_MENU_DOES_NOT_EXIST";
break;
case VFW_E_DVD_WRONG_SPEED:
return "VFW_E_DVD_WRONG_SPEED";
break;
case VFW_S_DVD_NON_ONE_SEQUENTIAL:
return "VFW_S_DVD_NON_ONE_SEQUENTIAL";
break;
case E_POINTER:
return "E_POINTER";
break;
case VFW_E_DVD_NOT_IN_KARAOKE_MODE:
return "VFW_E_DVD_NOT_IN_KARAOKE_MODE";
break;
case VFW_E_DVD_INVALID_DISC:
return "VFW_E_DVD_INVALID_DISC";
break;
case VFW_E_DVD_STREAM_DISABLED:
return "VFW_E_DVD_STREAM_DISABLED";
break;
case VFW_E_NOT_STOPPED:
return "VFW_E_NOT_STOPPED";
break;
default:
return "Unrecognized";
break;
}
}
//-----------------------------------------------------------------------------------------
// Function: MySleep
// Purpose: if the application is in automated mode, then sleep func is turned off
// Arguments: checks m_bAutomatedStatus to see if the func is in automation
// Returns: true if automated, false otherwist
//-----------------------------------------------------------------------------------------*/
bool MySleep(DWORD dwTime)
{
HANDLE hNeverHappensEvent;
hNeverHappensEvent = CreateEvent(NULL, FALSE, FALSE, "EVENTTHATNEVERHAPPENS");
WaitForSingleObject( hNeverHappensEvent, dwTime);
return false;
} // end of checkHResult method
//-----------------------------------------------------------------------------------------
// Function: ShellAbort
// Purpose: Prints a crash message text to the appropriate log(s)
// Arguments: none
// Returns: FNS_ABORTED
//-----------------------------------------------------------------------------------------*/
DWORD ShellAbort(CVMRCore *core)
{
AfxMessageBox("Unhandled exception, press OK to abort...");
exit(-1);
return NULL;
}
//-----------------------------------------------------------------------------------------
// Function: GetMessageName
// Purpose: Updates Name to the string version of the windows message
// Arguments: Name, long pointer to a string that will be updated
// msg - message id that we want displayed
//-----------------------------------------------------------------------------------------*/
void GetMessageName(LPSTR Name, UINT msg)
{
switch(msg)
{
// For put_MessageDrain and get_MessageDrain
case WM_KEYDOWN: lstrcpy(Name, "WM_KEYDOWN"); break;
case WM_KEYUP: lstrcpy(Name, "WM_KEYUP"); break;
case WM_LBUTTONDBLCLK: lstrcpy(Name, "WM_LBUTTONDBLCLK"); break;
case WM_LBUTTONDOWN: lstrcpy(Name, "WM_LBUTTONDOWN"); break;
case WM_LBUTTONUP: lstrcpy(Name, "WM_LBUTTONUP"); break;
case WM_MBUTTONDBLCLK: lstrcpy(Name, "WM_MBUTTONDBLCLK"); break;
case WM_MBUTTONDOWN: lstrcpy(Name, "WM_MBUTTONDOWN"); break;
case WM_MBUTTONUP: lstrcpy(Name, "WM_MBUTTONUP"); break;
case WM_MOUSEACTIVATE: lstrcpy(Name, "WM_MOUSEACTIVATE"); break;
case WM_MOUSEMOVE: lstrcpy(Name, "WM_MOUSEMOVE"); break;
case WM_NCHITTEST: lstrcpy(Name, "WM_NCHITTEST"); break;
case WM_NCLBUTTONDBLCLK: lstrcpy(Name, "WM_NCLBUTTONDBLCLK"); break;
case WM_NCLBUTTONDOWN: lstrcpy(Name, "WM_NCLBUTTONDOWN"); break;
case WM_NCLBUTTONUP: lstrcpy(Name, "WM_NCLBUTTONUP"); break;
case WM_NCMBUTTONDBLCLK: lstrcpy(Name, "WM_NCMBUTTONDBLCLK"); break;
case WM_NCMBUTTONDOWN: lstrcpy(Name, "WM_NCMBUTTONDOWN"); break;
case WM_NCMBUTTONUP: lstrcpy(Name, "WM_NCMBUTTONUP"); break;
case WM_NCMOUSEMOVE: lstrcpy(Name, "WM_NCMOUSEMOVE"); break;
case WM_NCRBUTTONDBLCLK: lstrcpy(Name, "WM_NCRBUTTONDBLCLK"); break;
case WM_NCRBUTTONDOWN: lstrcpy(Name, "WM_NCRBUTTONDOWN"); break;
case WM_NCRBUTTONUP: lstrcpy(Name, "WM_NCRBUTTONUP"); break;
case WM_RBUTTONDBLCLK: lstrcpy(Name, "WM_RBUTTONDBLCLK"); break;
case WM_RBUTTONDOWN: lstrcpy(Name, "WM_RBUTTONDOWN"); break;
case WM_RBUTTONUP: lstrcpy(Name, "WM_RBUTTONUP"); break;
// For NotifyOwnerMessage
case WM_DEVMODECHANGE: lstrcpy(Name,"WM_DEVMODECHANGE"); break;
case WM_DISPLAYCHANGE: lstrcpy(Name,"WM_DISPLAYCHANGE"); break;
case WM_MOVE: lstrcpy(Name,"WM_MOVE"); break;
case WM_PALETTECHANGED: lstrcpy(Name,"WM_PALETTECHANGED"); break;
case WM_PALETTEISCHANGING: lstrcpy(Name,"WM_PALETTEISCHANGING"); break;
case WM_QUERYNEWPALETTE: lstrcpy(Name,"WM_QUERYNEWPALETTE"); break;
case WM_SYSCOLORCHANGE: lstrcpy(Name,"WM_SYSCOLORCHANGE"); break;
default: wsprintf(Name, "Unknown Messgage %u", msg);
}
return;
}
/*****************************Private*Routine******************************\
* VerifyVMR
*
\**************************************************************************/
BOOL VerifyVMR(void)
{
HRESULT hres;
CoInitialize(NULL);
// Verify that the VMR exists on this system
IBaseFilter* pBF = NULL;
hres = CoCreateInstance(CLSID_VideoMixingRenderer,
NULL,
CLSCTX_INPROC,
IID_IBaseFilter,
(LPVOID *)&pBF);
if(SUCCEEDED(hres))
{
pBF->Release();
CoUninitialize();
return TRUE;
}
else
{
MessageBox(NULL,
TEXT("This application requires the Video Mixing Renderer, which is present\r\n")
TEXT("only on Windows XP.\r\n\r\n")
TEXT("The Video Mixing Renderer (VMR) is also not enabled when viewing a \r\n")
TEXT("remote Windows XP machine through a Remote Desktop session.\r\n")
TEXT("You can run VMR-enabled applications only on your local machine.")
TEXT("\r\n\r\nThis sample will now exit."),
TEXT("Video Mixing Renderer capabilities are required"), MB_OK);
CoUninitialize();
return FALSE;
}
}

View File

@@ -0,0 +1,25 @@
//------------------------------------------------------------------------------
// File: Utils.h
//
// Desc: DirectShow sample code
// Helper function prototypes
//
// Copyright (c) 2000-2001 Microsoft Corporation. All rights reserved.
//------------------------------------------------------------------------------
#if !defined(UTILS_H)
#define UTILS_H
#include "stdafx.h"
// helper function prototypes
DWORD MyMessage(char *sQuestion, char *sTitle);
DWORD ShellAbort(CVMRCore *core);
const char * hresultNameLookup(HRESULT hres);
bool MySleep(DWORD dwTime = 2500);
void GetMessageName(LPSTR Name, UINT msg);
#endif

View File

@@ -0,0 +1,972 @@
//------------------------------------------------------------------------------
// File: VMRCore.h
//
// Desc: DirectShow sample code
// Header file and class description for CVMRCore,
// "main" module to manage VMR and its interfaces
// This class is called from CDemonstration;
//
// Copyright (c) 2000-2001 Microsoft Corporation. All rights reserved.
//------------------------------------------------------------------------------
#include "stdafx.h"
#include <objbase.h>
#include "resource.h"
//////////////////////////////////////////////////////////////////////
// Construction/Destruction
//////////////////////////////////////////////////////////////////////
DWORD WINAPI WndlessControlThread(LPVOID lpvThreadParam);
CVMRCore::CVMRCore(CVMRMixDlg * pDlg, // pointer to the 'parent' dialog
CMediaList * pML) : // media play-list
m_tID(NULL),
m_hEventResumeCore(NULL),
m_hEventStopTest(NULL),
m_hEventCloseWindow(NULL),
m_hEventKillCore(NULL),
m_hWinThread(NULL),
m_pDlg(pDlg),
m_pMixerBitmap(NULL),
m_pML(pML),
m_pIMediaSeeking(NULL),
m_pIMixerControl(NULL),
m_nConnectedPins(0),
m_pIMonConfig(NULL),
m_hwnd(NULL),
m_pIMC(NULL),
m_pIVidWindow(NULL),
m_pIWndless(NULL),
m_dwVMRMode(NULL),
m_dwVMRPrefs(NULL),
m_pConfig(NULL),
m_pGraph(NULL),
m_pTestFilter(NULL),
m_lpDestRect(NULL),
m_lpSrcRect(NULL)
{
// by default, set windowless mode and allow overlays
m_dwVMRMode = VMRMode_Windowless;
m_dwVMRPrefs = RenderPrefs_AllowOverlays;
m_dwID = (DWORD) rand();
sprintf( m_szEventStopTest, "STOP_TEST_%ld", m_dwID);
sprintf( m_szEventCloseWindow, "CLOSE_WINDOW_%ld", m_dwID);
sprintf( m_szEventKillCore, "KILL_CORE_%ld", m_dwID);
sprintf( m_szEventResumeCore, "RESUME_CORE_%ld", m_dwID);
m_hEventResumeCore = CreateEvent(NULL, FALSE, FALSE, m_szEventResumeCore);
m_hEventCloseWindow = CreateEvent(NULL, FALSE, FALSE, m_szEventCloseWindow);
m_hEventKillCore = CreateEvent(NULL, FALSE, FALSE, m_szEventKillCore);
m_hEventStopTest = CreateEvent(NULL, FALSE, FALSE, m_szEventStopTest);
CoInitializeEx(NULL, COINIT_MULTITHREADED);
}
//------------------------------------------------------------------------------
CVMRCore::CVMRCore( CVMRMixDlg * pDlg, // 'parent dialog
DWORD dwVMRMode, // rendering mode
DWORD dwVMRPrefs, // rendering preferences
CMediaList * pML) : // play-list
m_tID(NULL),
m_hEventStopTest(NULL),
m_hEventCloseWindow(NULL),
m_hEventKillCore(NULL),
m_pDlg(pDlg),
m_pMixerBitmap(NULL),
m_pML( pML),
m_pIMediaSeeking(NULL),
m_pIMixerControl(NULL),
m_nConnectedPins(0),
m_hEventResumeCore(NULL),
m_hWinThread(NULL),
m_pIMonConfig(NULL),
m_hwnd(NULL),
m_pIMC(NULL),
m_pIVidWindow(NULL),
m_pIWndless(NULL),
m_dwVMRMode(NULL),
m_dwVMRPrefs(NULL),
m_pConfig(NULL),
m_pGraph(NULL),
m_pTestFilter(NULL),
m_lpDestRect(NULL),
m_lpSrcRect(NULL)
{
(dwVMRPrefs) ? (m_dwVMRPrefs = dwVMRPrefs)
:(m_dwVMRPrefs = RenderPrefs_AllowOverlays);
(dwVMRMode) ? (m_dwVMRMode = dwVMRMode)
: (m_dwVMRMode = VMRMode_Windowless);
m_dwID = (DWORD) rand();
sprintf( m_szEventStopTest, "STOP_TEST_%ld", m_dwID);
sprintf( m_szEventCloseWindow, "CLOSE_WINDOW_%ld", m_dwID);
sprintf( m_szEventKillCore, "KILL_CORE_%ld", m_dwID);
sprintf( m_szEventResumeCore, "RESUME_CORE_%ld", m_dwID);
m_hEventResumeCore = CreateEvent(NULL, FALSE, FALSE, m_szEventResumeCore);
m_hEventCloseWindow = CreateEvent(NULL, FALSE, FALSE, m_szEventCloseWindow);
m_hEventKillCore = CreateEvent(NULL, FALSE, FALSE, m_szEventKillCore);
m_hEventStopTest = CreateEvent(NULL, FALSE, FALSE, m_szEventStopTest);
CoInitializeEx(NULL, COINIT_MULTITHREADED);
}
//------------------------------------------------------------------------------
CVMRCore::~CVMRCore()
{
ReleaseInterfaces();
CloseHandle(m_hEventResumeCore);
CloseHandle(m_hEventStopTest);
CloseHandle(m_hEventKillCore);
CloseHandle(m_hWinThread);
CoUninitialize();
}
//------------------------------------------------------------------------------
// CreateGraph
// Desc: Creates a valid filter graph for VMR
// Returns: S_OK if everything succeeds, else the hresult
// returned by the API called that failed
//------------------------------------------------------------------------------
HRESULT CVMRCore::CreateGraph()
{
// keeps track of any nonessential initializations
HRESULT hrInit = S_OK;
int ncount; // counter for media files from the play list
// graph has already been successfully created
if (m_pGraph)
{
return S_FALSE;
}
HRESULT hr;
// get the graph interface
hr = CoCreateInstance(CLSID_FilterGraph, NULL, CLSCTX_INPROC_SERVER, IID_IGraphBuilder,
reinterpret_cast<void**>(&m_pGraph));
if (FAILED(hr))
{
return hr;
}
// add VMR (called 'Default Video Renderer' in WindowsXP)
hr = AddTestFilter();
if (FAILED(hr))
{
OutputDebugString("Couldn't add the Test Filter to the Graph\n");
goto cleanup;
}
// convert filename from module to unicode and render
if( m_pML->Size() < 1)
{
OutputDebugString("There is nothing to render!\n");
goto cleanup;
}
// Render the files
for( ncount =0; ncount < m_pML->Size(); ncount++)
{
hr = m_pGraph->RenderFile(m_pML->GetFileNameW(ncount), NULL);
if (FAILED(hr))
{
char szMsg[MAX_PATH];
sprintf( szMsg, "Error while rendering file, method returned %s\n",
hresultNameLookup(hr) );
OutputDebugString( szMsg);
continue;
}
m_pML->GetItem(ncount)->m_bInUse = true;
m_nConnectedPins++;
}
if( FAILED(hr))
{
goto cleanup;
}
// verify that there is only one renderer in the graph
if (!ListFilters())
{
OutputDebugString("There is more than one renderer in the graph.\n");
hr = E_FAIL;
goto cleanup;
}
// get the media control so we can play
hr = m_pGraph->QueryInterface(IID_IMediaControl, reinterpret_cast<void**>(&m_pIMC));
if (FAILED(hr))
{
OutputDebugString("Couldn't get IMediaControl interface!\n");
goto cleanup;
}
// now that file is rendered, initialize the appropriate interfaces
hr = InitRelevantInterfaces();
if (FAILED(hr))
{
OutputDebugString("Not all interfaces were initialized.\n");
hrInit = S_FALSE;
}
// create the window for the windowless control if needed
if (m_dwVMRMode & VMRMode_Windowless)
{
// if windowless mode is desired, the window needs to be setup
CreateWindowlessWindow();
// only applicable for windoless control
hr = m_pIWndless->SetVideoClippingWindow(m_hwnd);
if (FAILED(hr))
{
OutputDebugString("Error while setting the Video Clipping Window\n");
goto cleanup;
}
} // if (m_dwVMRMode & VMRMode_Windowless)
return hrInit;
cleanup:
// if we fail, release interfaces
SAFERELEASE(m_pGraph);
SAFERELEASE(m_pTestFilter);
return hr;
}
//------------------------------------------------------------------------------
// AddTestFilter
// Desc: Adds the VMR to the graph
// Returns: S_OK if the filter is added, otherwise the corresponding
// DShow COM error
//------------------------------------------------------------------------------
HRESULT CVMRCore::AddTestFilter()
{
HRESULT hr = CoCreateInstance(CLSID_VideoMixingRenderer, NULL, CLSCTX_INPROC_SERVER, IID_IBaseFilter,
reinterpret_cast<void**>(&m_pTestFilter));
if (FAILED(hr))
{
OutputDebugString("Couldn't load VideoMixingRenderer Filter\n");
return hr;
}
// now add this filter to the graph
// add the VMR to the filter graph
hr = m_pGraph->AddFilter(m_pTestFilter, L"Default Video Renderer");
if (FAILED(hr))
{
OutputDebugString("Couldn't add Video Mixing Renderer Filter to the graph\n");
SAFERELEASE(m_pTestFilter);
return hr;
}
// make dynamic reconnection possible
IGraphConfig * pIGraphConfig = NULL;
hr = m_pGraph->QueryInterface( __uuidof(IGraphConfig), (LPVOID *) &pIGraphConfig);
if( SUCCEEDED(hr) )
{
hr = pIGraphConfig->SetFilterFlags(m_pTestFilter, AM_FILTER_FLAGS_REMOVABLE);
}
SAFERELEASE( pIGraphConfig );
// the VMR requires certain setup procedures:
// first get the pin config interface (that is IVMRFilterConfig and
// set up the initialization settings for the VMR
hr = m_pTestFilter->QueryInterface(__uuidof(IVMRFilterConfig), reinterpret_cast<void**>(&m_pConfig));
if (FAILED(hr))
{
OutputDebugString("Couldn't get IVMRFilterConfig interface\n");
return hr;
}
// We MUST set the number of streams first
// it sets VMR to mixing or non-mixing mode.
// By specifying SetNumberOfStreams(1) we guarantee that the came copy
// of the rendering filter will be used when rendering several sources
int nSources;
nSources = (m_pML->Size() >1) ? 16 : 1;
hr = m_pConfig->SetNumberOfStreams(nSources);
if (FAILED(hr))
{
OutputDebugString("Couldn't Set the number of streams.\n");
return hr;
}
// now set the rendering mode
hr = m_pConfig->SetRenderingMode(m_dwVMRMode);
if (FAILED(hr))
{
OutputDebugString("Failed to set the rendering mode\n");
return hr;
}
// now set the preferences
hr = m_pConfig->SetRenderingPrefs(m_dwVMRPrefs);
if (FAILED(hr))
{
char szMsg[MAX_PATH];
sprintf( szMsg, "hr = %s\n", hresultNameLookup(hr));
OutputDebugString( szMsg);
OutputDebugString("Error while setting rendering preferences!\n");
OutputDebugString("Attempting to continue rendering file\n");
}
return S_OK;
}
//------------------------------------------------------------------------------
// InitRelevantInterfaces
// Desc: QIs for all the interfaces that are appropriate
// Returns: S_OK if the all of the relevant interfaces are gotten
// correctly
// Notes: This method also verifies which mode the VMR is in
// and if it needs a window created that will be
// by the windowless control
//------------------------------------------------------------------------------
HRESULT CVMRCore::InitRelevantInterfaces()
{
HRESULT hr = E_FAIL;
HRESULT hrComplete = S_OK;
if (m_dwVMRMode & VMRMode_Windowless)
{
hr = m_pTestFilter->QueryInterface(__uuidof(IVMRWindowlessControl),
reinterpret_cast<void**>(&m_pIWndless));
if (FAILED(hr))
{
OutputDebugString("Couldn't get IVMRWindowlessControl interface\n");
hrComplete = hr;
}
// now that the interface is ready, place the video on the screen
RECT rect;
if( !m_hwnd )
{
CreateWindowlessWindow();
}
ASSERT( m_hwnd);
GetClientRect(m_hwnd, &rect);
hr = m_pIWndless->SetVideoPosition(NULL, &rect);
} // if mode is windowless
hr = m_pTestFilter->QueryInterface(__uuidof(IVMRMonitorConfig),
reinterpret_cast<void**>(&m_pIMonConfig));
if (FAILED(hr))
{
OutputDebugString("Couldn't get IVMRMonitorConfig interface\n");
return hr;
}
hr = m_pTestFilter->QueryInterface( __uuidof(IVMRMixerControl), (LPVOID *) &m_pIMixerControl ) ;
if( FAILED(hr))
{
OutputDebugString("Cannot find IVMRMixerControl interface\n");
return hr;
}
hr = m_pTestFilter->QueryInterface( __uuidof(IVMRMixerBitmap), (LPVOID *) &m_pMixerBitmap ) ;
if( FAILED(hr))
{
OutputDebugString("Cannot find IVMRMixerBitmap interface\n");
return hr;
}
hr = GetIGraphBuilder()->QueryInterface(__uuidof(IMediaSeeking), reinterpret_cast<void**>(&m_pIMediaSeeking));
if( FAILED(hr))
{
OutputDebugString("Cannot find IMediaSeeking interface\n");
return hr;
}
hr = m_pGraph->QueryInterface(IID_IVideoWindow,
reinterpret_cast<void**>(&m_pIVidWindow));
if (FAILED(hr))
{
OutputDebugString("Couldn't get IVideoWindow interface\n");
hrComplete = hr;
}
return hrComplete;
}
//------------------------------------------------------------------------------
// Function: Play
// Desc: Begins to play the core video, checks for window initiziation
// Parameter: bool bDoNotRunYet, if true, then do not run IMediaControl
// Returns: HRESULT returned by the the MediaControlers call to run
// Note: We catch all unhandled exceptions here
//------------------------------------------------------------------------------
HRESULT CVMRCore::Play(bool bDoNotRunYet /* = false */)
{
try
{
HRESULT hr = S_OK;
// if there is no media control interface, get it created
// return successfully with the graph running or the error
if (!m_pIMC)
hr = CreateGraph();
if( bDoNotRunYet )
{
return hr;
}
hr = (SUCCEEDED(hr)) ? m_pIMC->Run() : hr;
return hr;
} // try
catch (HRESULT hr)
{
if (hr == E_FAIL)
{
OutputDebugString("Unhandled exception in CVMRCore::Play\n");
SetAbort();
return E_FAIL;
}
}
catch(...)
{
SetAbort();
return E_FAIL;
}
return S_OK;
}
//------------------------------------------------------------------------------
// Function: Pause
// Purpose: Begins the core video paused, checks for window initiziation
// Returns: HRESULT returned by the the MediaControlers call to run
// Note: We catch all unhandled exceptions here
//------------------------------------------------------------------------------
HRESULT CVMRCore::Pause()
{
try
{
HRESULT hr = S_OK;
// if there is no media control interface, get it created
// return successfully with the graph running or the error
if (!m_pIMC)
hr = CreateGraph();
return (SUCCEEDED(hr)) ? m_pIMC->Pause() : hr;
} // try
catch (HRESULT hr)
{
if (hr == E_FAIL)
{
OutputDebugString("Failed to pause the graph.\n");
SetAbort();
return E_FAIL;
}
}
catch(...)
{
SetAbort();
return E_FAIL;
}
return S_OK;
}
//------------------------------------------------------------------------------
// Function: Stop
// Purpose: Begins to the core video stopped, checks for window initiziation
// Returns: HRESULT returned by the the MediaControlers call to run
// Note: We catch all unhandled exceptions here
//------------------------------------------------------------------------------
HRESULT CVMRCore::Stop()
{
try
{
HRESULT hr = S_OK;
// if there is no media control interface, get it created
// return successfully with the graph running or the error
if (!m_pIMC)
hr = CreateGraph();
return (SUCCEEDED(hr)) ? m_pIMC->Stop() : hr;
} // try
catch (HRESULT hr)
{
if (hr == E_FAIL)
{
OutputDebugString("Failed to stop the graph.\n");
SetAbort();
return E_FAIL;
}
}
catch(...)
{
SetAbort();
return E_FAIL;
}
return S_OK;
}
//------------------------------------------------------------------------------
// ReleaseInterfaces
// Desc: Releases the IUnknown interfaces for all member variable
// interfaces created by this object
//------------------------------------------------------------------------------
void CVMRCore::ReleaseInterfaces()
{
// close the window if it exists
KillWindow();
SAFERELEASE(m_pMixerBitmap);
SAFERELEASE(m_pIMediaSeeking);
SAFERELEASE(m_pIMixerControl);
SAFERELEASE(m_pIMonConfig);
SAFERELEASE(m_pIWndless);
SAFERELEASE(m_pConfig);
SAFERELEASE(m_pIMC);
SAFERELEASE(m_pTestFilter);
SAFERELEASE(m_pGraph);
SAFERELEASE(m_pIVidWindow);
}
//------------------------------------------------------------------------------
// IsActive
// Desc: checks if VMRCore is active
// return: false if m_hEventKillCore is set (user closes the window);
// true otherwise
//------------------------------------------------------------------------------
bool CVMRCore::IsActive()
{
DWORD dwRes = NULL;
dwRes = WaitForSingleObject( m_hEventKillCore, 10);
if( WAIT_OBJECT_0 != dwRes)
{
return true;
}
else
{
return false;
}
}
//------------------------------------------------------------------------------
// ListFilters
// Desc: Logs to the debugger output the filters in our created filter graph
// Returns: true if one VMR filter was found; false otherwise
//------------------------------------------------------------------------------
bool CVMRCore::ListFilters()
{
if (m_pGraph)
{
IEnumFilters * ppEnum;
ULONG cFilters, cFetched;
IBaseFilter *ppFilter[MAXFILTERS];
FILTER_INFO pInfo;
HRESULT hr;
char sLogBuffer[MAX_PATH];
int iRendererCount = 0;
char buffer[MAX_PATH];
// get pointer to list of filters in graph
hr = m_pGraph->EnumFilters(&ppEnum);
cFilters = MAXFILTERS; // number of filters to retrieve
hr = ppEnum->Next(cFilters, &(ppFilter[0]), &cFetched);
sprintf(buffer, "Filter List (%d found): \n", cFetched);
OutputDebugString(buffer);
for (UINT i = 0; i < cFetched; i++)
{
//get, covert and display filter name
ppFilter[i]->QueryFilterInfo(&pInfo);
WideCharToMultiByte(CP_ACP, 0, pInfo.achName, -1, buffer, MAX_PATH, NULL, NULL);
// keep count of renderers to throw an exception when there is more than
// one renderer
if (IsRenderer(buffer))
iRendererCount++;
if( 2 == iRendererCount )
{
// with some cards, a glitch can occur and there will be several
// VMR filters in the same graph. Here, we try to prevent it
// (okay, if you do not like the line below, go trough the graph
// and reconnect all the spources to one VMR)
hr = m_pGraph->RemoveFilter(ppFilter[i]);
if(FAILED(hr))
{
iRendererCount--;
}
}// if
sprintf(sLogBuffer, "(%d) = %s\n", i+1 , buffer);
OutputDebugString(sLogBuffer);
// release any IUnknowns that were addrefed by successful calls of Enum and Query
SAFERELEASE(pInfo.pGraph);
SAFERELEASE(ppFilter[i]);
} // for
SAFERELEASE(ppEnum);
// if more than one renderer is present, the wrong renderer may get tested
if (iRendererCount > 1)
return false;
return true;
} // if m_pGraph
return false;
} // ListFilters
//------------------------------------------------------------------------------
// CreateWindowlessWindow
// Desc: Creates the events and thread that will handle the windowless control's
// playback window
// Returns: S_OK when the thread is completed
//------------------------------------------------------------------------------
HRESULT CVMRCore::CreateWindowlessWindow()
{
if( NULL != m_hwnd)
{
return E_INVALIDARG;
}
// spin off and create the playback window on another thread so that
// it will have its own message pump so that any messages that the
// VMR is supposed to be handled can be set
m_hWinThread = CreateThread(NULL, NULL, WndlessControlThread, this, NULL, &m_tID);
::WaitForSingleObject(m_hEventResumeCore, INFINITE);
return S_OK;
}
//------------------------------------------------------------------------------
// WndlessControlThread
// Desc: Thread code that creates a playback window for the VMR
// Arguments: Pointer to thread paramters in this case a structure holding the hwnd and
// a pointer to the core object that is calling it.
// Returns: S_OK when the thread is completed
// Remarks: Requires a call to the core's KillThread so that
// this thread will end!
//------------------------------------------------------------------------------
DWORD WINAPI WndlessControlThread(LPVOID lpvThreadParam)
{
// passed a to the thread
CVMRCore * pCore = static_cast<CVMRCore *>(lpvThreadParam);
HWND hwnd;
if( !pCore )
{
return NULL;
}
// this code will create the window and run the windows proc for each test
// each test will be on its own thread
// register playback window
WNDCLASSEX wndclass = {
sizeof(WNDCLASSEX),
CS_HREDRAW * CS_VREDRAW,
CVMRCore::WndProc,
0,
0,
AfxGetInstanceHandle(),
LoadIcon(AfxGetInstanceHandle(), MAKEINTRESOURCE(IDR_MAINFRAME)),
LoadCursor(NULL, IDC_ARROW),
HBRUSH(COLOR_WINDOW+1),
NULL,
TEXT("EventWindow"),
NULL
};
RegisterClassEx(&wndclass);
// create the playback window
// it is always in dlg client coordinates
RECT rPlayback;
int cx = GetSystemMetrics(SM_CXFULLSCREEN);
int cy = GetSystemMetrics(SM_CYFULLSCREEN);
if( !pCore->GetDlg()->IsFullScreen())
{
cx /=4;
cy /=4;
}
rPlayback.left = 0;
rPlayback.top = 0;
rPlayback.right = cx;
rPlayback.bottom = cy;
// need to update member variable of class with this
hwnd = CreateWindow(
TEXT("EventWindow"),
TEXT("VMRMix Playback Window"),
WS_OVERLAPPEDWINDOW | WS_MAXIMIZE,
rPlayback.left,
rPlayback.top,
rPlayback.right - rPlayback.left,
rPlayback.bottom - rPlayback.top,
NULL,
NULL,
AfxGetInstanceHandle(),
pCore); // we send the this pointer here so we can retrieve it from WM_CREATE later
SetWindowLongPtr(hwnd, GWLP_USERDATA, reinterpret_cast<LONG_PTR>(pCore));
// for the windowless controls clipping window
pCore->SetHwnd(hwnd);
ShowWindow(hwnd , SW_SHOWNORMAL);
UpdateWindow(hwnd ) ;
// set an event here so that our other thread can continue now that the window is created
HANDLE hCoreEvent = ::OpenEvent(EVENT_ALL_ACCESS, NULL, pCore->m_szEventResumeCore);
SetEvent(hCoreEvent);
CloseHandle(hCoreEvent);
// now run a message loop so that this thread will not die
MSG msg;
HANDLE hTestOverEvent = ::OpenEvent(EVENT_ALL_ACCESS, NULL, pCore->m_szEventStopTest);
HANDLE hWindowClose = ::OpenEvent(EVENT_ALL_ACCESS, NULL, pCore->m_szEventCloseWindow);
while (WAIT_OBJECT_0 != WaitForSingleObject(hTestOverEvent, 1000))
{
OutputDebugString("WndlessControlThread:: Inside while Wait(hTestOverEvent)\n");
while (::PeekMessage(&msg, NULL, 0, 0, 0))
{
OutputDebugString("WndlessControlThread:: Inside while (::PeekMessage\n");
MSG msgCur;
if (!::GetMessage(&msgCur, NULL, NULL, NULL)) // the quit message came
{
::PostQuitMessage(0);
break;
}
::TranslateMessage(&msgCur);
::DispatchMessage(&msgCur);
} ///while peeke
}// while wait
// trigger remaining events and close all locally opened handles
SetEvent(hWindowClose);
CloseHandle(hWindowClose);
CloseHandle(hTestOverEvent);
return S_OK;
}
//------------------------------------------------------------------------------
// WndProc
// Desc: Window procedure for multithreaded implementation
// Returns: LRESULT
//------------------------------------------------------------------------------
LRESULT CALLBACK CVMRCore::WndProc(HWND hWnd, UINT uMessage, WPARAM wParam, LPARAM lParam)
{
// retrieve the pointer to the instance of CVMRCore that this window belongs to
// because WndProc is a static method, it doesn't have a this pointer
CVMRCore * pCore = NULL;
BOOL bRetVal = false;
pCore = reinterpret_cast<CVMRCore *>(GetWindowLongPtr(hWnd, GWLP_USERDATA));
if( !pCore )
{
return DefWindowProc(hWnd, uMessage, wParam, lParam);
}
switch (uMessage)
{
case WM_CREATE:
return 0;
case WM_SIZE:
return pCore->OnSize(wParam, lParam);
case WM_PAINT:
return pCore->OnPaint(hWnd);
case WM_CLOSE:
OutputDebugString("message WM_CLOSE obtained by CVMRCore::WndProc\n");
return pCore->KillWindow();
case WM_DESTROY:
PostQuitMessage(-1);
return (0);
}
return DefWindowProc(hWnd, uMessage, wParam, lParam);
}
//------------------------------------------------------------------------------
// KillWindow
// Desc: Sets the event when multithreaded that the playback thread may close the
// playback window
//------------------------------------------------------------------------------
LRESULT CVMRCore::KillWindow()
{
if( m_pIMC)
{
m_pIMC->Stop();
}
if( !SetEvent( m_hEventStopTest ))
{
DWORD dwRes = GetLastError();
OutputDebugString("KillWindow::Failed to set event m_hEventStopTest\n");
}
else
{
OutputDebugString("KillWindow::Event m_hEventStopTest is set\n");
}
if( this->m_hWinThread )
{
if( !PostThreadMessage(m_tID, WM_QUIT, NULL, NULL) )
{
DWORD dwRes = GetLastError();
}
}
SetEvent( m_hEventKillCore );
OutputDebugString("KillWindow::m_hEventKillCore is set ...\n");
return 0;
}
//------------------------------------------------------------------------------
// Function: OnSize
// Purpose: Resets the video in the newly sized window
// Arguments: lParam - height and width of the window
// wparam - type of resizing requested
// Returns: Nothing
//------------------------------------------------------------------------------
LRESULT CVMRCore::OnSize(LPARAM lParam, WPARAM wParam)
{
SetClientVideo();
return 0;
}
//------------------------------------------------------------------------------
// Function: SetClientVideo
// Purpose: Sets the video position to the current client area size of the playback
// window if the m_lpSrcRect and m_lpDestRect have been given valid values.
// Arguments: None
// Returns: True if the rectangles have been initialized, false if the client
// window's default size is used
// Notes: One might wish to post a WM_PAINT message since this code will reset
// any source and destination changes to the windowless control
//------------------------------------------------------------------------------
bool CVMRCore::SetClientVideo()
{
if ( m_pIWndless)
{
// both of the rectangles have been set
if (m_lpSrcRect && m_lpDestRect)
{
HRESULT hr = m_pIWndless->SetVideoPosition(m_lpSrcRect, m_lpDestRect);
ASSERT(SUCCEEDED(hr));
return true;
}
}
RECT rect;
// reset video window, this will change any previous settings
GetClientRect(m_hwnd, &rect);
ASSERT(m_pIWndless);
if (m_pIWndless)
HRESULT hr = m_pIWndless->SetVideoPosition(NULL, &rect);
return false;
}
//------------------------------------------------------------------------------
// Function: SetAbort
// Purpose: emergency abort
// Other: Alerts the module to not allow any more test to be executed
//------------------------------------------------------------------------------
void CVMRCore::SetAbort()
{
// an unhandled exception has been thrown
ReleaseInterfaces();
}
//------------------------------------------------------------------------------
// Function: OnPaint
// Purpose: Paints the playback window's client area
// Arguments: hWnd of the client window
//------------------------------------------------------------------------------
LRESULT CVMRCore::OnPaint(HWND hWnd)
{
if (NULL == m_pIWndless)
return 0;
RECT rect;
GetClientRect(m_hwnd, &rect);
PAINTSTRUCT ps;
HDC hdc;
hdc = BeginPaint(hWnd, &ps);
HRESULT hr = m_pIWndless->RepaintVideo(hWnd, hdc);
if(!SUCCEEDED(hr))
{
char szMsg[MAX_PATH];
sprintf( szMsg, "%s", hresultNameLookup(hr));
}
EndPaint(hWnd, &ps);
return 0;
}
//------------------------------------------------------------------------------
// Function: GetClientHwnd
// Purpose: Access to the private core's client's hwnd
// Returns: handle to the renderer's playback controlling window
//------------------------------------------------------------------------------
HWND CVMRCore::GetClientHwnd()
{
// we may have already set this up in windowless control
if (m_hwnd)
return m_hwnd;
HWND hwnd; // handle to the window we are looking for
TCHAR buffer[MAX_PATH];
hwnd = GetTopWindow(NULL);
while (hwnd)
{
// get title bar's window and compare
if (GetWindowText(hwnd, buffer, MAX_PATH))
{
// old renderer, windowed mode of VMR
if (!strcmp(buffer, "ActiveMovie Window"))
break; // title found save use hwnd
if (!strcmp(buffer, "Windowless Control"))
break;
} //
hwnd = GetNextWindow(hwnd, GW_HWNDNEXT);
} // while
if (!hwnd)
{
OutputDebugString("Could not find window handle for playback window\n");
return NULL;
}
m_hwnd = hwnd;
return m_hwnd;
}
//------------------------------------------------------------------------------
// Function: IsRenderer
// Purpose: Defines if a given filter is a video renderer
// Arguments: strFilterName - NON wide string pointer that holds
// the name of the filter being checked
// Returns: true if the filter name is a filter that is being sought, false otherwise
// Other: This function can be useful because sometimes with some videocards
// several copies of VMR appear in the same graph.
// Name 'Video renderer' corresponds to older version of venderer
//------------------------------------------------------------------------------
bool CVMRCore::IsRenderer(char *strFilterName)
{
if (!strncmp(strFilterName, "Video Mixing", 12))
return true;
if (!strncmp(strFilterName, "Video Render", 12))
return true;
return false;
}

View File

@@ -0,0 +1,119 @@
//------------------------------------------------------------------------------
// File: VMRCore.h
//
// Desc: DirectShow sample code
// Header file and class description for CVMRCore,
// "main" module to manage VMR and its interfaces
// This class is called from CDemonstration.
//
// Copyright (c) 2000-2001 Microsoft Corporation. All rights reserved.
//------------------------------------------------------------------------------
#if !defined(AFX_NEWCORE_H__9D74D6FC_F94C_45E6_A991_E38D47C3441D__INCLUDED_)
#define AFX_NEWCORE_H__9D74D6FC_F94C_45E6_A991_E38D47C3441D__INCLUDED_
#if _MSC_VER > 1000
#pragma once
#endif // _MSC_VER > 1000
#include "stdafx.h"
class CVMRMixDlg;
class CVMRCore
{
public:
CVMRCore(CVMRMixDlg * pDlg, CMediaList *pML);
CVMRCore( CVMRMixDlg * pDlg,
DWORD dwVMRMode,
DWORD dwVMRPrefs,
CMediaList *pML);
virtual ~CVMRCore();
HWND GetClientHwnd();
virtual bool ListFilters();
HRESULT Pause();
HRESULT Stop();
HRESULT Play(bool bDoNotRunYet = false);
bool IsActive();
// functions to get information about the video playback window
void SetAbort();
void SetHwnd(HWND hwnd){m_hwnd = hwnd;};
bool SetClientVideo();
CVMRMixDlg * GetDlg(){ return m_pDlg;};
// windows procedure function for the windowless control
static LRESULT CALLBACK WndProc(HWND hWnd, UINT uMessage, WPARAM wParam, LPARAM lParam);
char m_szEventStopTest[MAX_PATH];
char m_szEventCloseWindow[MAX_PATH];
char m_szEventKillCore[MAX_PATH];
char m_szEventResumeCore[MAX_PATH];
// access to interfaces and member variables
IVMRWindowlessControl * GetVMRWndless(){return m_pIWndless;};
IGraphBuilder * GetIGraphBuilder(){return m_pGraph;};
IBaseFilter * GetTestFilter(){return m_pTestFilter;};
IVMRFilterConfig * GetVMRConfig() { return m_pConfig; };
IVMRMonitorConfig * GetVMRMonitorConfig() { return m_pIMonConfig; };
IMediaControl * GetMediaControl(){return m_pIMC;};
IVMRMixerControl * GetMixerControl(){ return m_pIMixerControl;};
IMediaSeeking * GetMediaSeeking() { return m_pIMediaSeeking;};
IVMRMixerBitmap * GetMixerBitmap(){ return m_pMixerBitmap;};
protected:
// protected member variables
HWND m_hwnd;
IGraphBuilder * m_pGraph; // graph
IBaseFilter * m_pTestFilter;// the renderer filter
IVMRWindowlessControl * m_pIWndless;
IMediaControl * m_pIMC;
IVMRFilterConfig * m_pConfig;
IVMRMonitorConfig * m_pIMonConfig;
IVideoWindow * m_pIVidWindow;
IVMRMixerControl * m_pIMixerControl;
IMediaSeeking * m_pIMediaSeeking;
IVMRMixerBitmap * m_pMixerBitmap;
DWORD m_dwVMRMode; // VMR Mode setup flags
DWORD m_dwVMRPrefs; // VMR Prefs setup
LPRECT m_lpSrcRect; // pointer to SRC rect for painting
LPRECT m_lpDestRect; // pointer to Dest rect for painting
// working functions
virtual HRESULT CreateGraph();
virtual HRESULT AddTestFilter();
virtual HRESULT InitRelevantInterfaces();
HRESULT CreateWindowlessWindow();
virtual void ReleaseInterfaces();
virtual LRESULT OnPaint(HWND hWnd);
virtual LRESULT OnSize(LPARAM lParam, WPARAM wParam);
private:
DWORD m_tID; // thread identifier for windless mode
DWORD m_dwID; // ID of this copy of CVMRCore. Generated as rand();
CVMRMixDlg * m_pDlg; // 'parent' dialog
CMediaList * m_pML; // media list to render
int m_nConnectedPins; // number of active input pins of VMR
HANDLE m_hWinThread; // windowless control's window thread
HANDLE m_hEventStopTest;
HANDLE m_hEventCloseWindow;
HANDLE m_hEventKillCore;
HANDLE m_hEventResumeCore; // control window
// private working functions
bool IsRenderer(char * strFilterName); // determines if a filter is a video renderer
LRESULT KillWindow(); // process closing window by user
};
#endif // !defined(AFX_NEWCORE_H__9D74D6FC_F94C_45E6_A991_E38D47C3441D__INCLUDED_)

View File

@@ -0,0 +1,90 @@
//------------------------------------------------------------------------------
// File: VMRMix.cpp
//
// Desc: DirectShow sample code
// Implementation of CVMRMixApp
//
// Copyright (c) 2000-2001 Microsoft Corporation. All rights reserved.
//------------------------------------------------------------------------------
#include "stdafx.h"
#include "VMRMix.h"
#include "VMRMixDlg.h"
#ifdef _DEBUG
#define new DEBUG_NEW
#undef THIS_FILE
static char THIS_FILE[] = __FILE__;
#endif
extern BOOL VerifyVMR(void);
/////////////////////////////////////////////////////////////////////////////
// CVMRMixApp
BEGIN_MESSAGE_MAP(CVMRMixApp, CWinApp)
//{{AFX_MSG_MAP(CVMRMixApp)
// NOTE - the ClassWizard will add and remove mapping macros here.
// DO NOT EDIT what you see in these blocks of generated code!
//}}AFX_MSG
ON_COMMAND(ID_HELP, CWinApp::OnHelp)
END_MESSAGE_MAP()
/////////////////////////////////////////////////////////////////////////////
// CVMRMixApp construction
CVMRMixApp::CVMRMixApp()
{
// TODO: add construction code here,
// Place all significant initialization in InitInstance
}
/////////////////////////////////////////////////////////////////////////////
// The one and only CVMRMixApp object
CVMRMixApp theApp;
/////////////////////////////////////////////////////////////////////////////
// CVMRMixApp initialization
BOOL CVMRMixApp::InitInstance()
{
// Standard initialization
// If you are not using these features and wish to reduce the size
// of your final executable, you should remove from the following
// the specific initialization routines you do not need.
// In MFC 5.0, Enable3dControls and Enable3dControlsStatic are obsolete because
// their functionality is incorporated into Microsoft's 32-bit operating systems.
#if (_MSC_VER <= 1200)
#ifdef _AFXDLL
Enable3dControls(); // Call this when using MFC in a shared DLL
#else
Enable3dControlsStatic(); // Call this when linking to MFC statically
#endif
#endif
// Verify that the Video Mixing Renderer is present (requires Windows XP).
// Otherwise, this sample cannot continue.
if (!VerifyVMR())
return FALSE;
CVMRMixDlg dlg;
m_pMainWnd = &dlg;
int nResponse = dlg.DoModal();
if (nResponse == IDOK)
{
// TODO: Place code here to handle when the dialog is
// dismissed with OK
}
else if (nResponse == IDCANCEL)
{
// TODO: Place code here to handle when the dialog is
// dismissed with Cancel
}
// Since the dialog has been closed, return FALSE so that we exit the
// application, rather than start the application's message pump.
return FALSE;
}

View File

@@ -0,0 +1,210 @@
# Microsoft Developer Studio Project File - Name="VMRMix" - Package Owner=<4>
# Microsoft Developer Studio Generated Build File, Format Version 6.00
# ** DO NOT EDIT **
# TARGTYPE "Win32 (x86) Application" 0x0101
CFG=VMRMix - Win32 Debug
!MESSAGE This is not a valid makefile. To build this project using NMAKE,
!MESSAGE use the Export Makefile command and run
!MESSAGE
!MESSAGE NMAKE /f "VMRMix.mak".
!MESSAGE
!MESSAGE You can specify a configuration when running NMAKE
!MESSAGE by defining the macro CFG on the command line. For example:
!MESSAGE
!MESSAGE NMAKE /f "VMRMix.mak" CFG="VMRMix - Win32 Debug"
!MESSAGE
!MESSAGE Possible choices for configuration are:
!MESSAGE
!MESSAGE "VMRMix - Win32 Release" (based on "Win32 (x86) Application")
!MESSAGE "VMRMix - Win32 Debug" (based on "Win32 (x86) Application")
!MESSAGE
# Begin Project
# PROP AllowPerConfigDependencies 0
# PROP Scc_ProjName ""
# PROP Scc_LocalPath ""
CPP=cl.exe
MTL=midl.exe
RSC=rc.exe
!IF "$(CFG)" == "VMRMix - Win32 Release"
# PROP BASE Use_MFC 5
# PROP BASE Use_Debug_Libraries 0
# PROP BASE Output_Dir "Release"
# PROP BASE Intermediate_Dir "Release"
# PROP BASE Target_Dir ""
# PROP Use_MFC 5
# PROP Use_Debug_Libraries 0
# PROP Output_Dir "Release"
# PROP Intermediate_Dir "Release"
# PROP Ignore_Export_Lib 0
# PROP Target_Dir ""
# ADD BASE CPP /nologo /MT /W3 /GX /O2 /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /Yu"stdafx.h" /FD /c
# ADD CPP /nologo /MT /W3 /GX /O2 /I "..\..\..\DirectShow\BaseClasses" /D "NDEBUG" /D "WIN32" /D "_WINDOWS" /D "_MBCS" /D WINVER=0x501 /Yu"stdafx.h" /FD /c
# ADD BASE MTL /nologo /D "NDEBUG" /mktyplib203 /win32
# ADD MTL /nologo /D "NDEBUG" /mktyplib203 /win32
# ADD BASE RSC /l 0x409 /d "NDEBUG"
# ADD RSC /l 0x409 /d "NDEBUG" /d "WIN32"
BSC32=bscmake.exe
# ADD BASE BSC32 /nologo
# ADD BSC32 /nologo
LINK32=link.exe
# ADD BASE LINK32 /nologo /subsystem:windows /machine:I386
# ADD LINK32 ..\..\..\DirectShow\baseclasses\release\strmbase.lib strmiids.lib quartz.lib ddraw.lib dxguid.lib version.lib shell32.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib winmm.lib comctl32.lib shell32.lib /nologo /subsystem:windows /pdb:none /machine:I386 /OPT:NOREF /OPT:ICF
!ELSEIF "$(CFG)" == "VMRMix - Win32 Debug"
# PROP BASE Use_MFC 5
# PROP BASE Use_Debug_Libraries 1
# PROP BASE Output_Dir "Debug"
# PROP BASE Intermediate_Dir "Debug"
# PROP BASE Target_Dir ""
# PROP Use_MFC 6
# PROP Use_Debug_Libraries 1
# PROP Output_Dir "Debug"
# PROP Intermediate_Dir "Debug"
# PROP Ignore_Export_Lib 0
# PROP Target_Dir ""
# ADD BASE CPP /nologo /MTd /W3 /Gm /GX /ZI /Od /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /Yu"stdafx.h" /FD /GZ /c
# ADD CPP /nologo /MDd /W3 /Gm /GX /ZI /Od /I "..\..\..\DirectShow\BaseClasses" /D "_DEBUG" /D "_AFXDLL" /D "WIN32" /D "_WINDOWS" /D "_MBCS" /D WINVER=0x501 /YX"stdafx.h" /FD /GZ /c
# SUBTRACT CPP /Fr
# ADD BASE MTL /nologo /D "_DEBUG" /mktyplib203 /win32
# ADD MTL /nologo /D "_DEBUG" /mktyplib203 /win32
# ADD BASE RSC /l 0x409 /d "_DEBUG"
# ADD RSC /l 0x409 /d "_DEBUG" /d "_AFXDLL" /d "WIN32"
BSC32=bscmake.exe
# ADD BASE BSC32 /nologo
# ADD BSC32 /nologo
LINK32=link.exe
# ADD BASE LINK32 /nologo /subsystem:windows /debug /machine:I386 /pdbtype:sept
# ADD LINK32 ..\..\..\DirectShow\baseclasses\debug\strmbasd.lib strmiids.lib comctl32.lib winmm.lib ddraw.lib /nologo /subsystem:windows /debug /machine:I386 /nodefaultlib:"libcmtd" /pdbtype:sept
# SUBTRACT LINK32 /map
!ENDIF
# Begin Target
# Name "VMRMix - Win32 Release"
# Name "VMRMix - Win32 Debug"
# Begin Group "Source Files"
# PROP Default_Filter "cpp;c;cxx;rc;def;r;odl;idl;hpj;bat"
# Begin Source File
SOURCE=.\Demonstration.cpp
# End Source File
# Begin Source File
SOURCE=.\DlgWait.cpp
# End Source File
# Begin Source File
SOURCE=.\SourceInfo.cpp
# End Source File
# Begin Source File
SOURCE=.\StdAfx.cpp
# ADD CPP /Yc"stdafx.h"
# End Source File
# Begin Source File
SOURCE=.\Utils.cpp
# End Source File
# Begin Source File
SOURCE=.\VMRCore.cpp
# End Source File
# Begin Source File
SOURCE=.\VMRMix.cpp
# End Source File
# Begin Source File
SOURCE=.\VMRMix.rc
# End Source File
# Begin Source File
SOURCE=.\VMRMixDlg.cpp
# End Source File
# End Group
# Begin Group "Header Files"
# PROP Default_Filter "h;hpp;hxx;hm;inl"
# Begin Source File
SOURCE=.\Demonstration.h
# End Source File
# Begin Source File
SOURCE=.\DlgWait.h
# End Source File
# Begin Source File
SOURCE=.\Resource.h
# End Source File
# Begin Source File
SOURCE=.\SourceInfo.h
# End Source File
# Begin Source File
SOURCE=.\StdAfx.h
# End Source File
# Begin Source File
SOURCE=.\Utils.h
# End Source File
# Begin Source File
SOURCE=.\VMRCore.h
# End Source File
# Begin Source File
SOURCE=.\VMRMix.h
# End Source File
# Begin Source File
SOURCE=.\VMRMixDlg.h
# End Source File
# End Group
# Begin Group "Resource Files"
# PROP Default_Filter "ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe"
# Begin Source File
SOURCE=.\res\bitmap1.bmp
# End Source File
# Begin Source File
SOURCE=.\res\bitmap2.bmp
# End Source File
# Begin Source File
SOURCE=.\res\bitmap3.bmp
# End Source File
# Begin Source File
SOURCE=.\res\close.bmp
# End Source File
# Begin Source File
SOURCE=.\res\Logo.bmp
# End Source File
# Begin Source File
SOURCE=.\res\VMRMix.ico
# End Source File
# Begin Source File
SOURCE=.\res\VMRMix.rc2
# End Source File
# End Group
# Begin Source File
SOURCE=.\ReadMe.txt
# End Source File
# End Target
# End Project

View File

@@ -0,0 +1,29 @@
Microsoft Developer Studio Workspace File, Format Version 6.00
# WARNING: DO NOT EDIT OR DELETE THIS WORKSPACE FILE!
###############################################################################
Project: "VMRMix"=.\VMRMix.dsp - Package Owner=<4>
Package=<5>
{{{
}}}
Package=<4>
{{{
}}}
###############################################################################
Global:
Package=<5>
{{{
}}}
Package=<3>
{{{
}}}
###############################################################################

View File

@@ -0,0 +1,55 @@
//------------------------------------------------------------------------------
// File: VMRMix.h
//
// Desc: DirectShow sample code
// Header file and class description for CVMRMixApp
//
// Copyright (c) 2000-2001 Microsoft Corporation. All rights reserved.
//------------------------------------------------------------------------------
#if !defined(AFX_VMRMix_H__D7D7485E_84F1_4BE2_ACF2_569097C46073__INCLUDED_)
#define AFX_VMRMix_H__D7D7485E_84F1_4BE2_ACF2_569097C46073__INCLUDED_
#if _MSC_VER > 1000
#pragma once
#endif // _MSC_VER > 1000
#ifndef __AFXWIN_H__
#error include 'stdafx.h' before including this file for PCH
#endif
#include "resource.h" // main symbols
/////////////////////////////////////////////////////////////////////////////
// CVMRMixApp:
// See VMRMix.cpp for the implementation of this class
//
class CVMRMixApp : public CWinApp
{
public:
CVMRMixApp();
// Overrides
// ClassWizard generated virtual function overrides
//{{AFX_VIRTUAL(CVMRMixApp)
public:
virtual BOOL InitInstance();
//}}AFX_VIRTUAL
// Implementation
//{{AFX_MSG(CVMRMixApp)
// NOTE - the ClassWizard will add and remove member functions here.
// DO NOT EDIT what you see in these blocks of generated code !
//}}AFX_MSG
DECLARE_MESSAGE_MAP()
};
/////////////////////////////////////////////////////////////////////////////
//{{AFX_INSERT_LOCATION}}
// Microsoft Visual C++ will insert additional declarations immediately before the previous line.
#endif // !defined(AFX_VMRMix_H__D7D7485E_84F1_4BE2_ACF2_569097C46073__INCLUDED_)

View File

@@ -0,0 +1,268 @@
//Microsoft Developer Studio generated resource script.
//
#include "resource.h"
#define APSTUDIO_READONLY_SYMBOLS
/////////////////////////////////////////////////////////////////////////////
//
// Generated from the TEXTINCLUDE 2 resource.
//
#include "afxres.h"
/////////////////////////////////////////////////////////////////////////////
#undef APSTUDIO_READONLY_SYMBOLS
/////////////////////////////////////////////////////////////////////////////
// English (U.S.) resources
#if !defined(AFX_RESOURCE_DLL) || defined(AFX_TARG_ENU)
#ifdef _WIN32
LANGUAGE LANG_ENGLISH, SUBLANG_ENGLISH_US
#pragma code_page(1252)
#endif //_WIN32
#ifdef APSTUDIO_INVOKED
/////////////////////////////////////////////////////////////////////////////
//
// TEXTINCLUDE
//
1 TEXTINCLUDE DISCARDABLE
BEGIN
"resource.h\0"
END
2 TEXTINCLUDE DISCARDABLE
BEGIN
"#include ""afxres.h""\r\n"
"\0"
END
3 TEXTINCLUDE DISCARDABLE
BEGIN
"#define _AFX_NO_SPLITTER_RESOURCES\r\n"
"#define _AFX_NO_OLE_RESOURCES\r\n"
"#define _AFX_NO_TRACKER_RESOURCES\r\n"
"#define _AFX_NO_PROPERTY_RESOURCES\r\n"
"\r\n"
"#if !defined(AFX_RESOURCE_DLL) || defined(AFX_TARG_ENU)\r\n"
"#ifdef _WIN32\r\n"
"LANGUAGE 9, 1\r\n"
"#pragma code_page(1252)\r\n"
"#endif //_WIN32\r\n"
"#include ""res\\VMRMix.rc2"" // non-Microsoft Visual C++ edited resources\r\n"
"#include ""afxres.rc"" // Standard components\r\n"
"#endif\r\n"
"\0"
END
#endif // APSTUDIO_INVOKED
/////////////////////////////////////////////////////////////////////////////
//
// Icon
//
// Icon with lowest ID value placed first to ensure application icon
// remains consistent on all systems.
IDR_MAINFRAME ICON DISCARDABLE "res\\VMRMix.ico"
/////////////////////////////////////////////////////////////////////////////
//
// Dialog
//
IDD_ABOUTBOX DIALOG DISCARDABLE 0, 0, 235, 81
STYLE DS_MODALFRAME | WS_POPUP | WS_CAPTION | WS_SYSMENU
CAPTION "About VMRMix"
FONT 8, "MS Sans Serif"
BEGIN
ICON IDR_MAINFRAME,IDC_STATIC,11,17,21,20
LTEXT "VMRMix Version 8.1",IDC_STATIC,40,10,119,8,SS_NOPREFIX
LTEXT "Copyright (C) 2001 Microsoft Corporation",IDC_STATIC,40,
25,188,8
DEFPUSHBUTTON "OK",IDOK,178,7,50,14,WS_GROUP
LTEXT "This sample demonstrates some of the mixing, blending, and rendering capabilities of the Video Mixing Renderer in Windows XP. ",
IDC_STATIC,40,40,187,30
END
IDD_VMRMIX_DIALOG DIALOGEX 0, 0, 216, 110
STYLE DS_MODALFRAME | DS_CENTER | WS_MINIMIZEBOX | WS_POPUP | WS_VISIBLE |
WS_CAPTION | WS_SYSMENU
EXSTYLE WS_EX_APPWINDOW
CAPTION "VMRMix for Windows XP"
FONT 8, "MS Sans Serif"
BEGIN
CONTROL "Slider1",IDC_SLIDER,"msctls_trackbar32",TBS_AUTOTICKS |
TBS_TOP | TBS_ENABLESELRANGE | WS_TABSTOP,69,36,123,21
CONTROL "&Display bitmap over the video?",IDC_CHECK_APPLYBITMAP,
"Button",BS_AUTOCHECKBOX | WS_TABSTOP,8,66,116,10
CONTROL "&Maximize window?",IDC_CHECK_FULLSCREEN,"Button",
BS_AUTOCHECKBOX | WS_TABSTOP,132,66,75,10
PUSHBUTTON "&Start",IDC_BUTTON_PLAY,52,87,50,16,BS_CENTER |
BS_VCENTER
DEFPUSHBUTTON "E&xit",IDOK,113,87,50,16
CTEXT "Number of sources:",IDC_STATIC_STREAMS_TITLE,3,36,67,16,
SS_CENTERIMAGE
CTEXT "16",IDC_STATIC_NSRC,195,36,15,16,SS_CENTERIMAGE
CTEXT "Select the number of video streams to mix together. These streams will be randomly selected from the specified media directory and will be blended together in a new window.",
IDC_STATIC,3,5,209,30
END
IDD_DIALOG_PROGRESS DIALOG DISCARDABLE 0, 0, 187, 20
STYLE DS_MODALFRAME | DS_CENTER | WS_POPUP | WS_CAPTION
CAPTION "Loading media settings..."
FONT 8, "MS Sans Serif"
BEGIN
CONTROL "Progress1",IDC_PROGRESS,"msctls_progress32",WS_BORDER,7,
7,173,6
END
IDD_DIALOG_PLAYBACK DIALOG DISCARDABLE 0, 0, 246, 183
STYLE WS_CHILD
FONT 8, "MS Sans Serif"
BEGIN
END
#ifndef _MAC
/////////////////////////////////////////////////////////////////////////////
//
// Version
//
VS_VERSION_INFO VERSIONINFO
FILEVERSION 8,1,0,0
PRODUCTVERSION 8,1,0,0
FILEFLAGSMASK 0x3fL
#ifdef _DEBUG
FILEFLAGS 0x1L
#else
FILEFLAGS 0x0L
#endif
FILEOS VOS_NT_WINDOWS32
FILETYPE 0x1L
FILESUBTYPE 0x0L
BEGIN
BLOCK "StringFileInfo"
BEGIN
BLOCK "040904b0"
BEGIN
VALUE "Comments", "DirectShow Windows XP Sample\0"
VALUE "CompanyName", "Microsoft\0"
VALUE "FileDescription", "VMRMix Application\0"
VALUE "FileVersion", "8.10\0"
VALUE "InternalName", "VMR Mix\0"
VALUE "LegalCopyright", "Copyright (c) 2000-2001 Microsoft Corporation\0"
VALUE "LegalTrademarks", "\0"
VALUE "OriginalFilename", "VMRMix.EXE\0"
VALUE "PrivateBuild", "\0"
VALUE "ProductName", "DirectX 8.1 SDK\0"
VALUE "ProductVersion", "8.1\0"
VALUE "SpecialBuild", "\0"
END
END
BLOCK "VarFileInfo"
BEGIN
VALUE "Translation", 0x409, 1200
END
END
#endif // !_MAC
/////////////////////////////////////////////////////////////////////////////
//
// DESIGNINFO
//
#ifdef APSTUDIO_INVOKED
GUIDELINES DESIGNINFO DISCARDABLE
BEGIN
IDD_ABOUTBOX, DIALOG
BEGIN
LEFTMARGIN, 7
RIGHTMARGIN, 228
TOPMARGIN, 7
BOTTOMMARGIN, 74
END
IDD_DIALOG_PROGRESS, DIALOG
BEGIN
LEFTMARGIN, 7
RIGHTMARGIN, 180
TOPMARGIN, 7
BOTTOMMARGIN, 13
END
IDD_DIALOG_PLAYBACK, DIALOG
BEGIN
LEFTMARGIN, 7
RIGHTMARGIN, 239
TOPMARGIN, 7
BOTTOMMARGIN, 176
END
END
#endif // APSTUDIO_INVOKED
/////////////////////////////////////////////////////////////////////////////
//
// Menu
//
IDR_MENU MENU DISCARDABLE
BEGIN
POPUP "File"
BEGIN
MENUITEM "Select media folder...", ID_FILE_SELECTMEDIAFOLDER
MENUITEM "Exit", ID_FILE_EXIT
END
END
/////////////////////////////////////////////////////////////////////////////
//
// Bitmap
//
IDB_BITMAP_LOGO BITMAP DISCARDABLE "res\\Logo.bmp"
/////////////////////////////////////////////////////////////////////////////
//
// String Table
//
STRINGTABLE DISCARDABLE
BEGIN
IDS_ABOUTBOX "&About VMRMix..."
END
#endif // English (U.S.) resources
/////////////////////////////////////////////////////////////////////////////
#ifndef APSTUDIO_INVOKED
/////////////////////////////////////////////////////////////////////////////
//
// Generated from the TEXTINCLUDE 3 resource.
//
#define _AFX_NO_SPLITTER_RESOURCES
#define _AFX_NO_OLE_RESOURCES
#define _AFX_NO_TRACKER_RESOURCES
#define _AFX_NO_PROPERTY_RESOURCES
#if !defined(AFX_RESOURCE_DLL) || defined(AFX_TARG_ENU)
#ifdef _WIN32
LANGUAGE 9, 1
#pragma code_page(1252)
#endif //_WIN32
#include "res\VMRMix.rc2" // non-Microsoft Visual C++ edited resources
#include "afxres.rc" // Standard components
#endif
/////////////////////////////////////////////////////////////////////////////
#endif // not APSTUDIO_INVOKED

View File

@@ -0,0 +1,511 @@
//------------------------------------------------------------------------------
// File: VMRMixDlg.cpp
//
// Desc: DirectShow sample code
// Implementation of the settings dialog
//
// Copyright (c) 2000-2001 Microsoft Corporation. All rights reserved.
//------------------------------------------------------------------------------
#include "stdafx.h"
#include "VMRMix.h"
#include "VMRMixDlg.h"
#include "DlgWait.h"
#include "Demonstration.h"
#ifdef _DEBUG
#define new DEBUG_NEW
#undef THIS_FILE
static char THIS_FILE[] = __FILE__;
#endif
class CDemonstration;
/////////////////////////////////////////////////////////////////////////////
// CAboutDlg dialog used for App About
class CAboutDlg : public CDialog
{
public:
CAboutDlg();
// Dialog Data
//{{AFX_DATA(CAboutDlg)
enum { IDD = IDD_ABOUTBOX };
//}}AFX_DATA
// ClassWizard generated virtual function overrides
//{{AFX_VIRTUAL(CAboutDlg)
protected:
virtual void DoDataExchange(CDataExchange* pDX); // DDX/DDV support
//}}AFX_VIRTUAL
// Implementation
protected:
//{{AFX_MSG(CAboutDlg)
//}}AFX_MSG
DECLARE_MESSAGE_MAP()
};
CAboutDlg::CAboutDlg() : CDialog(CAboutDlg::IDD)
{
//{{AFX_DATA_INIT(CAboutDlg)
//}}AFX_DATA_INIT
}
void CAboutDlg::DoDataExchange(CDataExchange* pDX)
{
CDialog::DoDataExchange(pDX);
//{{AFX_DATA_MAP(CAboutDlg)
//}}AFX_DATA_MAP
}
BEGIN_MESSAGE_MAP(CAboutDlg, CDialog)
//{{AFX_MSG_MAP(CAboutDlg)
// No message handlers
//}}AFX_MSG_MAP
END_MESSAGE_MAP()
/////////////////////////////////////////////////////////////////////////////
// CVMRMixDlg dialog
CVMRMixDlg::CVMRMixDlg(CWnd* pParent /*=NULL*/)
: CDialog(CVMRMixDlg::IDD, pParent)
{
//{{AFX_DATA_INIT(CVMRMixDlg)
// NOTE: the ClassWizard will add member initialization here
//}}AFX_DATA_INIT
// Note that LoadIcon does not require a subsequent DestroyIcon in Win32
m_hIcon = AfxGetApp()->LoadIcon(IDR_MAINFRAME);
m_bFullScreen = true;
m_bUseBitmap = true;
m_nMaxSources = 16;
m_nStreams = 5; // Initial number of streams
m_eState = eStop;
strcpy(m_szFolder,"");
}
void CVMRMixDlg::DoDataExchange(CDataExchange* pDX)
{
CDialog::DoDataExchange(pDX);
//{{AFX_DATA_MAP(CVMRMixDlg)
DDX_Control(pDX, IDC_CHECK_FULLSCREEN, m_chkFullScreen);
DDX_Control(pDX, IDC_CHECK_APPLYBITMAP, m_chkBitmap);
DDX_Control(pDX, IDC_SLIDER, m_Slider);
DDX_Control(pDX, IDOK, m_btnOK);
DDX_Control(pDX, IDC_BUTTON_PLAY, m_btnPlay);
//}}AFX_DATA_MAP
}
BEGIN_MESSAGE_MAP(CVMRMixDlg, CDialog)
//{{AFX_MSG_MAP(CVMRMixDlg)
ON_WM_SYSCOMMAND()
ON_WM_PAINT()
ON_WM_QUERYDRAGICON()
ON_BN_CLICKED(IDC_BUTTON_PLAY, OnButtonPlay)
ON_COMMAND(ID_FILE_SELECTMEDIAFOLDER, SelectFolder)
ON_NOTIFY(NM_RELEASEDCAPTURE, IDC_SLIDER, OnReleasedcaptureSlider)
ON_BN_CLICKED(IDC_CHECK_APPLYBITMAP, OnCheckApplybitmap)
ON_BN_CLICKED(IDC_CHECK_FULLSCREEN, OnCheckFullscreen)
//}}AFX_MSG_MAP
END_MESSAGE_MAP()
/////////////////////////////////////////////////////////////////////////////
// CVMRMixDlg message handlers
BOOL CVMRMixDlg::OnInitDialog()
{
CDialog::OnInitDialog();
// Add "About..." menu item to system menu.
// IDM_ABOUTBOX must be in the system command range.
ASSERT((IDM_ABOUTBOX & 0xFFF0) == IDM_ABOUTBOX);
ASSERT(IDM_ABOUTBOX < 0xF000);
CMenu* pSysMenu = GetSystemMenu(FALSE);
if (pSysMenu != NULL)
{
CString strAboutMenu;
strAboutMenu.LoadString(IDS_ABOUTBOX);
if (!strAboutMenu.IsEmpty())
{
pSysMenu->AppendMenu(MF_SEPARATOR);
pSysMenu->AppendMenu(MF_STRING, IDM_ABOUTBOX, strAboutMenu);
}
}
// Set the icon for this dialog. The framework does this automatically
// when the application's main window is not a dialog
SetIcon(m_hIcon, TRUE); // Set big icon
SetIcon(m_hIcon, FALSE); // Set small icon
SetNumberOfStreams(m_nStreams);
// upon initialization, ask user to specify media folder
// if failed, app cannot continue and quits
while( !strlen(m_szFolder) )
{
SelectFolder();
if( !strlen(m_szFolder) )
{
// If no media directory was specified, just exit
PostQuitMessage(0);
return FALSE;
}
m_MediaList.Initialize( m_szFolder );
if( 0 == m_MediaList.Size() )
{
AfxMessageBox("Selected folder does not contain any media file");
strcpy( m_szFolder, "");
}
}
// Read settings for the selected media file
BOOL bRes = GetMediaSettings();
if( bRes )
{
m_nMaxSources = (m_MediaList.Size() > 16) ? 16 : m_MediaList.Size();
m_Slider.SetRange(1, m_nMaxSources);
if( m_nStreams > m_nMaxSources)
{
SetNumberOfStreams( m_nMaxSources );
}
}
m_chkFullScreen.SetCheck( m_bFullScreen);
m_chkBitmap.SetCheck( m_bUseBitmap);
RECT rSlider;
m_Slider.GetWindowRect( &rSlider );
LPARAM lparam = MAKELPARAM( (rSlider.left + rSlider.right)/2, (rSlider.top + rSlider.bottom)/2);
m_Slider.SendMessage(WM_LBUTTONUP, NULL, lparam);
return bRes; // return TRUE unless you set the focus to a control
}
//-------------------------------------------------------------
// Windows message processing for CVMRMixDlg
//-------------------------------------------------------------
void CVMRMixDlg::OnSysCommand(UINT nID, LPARAM lParam)
{
if ((nID & 0xFFF0) == IDM_ABOUTBOX)
{
CAboutDlg dlgAbout;
dlgAbout.DoModal();
}
else
{
CDialog::OnSysCommand(nID, lParam);
}
}
// If you add a minimize button to your dialog, you will need the code below
// to draw the icon. For MFC applications using the document/view model,
// this is automatically done for you by the framework.
void CVMRMixDlg::OnPaint()
{
if (IsIconic())
{
CPaintDC dc(this); // device context for painting
SendMessage(WM_ICONERASEBKGND, (WPARAM) dc.GetSafeHdc(), 0);
// Center icon in client rectangle
int cxIcon = GetSystemMetrics(SM_CXICON);
int cyIcon = GetSystemMetrics(SM_CYICON);
CRect rect;
GetClientRect(&rect);
int x = (rect.Width() - cxIcon + 1) / 2;
int y = (rect.Height() - cyIcon + 1) / 2;
// Draw the icon
dc.DrawIcon(x, y, m_hIcon);
}
else
{
CDialog::OnPaint();
}
}
// The system calls this to obtain the cursor to display while the user drags
// the minimized window.
HCURSOR CVMRMixDlg::OnQueryDragIcon()
{
return (HCURSOR) m_hIcon;
}
void CVMRMixDlg::OnButtonPlay()
{
ShowWindow(SW_HIDE);
RunDemonstration();
ShowWindow(SW_SHOW);
}
void CVMRMixDlg::OnCheckApplybitmap()
{
m_bUseBitmap = ( m_chkBitmap.GetCheck() ) ? true : false;
}
void CVMRMixDlg::OnCheckFullscreen()
{
m_bFullScreen = ( m_chkFullScreen.GetCheck() ) ? true : false;
}
void CVMRMixDlg::OnReleasedcaptureSlider(NMHDR* pNMHDR, LRESULT* pResult)
{
int nPos = m_Slider.GetPos();
SetNumberOfStreams( nPos);
*pResult = 0;
}
//-------------------------------------------------------------
// CVMRMixDlg::SetNumberOfStreams
// Desc: Sets number of source streams for presentation (m_nStreams)
// and positions slider
// Return: true if successful and false otherwise
//-------------------------------------------------------------
bool CVMRMixDlg::SetNumberOfStreams( int n)
{
if( n<1 || n>m_nMaxSources )
return false;
char szMsg[MAX_PATH];
m_nStreams = n;
sprintf( szMsg, "%d", m_nStreams);
GetDlgItem(IDC_STATIC_NSRC)->SetWindowText(szMsg);
m_Slider.SetPos( n);
return true;
}
void CVMRMixDlg::SelectFolder()
{
OPENFILENAME ofn;
TCHAR szBuffer[MAX_PATH];
bool bFolderIsBad = true;
lstrcpy(szBuffer, TEXT(""));
static char szFilter[] = "Video Files (.MOV, .AVI, .MPG, .VOB, .QT)\0*.AVI;*.MOV;*.MPG;*.VOB;*.QT\0" \
"All Files (*.*)\0*.*\0\0";
ofn.lStructSize = sizeof(OPENFILENAME);
ofn.hwndOwner = NULL;
ofn.hInstance = NULL;
ofn.lpstrFilter = szFilter;
ofn.nFilterIndex = 1;
ofn.lpstrCustomFilter = NULL;
ofn.nMaxCustFilter = 0;
ofn.lpstrFile = szBuffer;
ofn.nMaxFile = _MAX_PATH;
ofn.lpstrFileTitle = NULL;
ofn.nMaxFileTitle = 0;
ofn.lpstrInitialDir = NULL;
ofn.lpstrTitle = "Please open any video file to select the folder...";
ofn.Flags = OFN_HIDEREADONLY | OFN_FILEMUSTEXIST | OFN_PATHMUSTEXIST;
ofn.nFileOffset = 0;
ofn.nFileExtension = 0;
ofn.lpstrDefExt = NULL;//"";
ofn.lCustData = 0L;
ofn.lpfnHook = NULL;
ofn.lpTemplateName = NULL;
while( bFolderIsBad )
{
if (GetOpenFileName (&ofn)) // user specified a file
{
char szTmp[MAX_PATH];
char *psz = NULL;
lstrcpy(szTmp, ofn.lpstrFile);
// write a profile string to test
strrev(szTmp);
psz = strstr(szTmp,"\\");
if( !psz )
{
if(MB_OK != AfxMessageBox("You must select a file folder with at least one media file. Continue?"))
{
bFolderIsBad = false;
}
else
{
continue;
}
}
strcpy( m_szFolder, psz);
strrev( m_szFolder );
return;
}// if
else
{
break;
}
}// while( bFolderIsBad )
if( bFolderIsBad )
{
strcpy( m_szFolder, "\0");
}
return;
}
void CVMRMixDlg::PostNcDestroy()
{
CDialog::PostNcDestroy();
}
//---------------------------------------------------------------
// CVMRMixDlg::GetMediaSettings
// Desc: scans media settings list, verifies media files,
// and reads duration info
// return: true if success and false otherwise
//---------------------------------------------------------------
bool CVMRMixDlg::GetMediaSettings()
{
HRESULT hr;
int n;
char szMsg[MAX_PATH];
char szInfo[MAX_PATH];
bool bRes;
CMediaList * pML = NULL;
CMediaList MLClone; // cloned and verified copy of the media list
CMediaList mlDirty;
if( 2 > m_MediaList.Size())
{
AfxMessageBox("You must select a folder with at least two valid media files.\r\n\r\nPlease try again.", MB_OK);
exit(-1);
}
CDlgWait dlgWait(m_MediaList.Size());
m_MediaList.Clone(m_MediaList.Size(), &mlDirty, 0);
m_MediaList.Clean();
pML = &mlDirty;
ASSERT(pML);
dlgWait.Create(IDD_DIALOG_PROGRESS);
dlgWait.ShowWindow( SW_SHOW);
for(n=0; n<pML->Size(); n++)
{
MLClone.Clean();
bRes = pML->Clone(1, &MLClone, n);
if( false == bRes )
{
sprintf( szMsg, "CVMRModule::GetMediaSettings(): failed to clone element %ld, setting source for 5 sec",n);
OutputDebugString( szMsg);
pML->GetItem(n)->m_llDuration = (5L * 10000000L);
continue;
}
IMediaSeeking * pMediaSeeking = NULL;
LONGLONG llDuration = 0L;
CVMRCore core(this, VMRMode_Renderless, NULL, &MLClone);
hr = core.Play(true);
if( FAILED(hr) )
{
sprintf( szMsg, "*** failed to render source %s, method returned %s",
pML->GetItem(n)->m_szPath, hresultNameLookup(hr));
OutputDebugString( szMsg);
continue;
}
hr = core.GetIGraphBuilder()->QueryInterface(__uuidof(IMediaSeeking), reinterpret_cast<void**>(&pMediaSeeking));
if( FAILED(hr))
{
OutputDebugString("Cannot find IMediaSeeking interface\n");
dlgWait.EndDialog(IDOK);
continue;
}
// get source parameters
core.GetMediaControl()->Stop();
hr = pMediaSeeking->GetDuration( &llDuration);
if( FAILED(hr) || llDuration < 100L)
{
OutputDebugString("Failed to obtain sample duration, setting to 5 sec\n");
llDuration = 5L * 10000000L;
}
pML->GetItem(n)->m_llDuration = llDuration;
sprintf( szInfo, "Source %d: name:%s, duration: %ld\n",
n, pML->GetItem(n)->m_szPath, llDuration);
OutputDebugString(szInfo);
SAFERELEASE(pMediaSeeking);
// this media file is valid, we can add it to the media list
SourceInfo * psi = NULL;
psi = new SourceInfo;
pML->GetItem(n)->CopyTo( psi);
m_MediaList.Add(psi);
dlgWait.SetPos(n);
}
dlgWait.EndDialog(IDOK);
if( 1 > m_MediaList.Size() )
{
AfxMessageBox("Some media sources are not supported with this application\r\n\r\nPlease try again with other sources.", MB_OK);
exit(-1);
}
m_MediaList.AdjustDuration();
return true;
}
//---------------------------------------------------------------
// CVMRMixDlg::RunDemonstration
// Desc: runs demonstration module
// return: HRESULT code
//---------------------------------------------------------------
HRESULT CVMRMixDlg::RunDemonstration()
{
HRESULT hr = S_OK;
m_MediaList.Shuffle();
CDemonstration demo(this, &m_MediaList, m_nStreams, &hr);
if( FAILED(hr))
{
OutputDebugString("Failed to initialize class CDemonstration\n");
return FNS_FAIL;
}
clock_t tStart = clock();
hr = demo.Perform();
char szMsg[MAX_PATH];
sprintf( szMsg, "TIME:: Actual: %ld ms, Expected: %ld ms\n",
(clock() - tStart) * 1000 / CLOCKS_PER_SEC, m_MediaList.GetAvgDuration() / 10000);
OutputDebugString( szMsg);
if( FAILED(hr))
{
OutputDebugString("Failed to Perform() demonstration\n");
}
if( FAILED(hr))
{
return FNS_FAIL;
}
else
{
return FNS_PASS;
}
}

View File

@@ -0,0 +1,91 @@
//------------------------------------------------------------------------------
// File: VMRMixDlg.h
//
// Desc: DirectShow sample code
// Headers and class description for the settings dialog
//
// Copyright (c) 2000-2001 Microsoft Corporation. All rights reserved.
//------------------------------------------------------------------------------
#if !defined(AFX_VMRMixDLG_H__023F795A_822F_482F_8EC9_00EC8D8AA54F__INCLUDED_)
#define AFX_VMRMixDLG_H__023F795A_822F_482F_8EC9_00EC8D8AA54F__INCLUDED_
#if _MSC_VER > 1000
#pragma once
#endif // _MSC_VER > 1000
/////////////////////////////////////////////////////////////////////////////
// CVMRMixDlg dialog
class CVMRMixDlg : public CDialog
{
// Construction
public:
HRESULT RunDemonstration();
bool GetMediaSettings();
bool IsFullScreen(){ return m_bFullScreen;};
bool IsBitmapToUse(){ return m_bUseBitmap;};
CVMRMixDlg(CWnd* pParent = NULL); // standard constructor
typedef enum eState
{
eStop,
ePlay
} eState;
CMediaList m_MediaList;
// Dialog Data
//{{AFX_DATA(CVMRMixDlg)
enum { IDD = IDD_VMRMIX_DIALOG };
CButton m_chkFullScreen;
CButton m_chkBitmap;
CSliderCtrl m_Slider;
CButton m_btnOK;
CButton m_btnStop;
CButton m_btnPlay;
CButton m_btnPause;
//}}AFX_DATA
// ClassWizard generated virtual function overrides
//{{AFX_VIRTUAL(CVMRMixDlg)
protected:
virtual void DoDataExchange(CDataExchange* pDX); // DDX/DDV support
virtual void PostNcDestroy();
//}}AFX_VIRTUAL
bool SetNumberOfStreams( int n);
bool SwitchStateTo( eState eNewState);
// Implementation
protected:
HICON m_hIcon;
// Generated message map functions
//{{AFX_MSG(CVMRMixDlg)
virtual BOOL OnInitDialog();
afx_msg void OnSysCommand(UINT nID, LPARAM lParam);
afx_msg void OnPaint();
afx_msg HCURSOR OnQueryDragIcon();
afx_msg void OnSize(UINT nType, int cx, int cy);
afx_msg int OnCreate(LPCREATESTRUCT lpCreateStruct);
afx_msg void OnButtonPlay();
afx_msg void SelectFolder();
afx_msg void OnReleasedcaptureSlider(NMHDR* pNMHDR, LRESULT* pResult);
afx_msg void OnCheckApplybitmap();
afx_msg void OnCheckFullscreen();
//}}AFX_MSG
DECLARE_MESSAGE_MAP()
private:
bool m_bFullScreen;
bool m_bUseBitmap;
int m_nStreams;
eState m_eState;
char m_szFolder[MAX_PATH];
int m_nMaxSources;
};
//{{AFX_INSERT_LOCATION}}
// Microsoft Visual C++ will insert additional declarations immediately before the previous line.
#endif // !defined(AFX_VMRMixDLG_H__023F795A_822F_482F_8EC9_00EC8D8AA54F__INCLUDED_)

Binary file not shown.

After

Width:  |  Height:  |  Size: 14 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 1.1 KiB

View File

@@ -0,0 +1,13 @@
//
// VMRMIX.RC2 - resources Microsoft Visual C++ does not edit directly
//
#ifdef APSTUDIO_INVOKED
#error this file is not editable by Microsoft Visual C++
#endif //APSTUDIO_INVOKED
/////////////////////////////////////////////////////////////////////////////
// Add manually edited resources here...
/////////////////////////////////////////////////////////////////////////////

View File

@@ -0,0 +1,33 @@
//{{NO_DEPENDENCIES}}
// Microsoft Developer Studio generated include file.
// Used by VMRMix.rc
//
#define IDM_ABOUTBOX 0x0010
#define IDD_ABOUTBOX 100
#define IDS_ABOUTBOX 101
#define IDD_VMRMIX_DIALOG 102
#define IDR_MAINFRAME 128
#define IDR_MENU 129
#define IDD_DIALOG_PROGRESS 133
#define IDB_BITMAP_LOGO 136
#define IDD_DIALOG_PLAYBACK 137
#define IDC_STATIC_NSRC 1001
#define IDC_BUTTON_PLAY 1003
#define IDC_STATIC_STREAMS_TITLE 1006
#define IDC_PROGRESS 1009
#define IDC_SLIDER 1011
#define IDC_CHECK_APPLYBITMAP 1012
#define IDC_CHECK_FULLSCREEN 1013
#define ID_FILE_SELECTMEDIAFOLDER 32771
#define ID_FILE_EXIT 32772
// Next default values for new objects
//
#ifdef APSTUDIO_INVOKED
#ifndef APSTUDIO_READONLY_SYMBOLS
#define _APS_NEXT_RESOURCE_VALUE 138
#define _APS_NEXT_COMMAND_VALUE 32773
#define _APS_NEXT_CONTROL_VALUE 1014
#define _APS_NEXT_SYMED_VALUE 101
#endif
#endif