Initial commit: Complete open-source Decal rebuild
All 5 phases of the open-source Decal rebuild: Phase 1: 14 decompiled .NET projects (Interop.*, Adapter, FileService, DecalUtil) Phase 2: 10 native DLLs rewritten as C# COM servers with matching GUIDs - DecalDat, DHS, SpellFilter, DecalInput, DecalNet, DecalFilters - Decal.Core, DecalControls, DecalRender, D3DService Phase 3: C++ shims for Inject.DLL (D3D9 hooking) and LauncherHook.DLL Phase 4: DenAgent WinForms tray application Phase 5: WiX installer and build script 25 C# projects building with 0 errors. Native C++ projects require VS 2022 + Windows SDK (x86). Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
This commit is contained in:
commit
d1442e3747
1382 changed files with 170725 additions and 0 deletions
281
Native/DecalControls/Notebook.cpp
Normal file
281
Native/DecalControls/Notebook.cpp
Normal file
|
|
@ -0,0 +1,281 @@
|
|||
// Notebook.cpp : Implementation of cNotebook
|
||||
#include "stdafx.h"
|
||||
#include "DecalControls.h"
|
||||
#include "Notebook.h"
|
||||
|
||||
/////////////////////////////////////////////////////////////////////////////
|
||||
// cNotebook
|
||||
|
||||
cNotebook::cNotebook():
|
||||
m_nNextPageID( 1001 ),
|
||||
m_nActiveTab( -1 ),
|
||||
m_nCaptureTab( -1 ),
|
||||
m_bHitCapture( false )
|
||||
{
|
||||
}
|
||||
|
||||
long cNotebook::hitTest( MouseState *pMS )
|
||||
{
|
||||
if( pMS->over != this )
|
||||
// Not hitting us, therefore not hitting a tab
|
||||
return -1;
|
||||
|
||||
// Yes for y boundaries
|
||||
if( pMS->client.y < 0 || pMS->client.y >= 16 )
|
||||
return -1;
|
||||
|
||||
// Walk through the list of tabs
|
||||
for( cPageList::iterator i = m_pages.begin(); i != m_pages.end(); ++ i )
|
||||
{
|
||||
if( pMS->client.x >= i->m_nLeft && pMS->client.x < i->m_nRight )
|
||||
// Hit a tab!
|
||||
return ( i - m_pages.begin() );
|
||||
}
|
||||
|
||||
// No tabs hit
|
||||
return -1;
|
||||
}
|
||||
|
||||
void cNotebook::positionActiveTab()
|
||||
{
|
||||
if( m_nActiveTab == -1 )
|
||||
return;
|
||||
|
||||
RECT rcClient;
|
||||
m_pSite->get_Position( &rcClient );
|
||||
|
||||
CComPtr< ILayerSite > pChild;
|
||||
m_pSite->get_Child( m_pages[ m_nActiveTab ].m_nPageID, ePositionByID, &pChild );
|
||||
|
||||
RECT rcChild = { 0, 16, rcClient.right - rcClient.left, rcClient.bottom - rcClient.top };
|
||||
pChild->put_Position( &rcChild );
|
||||
}
|
||||
|
||||
STDMETHODIMP cNotebook::AddPage(BSTR strText, IControl *pClient)
|
||||
{
|
||||
cPage p;
|
||||
p.m_strName = strText;
|
||||
p.m_nPageID = m_nNextPageID ++;
|
||||
|
||||
CComPtr< ILayer > pClientLayer;
|
||||
pClient->QueryInterface( &pClientLayer );
|
||||
|
||||
LayerParams lp = { p.m_nPageID, { 0, 0, 0, 0 }, eRenderClipped };
|
||||
m_pSite->CreateChild( &lp, pClientLayer );
|
||||
|
||||
m_pages.push_back( p );
|
||||
|
||||
if( m_nActiveTab == -1 )
|
||||
// Activate the page if it's the first one
|
||||
m_nActiveTab = 0;
|
||||
|
||||
m_pSite->Reformat();
|
||||
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
void cNotebook::onCreate()
|
||||
{
|
||||
// Load the images
|
||||
CComPtr< IPluginSite > pPlugin;
|
||||
m_pSite->get_PluginSite( &pPlugin );
|
||||
|
||||
pPlugin->LoadBitmapFile( _bstr_t( _T( "Tab-Active.bmp" ) ), &m_pActive );
|
||||
pPlugin->LoadBitmapFile( _bstr_t( _T( "Tab-Inactive.bmp" ) ), &m_pInactive );
|
||||
BSTR bstrFontName;
|
||||
pPlugin->get_FontName(&bstrFontName);
|
||||
pPlugin->CreateFont( bstrFontName /*_bstr_t( _T( "Times New Roman" ) )*/, 14, 0, &m_pFont );
|
||||
}
|
||||
|
||||
void cNotebook::onDestroy()
|
||||
{
|
||||
m_pActive.Release();
|
||||
m_pInactive.Release();
|
||||
}
|
||||
|
||||
#define TEXT_LR_MARGIN 5
|
||||
|
||||
STDMETHODIMP cNotebook::Reformat()
|
||||
{
|
||||
// Walk through the tabs and position the graphics
|
||||
long nTabPos = 0;
|
||||
for( cPageList::iterator i = m_pages.begin(); i != m_pages.end(); ++ i )
|
||||
{
|
||||
// Calculate the text length
|
||||
SIZE sz;
|
||||
m_pFont->MeasureText( i->m_strName, &sz );
|
||||
|
||||
long nWidth = sz.cx + TEXT_LR_MARGIN * 2;
|
||||
|
||||
i->m_nLeft = nTabPos;
|
||||
i->m_nRight = nTabPos + nWidth;
|
||||
nTabPos += nWidth;
|
||||
}
|
||||
|
||||
if( m_nActiveTab != -1 )
|
||||
positionActiveTab();
|
||||
|
||||
_ASSERTMEM( _CrtCheckMemory( ) );
|
||||
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
STDMETHODIMP cNotebook::Render( ICanvas *pCanvas )
|
||||
{
|
||||
for( cPageList::iterator i = m_pages.begin(); i != m_pages.end(); ++ i )
|
||||
{
|
||||
POINT ptTab = { i->m_nLeft, 0 };
|
||||
long nWidth = i->m_nRight - i->m_nLeft;
|
||||
long nIndex = i - m_pages.begin();
|
||||
|
||||
bool bActive = ( ( nIndex == m_nActiveTab ) || ( m_nCaptureTab != -1 && m_bHitCapture && nIndex == m_nCaptureTab ) );
|
||||
if( bActive )
|
||||
m_pActive->StretchBlt( pCanvas, &ptTab, nWidth, 7, 90 );
|
||||
else
|
||||
m_pInactive->StretchBlt( pCanvas, &ptTab, nWidth, 7, 90 );
|
||||
|
||||
// Draw the text
|
||||
POINT ptText = { i->m_nLeft + TEXT_LR_MARGIN, 2 };
|
||||
m_pFont->DrawText( &ptText, i->m_strName, ( bActive ) ? RGB( 0, 0, 0 ) : RGB( 192, 192, 192 ), pCanvas );
|
||||
}
|
||||
|
||||
_ASSERTMEM( _CrtCheckMemory( ) );
|
||||
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
STDMETHODIMP cNotebook::MouseDown( MouseState *pMS )
|
||||
{
|
||||
m_nCaptureTab = hitTest( pMS );
|
||||
|
||||
if( m_nCaptureTab != -1 )
|
||||
{
|
||||
m_bHitCapture = true;
|
||||
m_pSite->Invalidate();
|
||||
}
|
||||
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
STDMETHODIMP cNotebook::MouseUp( MouseState *pMS )
|
||||
{
|
||||
_ASSERTMEM( _CrtCheckMemory( ) );
|
||||
|
||||
if( m_nCaptureTab == -1 )
|
||||
return S_OK;
|
||||
|
||||
if( hitTest( pMS ) == m_nCaptureTab )
|
||||
put_ActiveTab( m_nCaptureTab );
|
||||
|
||||
_ASSERTMEM( _CrtCheckMemory( ) );
|
||||
|
||||
m_nCaptureTab = -1;
|
||||
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
STDMETHODIMP cNotebook::MouseMove( MouseState *pMS )
|
||||
{
|
||||
if( m_nCaptureTab == -1 )
|
||||
// We are hitting in progress
|
||||
return S_OK;
|
||||
|
||||
// Check for a hit
|
||||
bool bHitCapture = ( hitTest( pMS ) == m_nCaptureTab );
|
||||
if( bHitCapture != m_bHitCapture )
|
||||
{
|
||||
m_bHitCapture = bHitCapture;
|
||||
m_pSite->Invalidate();
|
||||
}
|
||||
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
STDMETHODIMP cNotebook::get_ActiveTab(long *pVal)
|
||||
{
|
||||
*pVal = m_nActiveTab;
|
||||
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
STDMETHODIMP cNotebook::put_ActiveTab(long newVal)
|
||||
{
|
||||
if( m_nActiveTab != -1 )
|
||||
{
|
||||
// Hide the current active view
|
||||
static RECT rcHide = { 0, 0, 0, 0 };
|
||||
CComPtr< ILayerSite > pChild;
|
||||
m_pSite->get_Child( m_pages[ m_nActiveTab ].m_nPageID, ePositionByID, &pChild );
|
||||
|
||||
pChild->put_Position( &rcHide );
|
||||
}
|
||||
|
||||
m_nActiveTab = newVal;
|
||||
|
||||
if( m_nActiveTab != -1 )
|
||||
positionActiveTab();
|
||||
|
||||
long nID;
|
||||
m_pSite->get_ID( &nID );
|
||||
Fire_Change( nID, m_nActiveTab );
|
||||
|
||||
m_pSite->Invalidate();
|
||||
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
STDMETHODIMP cNotebook::SchemaLoad(IView *pView, IUnknown *pSchema)
|
||||
{
|
||||
MSXML::IXMLDOMElementPtr pElement = pSchema;
|
||||
|
||||
MSXML::IXMLDOMElementPtr pPage;
|
||||
for( MSXML::IXMLDOMNodeListPtr pPages = pElement->selectNodes( _T( "page" ) ); ( pPage = pPages->nextNode() ).GetInterfacePtr() != NULL; )
|
||||
{
|
||||
// We have the page, get the text, then recurse and generate the control
|
||||
_variant_t vText = pPage->getAttribute( _T( "label" ) );
|
||||
|
||||
_ASSERTE( vText.vt == VT_BSTR );
|
||||
|
||||
cPage p;
|
||||
p.m_strName = vText.bstrVal;
|
||||
p.m_nPageID = m_nNextPageID ++;
|
||||
|
||||
m_pages.push_back( p );
|
||||
|
||||
MSXML::IXMLDOMElementPtr pControl = pPage->selectSingleNode( _T( "control" ) );
|
||||
|
||||
_ASSERTE( pControl.GetInterfacePtr() != NULL );
|
||||
|
||||
long nAssigned;
|
||||
pView->LoadControl( m_pSite, p.m_nPageID, pControl, &nAssigned );
|
||||
}
|
||||
|
||||
if( m_nActiveTab == -1 && m_pages.size() > 0 )
|
||||
// Activate the page if it's the first one
|
||||
m_nActiveTab = 0;
|
||||
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
STDMETHODIMP cNotebook::get_PageText(long nIndex, BSTR *pVal)
|
||||
{
|
||||
_ASSERTE( pVal != NULL );
|
||||
_ASSERTE( nIndex >= 0 );
|
||||
_ASSERTE( nIndex < m_pages.size() );
|
||||
|
||||
*pVal = OLE2BSTR( m_pages[ nIndex ].m_strName );
|
||||
|
||||
return S_OK;
|
||||
}
|
||||
|
||||
STDMETHODIMP cNotebook::put_PageText(long nIndex, BSTR newVal)
|
||||
{
|
||||
_ASSERTE( newVal != NULL );
|
||||
_ASSERTE( nIndex >= 0 );
|
||||
_ASSERTE( nIndex < m_pages.size() );
|
||||
|
||||
m_pages[ nIndex ].m_strName = newVal;
|
||||
m_pSite->Reformat();
|
||||
|
||||
return S_OK;
|
||||
}
|
||||
Loading…
Add table
Add a link
Reference in a new issue