234 lines
5.9 KiB
C++
234 lines
5.9 KiB
C++
////////////////////////////////////////////////////////////////////////////////
|
|
// Plainamp, Open source Winamp core
|
|
//
|
|
// Copyright © 2005 Sebastian Pipping <webmaster@hartwork.org>
|
|
//
|
|
// --> http://www.hartwork.org
|
|
//
|
|
// This source code is released under the GNU General Public License (GPL).
|
|
// See GPL.txt for details. Any non-GPL usage is strictly forbidden.
|
|
////////////////////////////////////////////////////////////////////////////////
|
|
|
|
|
|
#include "Embed.h"
|
|
#include "Console.h"
|
|
|
|
|
|
|
|
#define CLASSNAME_EMBED TEXT( "Winamp Gen" )
|
|
#define TITLE_EMBED TEXT( "Embed target" )
|
|
|
|
#define EMBED_WIDTH 320
|
|
#define EMBED_HEIGHT 240
|
|
|
|
|
|
|
|
const TCHAR * const szEmbedTitle = TITLE_EMBED;
|
|
bool bEmbedClassRegistered = false;
|
|
|
|
|
|
LRESULT CALLBACK WndprocEmbed( HWND hwnd, UINT message, WPARAM wp, LPARAM lp );
|
|
|
|
|
|
|
|
////////////////////////////////////////////////////////////////////////////////
|
|
/// Creates a new embed window.
|
|
///
|
|
/// @param ews Embed window state
|
|
/// @return New embed window handle
|
|
////////////////////////////////////////////////////////////////////////////////
|
|
HWND Embed::Embed( embedWindowState * ews )
|
|
{
|
|
// Register class
|
|
if ( !bEmbedClassRegistered )
|
|
{
|
|
WNDCLASS wc = {
|
|
0, // UINT style
|
|
WndprocEmbed, // WNDPROC lpfnWndProc
|
|
0, // int cbClsExtra
|
|
0, // int cbWndExtra
|
|
g_hInstance, // HINSTANCE hInstance
|
|
NULL, // HICON hIcon
|
|
LoadCursor( NULL, IDC_ARROW ), // HCURSOR hCursor
|
|
( HBRUSH )COLOR_WINDOW, // HBRUSH hbrBackground
|
|
NULL, // LPCTSTR lpszMenuName
|
|
CLASSNAME_EMBED // LPCTSTR lpszClassName
|
|
};
|
|
|
|
if( !RegisterClass( &wc ) ) return NULL;
|
|
|
|
bEmbedClassRegistered = true;
|
|
}
|
|
|
|
// Create window
|
|
HWND WindowEmbed = CreateWindowEx(
|
|
WS_EX_WINDOWEDGE | // DWORD dwExStyle
|
|
WS_EX_TOOLWINDOW, //
|
|
CLASSNAME_EMBED, // LPCTSTR lpClassName
|
|
szEmbedTitle, // LPCTSTR lpWindowName
|
|
WS_OVERLAPPED | // DWORD dwStyle
|
|
WS_CLIPCHILDREN | //
|
|
WS_BORDER | //
|
|
WS_CAPTION | //
|
|
WS_SYSMENU | //
|
|
WS_THICKFRAME | //
|
|
WS_MINIMIZEBOX | //
|
|
WS_MAXIMIZEBOX, //
|
|
10, // int x
|
|
10, // int y
|
|
EMBED_WIDTH, // int nWidth
|
|
EMBED_HEIGHT, // int nHeight
|
|
NULL, // HWND hWndParent
|
|
NULL, // HMENU hMenu
|
|
g_hInstance, // HINSTANCE hInstance
|
|
NULL // LPVOID lpParam
|
|
);
|
|
|
|
Console::Append( TEXT( "Embed window born" ) );
|
|
Console::Append( TEXT( " " ) );
|
|
|
|
if( !ews || !ews->me ) return WindowEmbed;
|
|
|
|
SetParent( ews->me, WindowEmbed );
|
|
|
|
return WindowEmbed;
|
|
}
|
|
|
|
|
|
|
|
////////////////////////////////////////////////////////////////////////////////
|
|
//
|
|
////////////////////////////////////////////////////////////////////////////////
|
|
inline bool SameThread( HWND hOther )
|
|
{
|
|
const DWORD dwOtherThreadId = GetWindowThreadProcessId( hOther, NULL );
|
|
const DWORD dwThisThreadId = GetCurrentThreadId();
|
|
return ( dwOtherThreadId == dwThisThreadId );
|
|
}
|
|
|
|
|
|
|
|
////////////////////////////////////////////////////////////////////////////////
|
|
///
|
|
////////////////////////////////////////////////////////////////////////////////
|
|
LRESULT CALLBACK WndprocEmbed( HWND hwnd, UINT message, WPARAM wp, LPARAM lp )
|
|
{
|
|
// static bool bAllowSizeMove = false;
|
|
|
|
switch( message )
|
|
{
|
|
|
|
case WM_PARENTNOTIFY:
|
|
switch( LOWORD( wp ) )
|
|
{
|
|
case WM_DESTROY:
|
|
{
|
|
const HWND hChild = GetWindow( hwnd, GW_CHILD );
|
|
if( !SameThread( hChild ) )
|
|
{
|
|
// Vis plugin
|
|
DestroyWindow( hwnd );
|
|
}
|
|
break;
|
|
}
|
|
|
|
}
|
|
break;
|
|
|
|
case WM_SIZE:
|
|
{
|
|
const HWND hChild = GetWindow( hwnd, GW_CHILD );
|
|
if( !hChild ) break;
|
|
MoveWindow( hChild, 0, 0, LOWORD( lp ), HIWORD( lp ), TRUE );
|
|
break;
|
|
}
|
|
|
|
/*
|
|
case WM_ENTERSIZEMOVE:
|
|
bAllowSizeMove = true;
|
|
break;
|
|
|
|
case WM_EXITSIZEMOVE:
|
|
bAllowSizeMove = false;
|
|
break;
|
|
|
|
case WM_WINDOWPOSCHANGING:
|
|
{
|
|
WINDOWPOS * pos = ( WINDOWPOS * )lp;
|
|
|
|
// Update child
|
|
if( IsWindow( WindowEmbedChild = GetWindow( WindowEmbed, GW_CHILD ) ) )
|
|
{
|
|
RECT r;
|
|
GetClientRect( WindowEmbed, &r );
|
|
MoveWindow( WindowEmbedChild, 0, 0, r.right, r.bottom, TRUE );
|
|
}
|
|
|
|
if( !bAllowSizeMove )
|
|
{
|
|
// Force SWP_NOMOVE
|
|
if( ( pos->flags & SWP_NOMOVE ) == 0 )
|
|
{
|
|
pos->flags |= SWP_NOMOVE;
|
|
}
|
|
|
|
// Force SWP_NOSIZE
|
|
if( ( pos->flags & SWP_NOSIZE ) == 0 )
|
|
{
|
|
pos->flags |= SWP_NOSIZE;
|
|
}
|
|
|
|
return 0;
|
|
}
|
|
|
|
break;
|
|
}
|
|
*/
|
|
case WM_SHOWWINDOW:
|
|
{
|
|
const HWND hChild = GetWindow( hwnd, GW_CHILD );
|
|
if( wp ) // Shown
|
|
{
|
|
// Update child size
|
|
RECT r;
|
|
GetClientRect( hwnd, &r );
|
|
MoveWindow( hChild, 0, 0, r.right, r.bottom, TRUE );
|
|
}
|
|
else // Hidden
|
|
{
|
|
ShowWindow( hChild, SW_HIDE );
|
|
DestroyWindow( hChild );
|
|
}
|
|
break;
|
|
}
|
|
|
|
case WM_SYSCOMMAND:
|
|
if( ( wp & 0xFFF0 ) == SC_CLOSE )
|
|
{
|
|
const HWND hChild = GetWindow( hwnd, GW_CHILD );
|
|
if( SameThread( hChild ) )
|
|
{
|
|
// Not a vis plugin
|
|
ShowWindow( hwnd, SW_HIDE );
|
|
return 0;
|
|
}
|
|
}
|
|
break;
|
|
|
|
case WM_DESTROY:
|
|
{
|
|
const HWND hChild = GetWindow( hwnd, GW_CHILD );
|
|
if( hChild && SameThread( hChild ) )
|
|
{
|
|
DestroyWindow( hChild );
|
|
}
|
|
|
|
Console::Append( TEXT( "Embed window dead" ) );
|
|
Console::Append( TEXT( " " ) );
|
|
break;
|
|
}
|
|
|
|
}
|
|
return DefWindowProc( hwnd, message, wp, lp );
|
|
}
|