Author | Topic: AppDesktop():CurrentSize() with Table PC | |
---|---|---|
Jim Lee | AppDesktop():CurrentSize() with Table PC on Thu, 28 Sep 2017 01:35:24 +0200 AppDesktop():CurrentSize() does not change on Table PC when switch on-fly from Landscape <-> Portait. all Layout Calculation, like CenterControl() / CenterPos() than are wrong --- #include "Xbp.ch" #include "Appevent.ch" PROCEDURE APPSYS() RETURN PROCEDURE MAIN LOCAL nEvent, mp1, mp2, oXbp LOCAL oDlg LOCAL aSize := {800,600} LOCAL aPos := {0,0} LOCAL aOld := {0,0} LOCAL aDesk := AppDesktop():CurrentSize() oDlg := XbpDialog():new( AppDesktop(), , aPos, aSize, , .F.) oDlg:taskList := .T. oDlg:title := "Table PC " oDlg:Close := {|| PostAppEvent(xbeP_Close,,,oDlg) } oDlg:create() CenterControl(oDlg) oDlg:SetPos( CenterPos( aSize, aDesk ) ) oDlg:Show() SetAppFocus(oDlg) nEvent := xbe_None DO WHILE nEvent <> xbeP_Close nEvent := AppEvent( @mp1, @mp2, @oXbp, 100 ) DO CASE CASE nEvent = xbe_None Timeout aDesk := ACLONE( AppDesktop():CurrentSize() ) IF aDesk[1] <> aOld[1] .AND. aDesk[2] <> aOld[2] aOld := ACLONE(aDesk) CenterControl(oDlg) oDlg:SetPos( CenterPos( aSize, aDesk ) ) oDlg:SetTitle( "Table PC " + VAR2CHAR(aDesk) ) ENDIF OTHERWISE oXbp:handleEvent( nEvent, mp1, mp2 ) ENDCASE ENDDO SetAppFocus(oDlg) oDlg:destroy() RETURN FUNCTION CenterPos( aSize, aRefSize ) RETURN { Int( (aRefSize[1]-aSize[1]) / 2 ), ; Int( (aRefSize[2]-aSize[2]) / 2 ) } | |
Frank Grossheinrich | Re: AppDesktop():CurrentSize() with Table PC on Fri, 29 Sep 2017 17:35:53 +0200 Jim, the desktop object does not recognize when resolution changes. This is what technically happens here. It disregards that change and returns the initial values when it has been created. See http://www.alaska-software.com/scripts/waa001.dll?WAA_PACKAGE=PUBLICDTS&WAA_FORM=DISPLAYPDR&PDRID=4244 The workaround within the PDR uses BAP. But you can overcome this quite easily: #include "dll.ch" EXTERN LONG GetWindowRect( nhwnd AS UINTEGER, @lprect AS STRING ) IN USER32.DLL (...) aBin := U2Bin(0)+U2Bin(0)+U2Bin(0)+U2Bin(0) GetWindowRect( AppDesktop():getHWND(), @aBin ) nX := Bin2U(aBin) nY := Bin2U( SubStr(aBin,5,4) ) nW := Bin2U( SubStr(aBin,9,4) ) nH := Bin2U( SubStr(aBin,13,4) ) aSize := {nW-nX,nH-nY} Does it help? Frank On 28.09.2017 01:35, Jim Lee wrote: > AppDesktop():CurrentSize() does not change on Table PC when switch on-fly > from Landscape <-> Portait. all Layout Calculation, like CenterControl() / > CenterPos() than are wrong > > --- > > #include "Xbp.ch" > #include "Appevent.ch" > > PROCEDURE APPSYS() > RETURN > > PROCEDURE MAIN > LOCAL nEvent, mp1, mp2, oXbp > LOCAL oDlg > LOCAL aSize := {800,600} > LOCAL aPos := {0,0} > LOCAL aOld := {0,0} > LOCAL aDesk := AppDesktop():CurrentSize() > > oDlg := XbpDialog():new( AppDesktop(), , aPos, aSize, , .F.) > oDlg:taskList := .T. > oDlg:title := "Table PC " > oDlg:Close := {|| PostAppEvent(xbeP_Close,,,oDlg) } > oDlg:create() > CenterControl(oDlg) > oDlg:SetPos( CenterPos( aSize, aDesk ) ) > oDlg:Show() > SetAppFocus(oDlg) > > nEvent := xbe_None > DO WHILE nEvent <> xbeP_Close > nEvent := AppEvent( @mp1, @mp2, @oXbp, 100 ) > DO CASE > CASE nEvent = xbe_None Timeout > aDesk := ACLONE( AppDesktop():CurrentSize() ) > IF aDesk[1] <> aOld[1] .AND. aDesk[2] <> aOld[2] > aOld := ACLONE(aDesk) > CenterControl(oDlg) > oDlg:SetPos( CenterPos( aSize, aDesk ) ) > oDlg:SetTitle( "Table PC " + VAR2CHAR(aDesk) ) > ENDIF > OTHERWISE > oXbp:handleEvent( nEvent, mp1, mp2 ) > ENDCASE > ENDDO > > SetAppFocus(oDlg) > oDlg:destroy() > RETURN > > FUNCTION CenterPos( aSize, aRefSize ) > RETURN { Int( (aRefSize[1]-aSize[1]) / 2 ), ; > Int( (aRefSize[2]-aSize[2]) / 2 ) } > > > | |
Jim Lee | Re: AppDesktop():CurrentSize() with Table PC on Sat, 30 Sep 2017 23:33:30 +0200 hi, i have read PDR 4244. i agree that it is not common to change the system's screen resolution via Control Pane. same Problem but other time. today we have Table PC and 2nd Monitor where we can move Apps to, each with own DPI scale factor, so we need right size from Appdesktop(). as you say how easy it is to fix i wonder why Alaska have not fix it yet since 2001 ?! p.s. i use GDI32 GetDeviceCaps() to find virtuel and native Desktop size. | |
James Loughner | Re: AppDesktop():CurrentSize() with Table PC on Sun, 01 Oct 2017 16:16:43 -0400 Since Alaska uses it own control loop and filters outs out events not supported by its framework it may help to use a Windows control loop which can be done something like this. PROCEDURE WindowsLoop(oParent) LOCAL nEvent:=0,xMp1:=NIL,xMp2:=NIL,oXbp:=NIL DO WHILE oParent:Status() = XBP_STAT_CREATE nEvent := AppEvent( @xMp1, @xMp2, @oXbp, 1 ) IF !Empty( nEvent ) oXbp:HandleEvent( nEvent, xMp1, xMp2) ELSE IF nEvent == 0 HandleWinEvents() ENDIF ENDIF ENDDO RETURN PROCEDURE HandleWinEvents() LOCAL rc IF sMsg == NIL sMsg := space(28) ENDIF DO WHILE (rc := PeekMessage( @sMsg, 0, 0, 0, 1 ) ) <> 0 IF rc == -1 EXIT ENDIF TranslateMessage( @sMsg ) DispatchMessage( @sMsg ) ENDDO RETURN FUNCTION PeekMessage( sMsg, hwnd, wMsgFilterMin,wMsgFilterMax, wRemoveMsg ) STATIC tpl := NIL IF tpl = NIL tpl := DllPrepareCall( "user32.dll", DLL_STDCALL, "PeekMessageA" ) ENDIF RETURN DllExecuteCall( tpl,; @sMsg, hwnd, wMsgFilterMin, wMsgFilterMax, wRemoveMsg ) You would need to tweak this for the specific windows message Jim On 09/30/2017 05:33 PM, Jim Lee wrote: > hi, > > i have read PDR 4244. > i agree that it is not common to change the system's screen resolution via > Control Pane. > > same Problem but other time. > > today we have Table PC and 2nd Monitor where we can move Apps to, each with > own DPI scale factor, so we need right size from Appdesktop(). > > as you say how easy it is to fix i wonder why Alaska have not fix it yet > since 2001 ?! > > p.s. i use GDI32 GetDeviceCaps() to find virtuel and native Desktop size. > > | |
James Loughner | Re: AppDesktop():CurrentSize() with Table PC on Sun, 01 Oct 2017 16:39:15 -0400 oops missed a couple of func On 10/01/2017 04:16 PM, James Loughner wrote: > Since Alaska uses it own control loop and filters outs out events not > supported by its framework it may help to use a Windows control loop > which can be done something like this. > > PROCEDURE WindowsLoop(oParent) > LOCAL nEvent:=0,xMp1:=NIL,xMp2:=NIL,oXbp:=NIL > DO WHILE oParent:Status() = XBP_STAT_CREATE > nEvent := AppEvent( @xMp1, @xMp2, @oXbp, 1 ) > IF !Empty( nEvent ) > oXbp:HandleEvent( nEvent, xMp1, xMp2) > ELSE > IF nEvent == 0 > HandleWinEvents() > ENDIF > ENDIF > ENDDO > RETURN > > PROCEDURE HandleWinEvents() > LOCAL rc > IF sMsg == NIL > sMsg := space(28) > ENDIF > DO WHILE (rc := PeekMessage( @sMsg, 0, 0, 0, 1 ) ) <> 0 > IF rc == -1 > EXIT > ENDIF > TranslateMessage( @sMsg ) > DispatchMessage( @sMsg ) > ENDDO > RETURN > > FUNCTION PeekMessage( sMsg, hwnd, wMsgFilterMin,wMsgFilterMax, wRemoveMsg ) > STATIC tpl := NIL > IF tpl = NIL > tpl := DllPrepareCall( "user32.dll", DLL_STDCALL, "PeekMessageA" ) > ENDIF > RETURN DllExecuteCall( tpl,; > @sMsg, hwnd, wMsgFilterMin, wMsgFilterMax, wRemoveMsg ) > FUNCTION TranslateMessage( sMsg ) STATIC tpl := NIL IF tpl = NIL tpl := DllPrepareCall( "user32.dll", DLL_STDCALL,"TranslateMessage" ) ENDIF RETURN DllExecuteCall( tpl, @sMsg ) <> 0 FUNCTION DispatchMessage( sMsg ) STATIC tpl := NIL IF tpl = NIL tpl := DllPrepareCall( "user32.dll", DLL_STDCALL,"DispatchMessageA" ) ENDIF RETURN DllExecuteCall( tpl, @sMsg ) > > You would need to tweak this for the specific windows message > > Jim > > On 09/30/2017 05:33 PM, Jim Lee wrote: >> hi, >> >> i have read PDR 4244. >> i agree that it is not common to change the system's screen resolution >> via >> Control Pane. >> >> same Problem but other time. >> >> today we have Table PC and 2nd Monitor where we can move Apps to, each >> with >> own DPI scale factor, so we need right size from Appdesktop(). >> >> as you say how easy it is to fix i wonder why Alaska have not fix it yet >> since 2001 ?! >> >> p.s. i use GDI32 GetDeviceCaps() to find virtuel and native Desktop size. >> >> > | |
Jim Lee | Re: AppDesktop():CurrentSize() with Table PC on Mon, 02 Oct 2017 20:03:54 +0200 hi, thx for code. it is not the problem to get a event when switch layout. i use a thread / timeout to check Desk Size. when using AppDesktop():CurrentSize() i wonder why it does not switch layout. now i know it simply does not work correct and old PDR 4244 still not fixed. |