diff --git a/harbour/ChangeLog b/harbour/ChangeLog index 3430b70b28..065ae692c5 100644 --- a/harbour/ChangeLog +++ b/harbour/ChangeLog @@ -17,6 +17,24 @@ past entries belonging to author(s): Viktor Szakats. */ +2010-01-23 14:05 UTC+0100 Viktor Szakats (harbour.01 syenar.hu) + * contrib/hbwin/hbwapi.h + * contrib/hbwin/wapi_alloc.c + * contrib/hbwin/wapi_wingdi.c + * contrib/hbwin/tests/testgdi.prg + + Reworked the way DEVMODE structure is handled. As many winapi + interfacing methods, this is also a strange beast, it contains + some hidden information, so it must be created using some + winapi calls. I finally settled with these three functions + to handle DEVMODE structure from .prg level: + __WAPI_DEVMODE_NEW( ) => + __WAPI_DEVMODE_SET( , ) + __WAPI_DEVMODE_GET( , ) + Then can be passed to WAPI_CREATEDC() and WAPI_RESETDC(). + Remember to recreate after using __WAPI_DEVMODE_SET() + and before using __WAPI_DEVMODE_GET() to refresh the structure + content with actual device settings. + 2010-01-23 12:36 UTC+0100 Viktor Szakats (harbour.01 syenar.hu) * contrib/hbide/ideprojmanager.prg ! Don't delete temp .hbp file when creating PPO file, otherwise diff --git a/harbour/contrib/hbwin/hbwapi.h b/harbour/contrib/hbwin/hbwapi.h index 0f26d845f6..6266d50b67 100644 --- a/harbour/contrib/hbwin/hbwapi.h +++ b/harbour/contrib/hbwin/hbwapi.h @@ -104,22 +104,22 @@ HB_EXPORT DWORD hbwapi_GetLastError( void ); HB_EXPORT POINT * hbwapi_par_POINT( POINT * p, int iParam, HB_BOOL bMandatory ); HB_EXPORT RECT * hbwapi_par_RECT( RECT * p, int iParam, HB_BOOL bMandatory ); -HB_EXPORT DEVMODE * hbwapi_par_DEVMODE( DEVMODE * p, int iParam, HB_BOOL bMandatory ); HB_EXPORT DOCINFO * hbwapi_par_DOCINFO( DOCINFO * p, int iParam, HB_BOOL bMandatory, void *** h ); HB_EXPORT void hbwapi_stor_POINT( POINT * p, int iParam ); HB_EXPORT void hbwapi_stor_RECT( RECT * p, int iParam ); -HB_EXPORT void hbwapi_stor_DEVMODE( DEVMODE * p, int iParam ); HB_EXPORT HDC hbwapi_par_HDC( int iParam ); HB_EXPORT HPEN hbwapi_par_HPEN( int iParam ); HB_EXPORT HBRUSH hbwapi_par_HBRUSH( int iParam ); HB_EXPORT HFONT hbwapi_par_HFONT( int iParam ); +HB_EXPORT PDEVMODE hbwapi_par_PDEVMODE( int iParam ); HB_EXPORT void hbwapi_ret_HDC( HDC p ); HB_EXPORT void hbwapi_ret_HPEN( HPEN p ); HB_EXPORT void hbwapi_ret_HBRUSH( HBRUSH p ); HB_EXPORT void hbwapi_ret_HFONT( HFONT p ); +HB_EXPORT void hbwapi_ret_PDEVMODE( PDEVMODE p ); HB_EXTERN_END diff --git a/harbour/contrib/hbwin/tests/testgdi.prg b/harbour/contrib/hbwin/tests/testgdi.prg index 1fac0e4bf1..428fa6873f 100644 --- a/harbour/contrib/hbwin/tests/testgdi.prg +++ b/harbour/contrib/hbwin/tests/testgdi.prg @@ -16,14 +16,17 @@ #include "hbwin.ch" PROCEDURE Main() + LOCAL cPrinterName := "Microsoft XPS Document Writer" + LOCAL hDC - LOCAL hDEVMODE + LOCAL pDEVMODE LOCAL hRECT LOCAL aRECT LOCAL hOBJECT - hDEVMODE := hb_hash() - ? hDC := wapi_CreateDC( NIL, "Microsoft XPS Document Writer", NIL, hDEVMODE ) + pDEVMODE := __wapi_DEVMODE_New( cPrinterName ) + __wapi_DEVMODE_Set( pDEVMODE, { "dmPaperSize" => WIN_DMPAPER_A3 } ) + ? hDC := wapi_CreateDC( NIL, cPrinterName, NIL, pDEVMODE ) ? wapi_StartDoc( hDC, { "lpszDocName" => "test job" } /* DOCINFO */ ) ? wapi_StartPage( hDC ) diff --git a/harbour/contrib/hbwin/wapi_alloc.c b/harbour/contrib/hbwin/wapi_alloc.c index 30b30380e0..4d8b00007c 100644 --- a/harbour/contrib/hbwin/wapi_alloc.c +++ b/harbour/contrib/hbwin/wapi_alloc.c @@ -94,7 +94,7 @@ HDC hbwapi_par_HDC( int iParam ) { void ** ph = ( void ** ) hb_parptrGC( &s_gc_HDC_funcs, iParam ); - return ph ? ( HDC ) * ph : ( HDC ) hb_parptr( iParam ); + return ph ? ( HDC ) *ph : ( HDC ) hb_parptr( iParam ); } static HB_GARBAGE_FUNC( s_gc_HPEN_release ) @@ -102,10 +102,10 @@ static HB_GARBAGE_FUNC( s_gc_HPEN_release ) void ** ph = ( void ** ) Cargo; /* Check if pointer is not NULL to avoid multiple freeing */ - if( ph && * ph ) + if( ph && *ph ) { /* Destroy the object */ - DeleteObject( ( HPEN ) * ph ); + DeleteObject( ( HPEN ) *ph ); /* set pointer to NULL to avoid multiple freeing */ *ph = NULL; @@ -136,7 +136,7 @@ HPEN hbwapi_par_HPEN( int iParam ) { void ** ph = ( void ** ) hb_parptrGC( &s_gc_HPEN_funcs, iParam ); - return ph ? ( HPEN ) * ph : NULL; + return ph ? ( HPEN ) *ph : NULL; } static HB_GARBAGE_FUNC( s_gc_HBRUSH_release ) @@ -144,10 +144,10 @@ static HB_GARBAGE_FUNC( s_gc_HBRUSH_release ) void ** ph = ( void ** ) Cargo; /* Check if pointer is not NULL to avoid multiple freeing */ - if( ph && * ph ) + if( ph && *ph ) { /* Destroy the object */ - DeleteObject( ( HBRUSH ) * ph ); + DeleteObject( ( HBRUSH ) *ph ); /* set pointer to NULL to avoid multiple freeing */ *ph = NULL; @@ -178,7 +178,7 @@ HBRUSH hbwapi_par_HBRUSH( int iParam ) { void ** ph = ( void ** ) hb_parptrGC( &s_gc_HBRUSH_funcs, iParam ); - return ph ? ( HBRUSH ) * ph : NULL; + return ph ? ( HBRUSH ) *ph : NULL; } static HB_GARBAGE_FUNC( s_gc_HFONT_release ) @@ -186,10 +186,10 @@ static HB_GARBAGE_FUNC( s_gc_HFONT_release ) void ** ph = ( void ** ) Cargo; /* Check if pointer is not NULL to avoid multiple freeing */ - if( ph && * ph ) + if( ph && *ph ) { /* Destroy the object */ - DeleteObject( ( HFONT ) * ph ); + DeleteObject( ( HFONT ) *ph ); /* set pointer to NULL to avoid multiple freeing */ *ph = NULL; @@ -220,5 +220,47 @@ HFONT hbwapi_par_HFONT( int iParam ) { void ** ph = ( void ** ) hb_parptrGC( &s_gc_HFONT_funcs, iParam ); - return ph ? ( HFONT ) * ph : NULL; + return ph ? ( HFONT ) *ph : NULL; +} + +static HB_GARBAGE_FUNC( s_gc_PDEVMODE_release ) +{ + void ** ph = ( void ** ) Cargo; + + /* Check if pointer is not NULL to avoid multiple freeing */ + if( ph && *ph ) + { + /* Destroy the object */ + hb_xfree( *ph ); + + /* set pointer to NULL to avoid multiple freeing */ + *ph = NULL; + } +} + +static const HB_GC_FUNCS s_gc_PDEVMODE_funcs = +{ + s_gc_PDEVMODE_release, + hb_gcDummyMark +}; + +void hbwapi_ret_PDEVMODE( PDEVMODE p ) +{ + if( p ) + { + void ** ph = ( void ** ) hb_gcAllocate( sizeof( PDEVMODE * ), &s_gc_PDEVMODE_funcs ); + + *ph = p; + + hb_retptrGC( ph ); + } + else + hb_retptr( NULL ); +} + +PDEVMODE hbwapi_par_PDEVMODE( int iParam ) +{ + void ** ph = ( void ** ) hb_parptrGC( &s_gc_PDEVMODE_funcs, iParam ); + + return ph ? ( PDEVMODE ) *ph : NULL; } diff --git a/harbour/contrib/hbwin/wapi_wingdi.c b/harbour/contrib/hbwin/wapi_wingdi.c index 50d439388a..d7dc2dba61 100644 --- a/harbour/contrib/hbwin/wapi_wingdi.c +++ b/harbour/contrib/hbwin/wapi_wingdi.c @@ -165,62 +165,6 @@ void hbwapi_stor_RECT( RECT * p, int iParam ) } } -DEVMODE * hbwapi_par_DEVMODE( DEVMODE * p, int iParam, HB_BOOL bMandatory ) -{ - PHB_ITEM pStru = hb_param( iParam, HB_IT_ANY ); - - memset( p, 0, sizeof( DEVMODE ) ); - - p->dmSize = sizeof( DEVMODE ); - - if( pStru && HB_IS_HASH( pStru ) ) - { - p->dmOrientation = ( short ) hb_itemGetNI( hb_hashGetCItemPtr( pStru, "dmOrientation" ) ); - p->dmPaperSize = ( short ) hb_itemGetNI( hb_hashGetCItemPtr( pStru, "dmPaperSize" ) ); - p->dmPaperLength = ( short ) hb_itemGetNI( hb_hashGetCItemPtr( pStru, "dmPaperLength" ) ); - p->dmPaperWidth = ( short ) hb_itemGetNI( hb_hashGetCItemPtr( pStru, "dmPaperWidth" ) ); - p->dmScale = ( short ) hb_itemGetNI( hb_hashGetCItemPtr( pStru, "dmScale" ) ); - p->dmCopies = ( short ) hb_itemGetNI( hb_hashGetCItemPtr( pStru, "dmCopies" ) ); - p->dmDefaultSource = ( short ) hb_itemGetNI( hb_hashGetCItemPtr( pStru, "dmDefaultSource" ) ); - p->dmPrintQuality = ( short ) hb_itemGetNI( hb_hashGetCItemPtr( pStru, "dmPrintQuality" ) ); - p->dmDuplex = ( short ) hb_itemGetNI( hb_hashGetCItemPtr( pStru, "dmDuplex" ) ); - - if( hb_hashGetCItemPtr( pStru, "dmOrientation" ) ) p->dmFields |= DM_ORIENTATION; - if( hb_hashGetCItemPtr( pStru, "dmPaperSize" ) ) p->dmFields |= DM_PAPERSIZE; - if( hb_hashGetCItemPtr( pStru, "dmPaperLength" ) ) p->dmFields |= DM_PAPERLENGTH; - if( hb_hashGetCItemPtr( pStru, "dmPaperWidth" ) ) p->dmFields |= DM_PAPERWIDTH; - if( hb_hashGetCItemPtr( pStru, "dmScale" ) ) p->dmFields |= DM_SCALE; - if( hb_hashGetCItemPtr( pStru, "dmCopies" ) ) p->dmFields |= DM_COPIES; - if( hb_hashGetCItemPtr( pStru, "dmDefaultSource" ) ) p->dmFields |= DM_DEFAULTSOURCE; - if( hb_hashGetCItemPtr( pStru, "dmPrintQuality" ) ) p->dmFields |= DM_PRINTQUALITY; - if( hb_hashGetCItemPtr( pStru, "dmDuplex" ) ) p->dmFields |= DM_DUPLEX; - - return p; - } - else if( bMandatory ) - return p; - - return NULL; -} - -void hbwapi_stor_DEVMODE( DEVMODE * p, int iParam ) -{ - PHB_ITEM pStru = hb_param( iParam, HB_IT_ANY ); - - if( pStru && HB_IS_HASH( pStru ) ) - { - s_hb_hashSetCItemNL( pStru, "dmOrientation" , p->dmOrientation ); - s_hb_hashSetCItemNL( pStru, "dmPaperSize" , p->dmPaperSize ); - s_hb_hashSetCItemNL( pStru, "dmPaperLength" , p->dmPaperLength ); - s_hb_hashSetCItemNL( pStru, "dmPaperWidth" , p->dmPaperWidth ); - s_hb_hashSetCItemNL( pStru, "dmScale" , p->dmScale ); - s_hb_hashSetCItemNL( pStru, "dmCopies" , p->dmCopies ); - s_hb_hashSetCItemNL( pStru, "dmDefaultSource", p->dmDefaultSource ); - s_hb_hashSetCItemNL( pStru, "dmPrintQuality" , p->dmPrintQuality ); - s_hb_hashSetCItemNL( pStru, "dmDuplex" , p->dmDuplex ); - } -} - DOCINFO * hbwapi_par_DOCINFO( DOCINFO * p, int iParam, HB_BOOL bMandatory, void *** ph ) { PHB_ITEM pStru = hb_param( iParam, HB_IT_ANY ); @@ -262,17 +206,97 @@ void hbwapi_strfree_DOCINFO( void ** h ) #if ! defined( HB_OS_WIN_CE ) +HB_FUNC( __WAPI_DEVMODE_NEW ) +{ + HANDLE hPrinter; + void * hDeviceName; + LPCTSTR lpDeviceName = HB_PARSTR( 1, &hDeviceName, NULL ); + + hb_retptr( NULL ); + + if( OpenPrinter( ( LPTSTR ) lpDeviceName, &hPrinter, NULL ) ) + { + LONG lSize = DocumentProperties( 0, hPrinter, ( LPTSTR ) lpDeviceName, NULL, NULL, 0 ); + + if( lSize > 0 ) + { + PDEVMODE pDevMode = ( PDEVMODE ) hb_xgrab( lSize ); + + if( DocumentProperties( 0, hPrinter, ( LPTSTR ) lpDeviceName, pDevMode, pDevMode, DM_OUT_BUFFER ) == IDOK ) + hbwapi_ret_PDEVMODE( pDevMode ); + else + hb_xfree( pDevMode ); + } + + ClosePrinter( hPrinter ); + } + + hb_strfree( hDeviceName ); +} + +HB_FUNC( __WAPI_DEVMODE_SET ) +{ + PDEVMODE pDevMode = hbwapi_par_PDEVMODE( 1 ); + PHB_ITEM pStru = hb_param( 2, HB_IT_ANY ); + + if( pDevMode && pStru && HB_IS_HASH( pStru ) ) + { + pDevMode->dmOrientation = ( short ) hb_itemGetNI( hb_hashGetCItemPtr( pStru, "dmOrientation" ) ); + pDevMode->dmPaperSize = ( short ) hb_itemGetNI( hb_hashGetCItemPtr( pStru, "dmPaperSize" ) ); + pDevMode->dmPaperLength = ( short ) hb_itemGetNI( hb_hashGetCItemPtr( pStru, "dmPaperLength" ) ); + pDevMode->dmPaperWidth = ( short ) hb_itemGetNI( hb_hashGetCItemPtr( pStru, "dmPaperWidth" ) ); + pDevMode->dmScale = ( short ) hb_itemGetNI( hb_hashGetCItemPtr( pStru, "dmScale" ) ); + pDevMode->dmCopies = ( short ) hb_itemGetNI( hb_hashGetCItemPtr( pStru, "dmCopies" ) ); + pDevMode->dmDefaultSource = ( short ) hb_itemGetNI( hb_hashGetCItemPtr( pStru, "dmDefaultSource" ) ); + pDevMode->dmPrintQuality = ( short ) hb_itemGetNI( hb_hashGetCItemPtr( pStru, "dmPrintQuality" ) ); + pDevMode->dmDuplex = ( short ) hb_itemGetNI( hb_hashGetCItemPtr( pStru, "dmDuplex" ) ); + + pDevMode->dmFields = 0; + if( hb_hashGetCItemPtr( pStru, "dmOrientation" ) ) pDevMode->dmFields |= DM_ORIENTATION; + if( hb_hashGetCItemPtr( pStru, "dmPaperSize" ) ) pDevMode->dmFields |= DM_PAPERSIZE; + if( hb_hashGetCItemPtr( pStru, "dmPaperLength" ) ) pDevMode->dmFields |= DM_PAPERLENGTH; + if( hb_hashGetCItemPtr( pStru, "dmPaperWidth" ) ) pDevMode->dmFields |= DM_PAPERWIDTH; + if( hb_hashGetCItemPtr( pStru, "dmScale" ) ) pDevMode->dmFields |= DM_SCALE; + if( hb_hashGetCItemPtr( pStru, "dmCopies" ) ) pDevMode->dmFields |= DM_COPIES; + if( hb_hashGetCItemPtr( pStru, "dmDefaultSource" ) ) pDevMode->dmFields |= DM_DEFAULTSOURCE; + if( hb_hashGetCItemPtr( pStru, "dmPrintQuality" ) ) pDevMode->dmFields |= DM_PRINTQUALITY; + if( hb_hashGetCItemPtr( pStru, "dmDuplex" ) ) pDevMode->dmFields |= DM_DUPLEX; + } + else + hb_errRT_BASE( EG_ARG, 2010, NULL, HB_ERR_FUNCNAME, HB_ERR_ARGS_BASEPARAMS ); +} + +HB_FUNC( __WAPI_DEVMODE_GET ) +{ + PDEVMODE pDevMode = hbwapi_par_PDEVMODE( 1 ); + PHB_ITEM pStru = hb_param( 2, HB_IT_ANY ); + + if( pDevMode && pStru && HB_IS_HASH( pStru ) ) + { + s_hb_hashSetCItemNL( pStru, "dmOrientation" , pDevMode->dmOrientation ); + s_hb_hashSetCItemNL( pStru, "dmPaperSize" , pDevMode->dmPaperSize ); + s_hb_hashSetCItemNL( pStru, "dmPaperLength" , pDevMode->dmPaperLength ); + s_hb_hashSetCItemNL( pStru, "dmPaperWidth" , pDevMode->dmPaperWidth ); + s_hb_hashSetCItemNL( pStru, "dmScale" , pDevMode->dmScale ); + s_hb_hashSetCItemNL( pStru, "dmCopies" , pDevMode->dmCopies ); + s_hb_hashSetCItemNL( pStru, "dmDefaultSource", pDevMode->dmDefaultSource ); + s_hb_hashSetCItemNL( pStru, "dmPrintQuality" , pDevMode->dmPrintQuality ); + s_hb_hashSetCItemNL( pStru, "dmDuplex" , pDevMode->dmDuplex ); + } + else + hb_errRT_BASE( EG_ARG, 2010, NULL, HB_ERR_FUNCNAME, HB_ERR_ARGS_BASEPARAMS ); +} + HB_FUNC( WAPI_CREATEDC ) { void * hDriver; void * hDevice; void * hOutput; - DEVMODE dm; hbwapi_ret_HDC( CreateDC( HB_PARSTRDEF( 1, &hDriver, NULL ), HB_PARSTRDEF( 2, &hDevice, NULL ), HB_PARSTR( 3, &hOutput, NULL ), - hbwapi_par_DEVMODE( &dm, 4, HB_FALSE ) ) ); + hbwapi_par_PDEVMODE( 4 ) ) ); hb_strfree( hDriver ); hb_strfree( hDevice ); @@ -282,10 +306,10 @@ HB_FUNC( WAPI_CREATEDC ) HB_FUNC( WAPI_RESETDC ) { HDC hDC = hbwapi_par_HDC( 1 ); - DEVMODE dm; + PDEVMODE pDEVMODE = hbwapi_par_PDEVMODE( 2 ); - if( hDC && hbwapi_par_DEVMODE( &dm, 2, HB_TRUE ) ) - hb_retl( ResetDC( hDC, &dm ) == hDC ); + if( hDC ) + hb_retl( ResetDC( hDC, pDEVMODE ) == hDC ); else hb_errRT_BASE( EG_ARG, 2010, NULL, HB_ERR_FUNCNAME, HB_ERR_ARGS_BASEPARAMS ); }