I am looking for a Windows graphics library for use with fb that has ZERO dependence upon 'fbgfx'. This is because of a bug in fbgfx that I simply cannot "live with" and which isn't a high priority to the fb devs to fix. I'm not a dev and never will be - I just need to find some way to write a graphics window app in fb that doesn't suspend operation whenever the window is clicked and dragged.
Is there anything in the fb arsenal that can completely replace fbgfx?
Thanks,
Jim
Graphics library that won't suspend while being dragged?
-
- Posts: 166
- Joined: May 14, 2007 12:20
- Location: Zagreb, Croatia
Re: fb v0.24 examples problems
Hi,
You don't need to replace fbgfx. This bug can be fixed with custom window procedure and hidden fbgfx window. Custom procedure gets all pixels from fbgfx buffer and draw it back to visible window. When you drag window, it continues to paint itself. And also, you can re-size window as this is not possible with fbgfx window.
Here is an example:
gfx.bi:
Example.bas:
You don't need to replace fbgfx. This bug can be fixed with custom window procedure and hidden fbgfx window. Custom procedure gets all pixels from fbgfx buffer and draw it back to visible window. When you drag window, it continues to paint itself. And also, you can re-size window as this is not possible with fbgfx window.
Here is an example:
gfx.bi:
Code: Select all
#Include Once "windows.bi"
Dim Shared As HINSTANCE hInst
hInst = GetModuleHandle(NULL)
Type WndParams
As BITMAPV4HEADER bmi
As Integer scrw, scrh
End Type
Dim Shared As HWND GraphicsHWND
Function WndProc(hWnd As HWND, msg As UINT, wParam As WPARAM, lParam As LPARAM) As LRESULT
Dim As WndParams Ptr wndp
wndp = Cast(WndParams Ptr, GetWindowLong(hWnd, GWL_USERDATA))
Select Case msg
Case WM_CREATE
wndp = Allocate(SizeOf(WndParams))
SetWindowLong(hWnd, GWL_USERDATA, Cast(Long, wndp))
wndp->scrw = GetSystemMetrics(SM_CXSCREEN)
wndp->scrh = GetSystemMetrics(SM_CYSCREEN)
With wndp->bmi
.bV4Size = Len( BITMAPV4HEADER )
.bv4width = wndp->scrw
.bv4height = -wndp->scrh
.bv4planes = 1
.bv4bitcount = 32
.bv4v4compression = 0
.bv4sizeimage = wndp->scrw*wndp->scrh*4
.bV4RedMask = &h0F00
.bV4GreenMask = &h00F0
.bV4BlueMask = &h000F
.bV4AlphaMask = &hF000
End With
SetTimer(hWnd, 1, 1000/25, 0)
Case WM_PAINT
Dim As PAINTSTRUCT ps
Dim As Integer x, y, w, h
BeginPaint(hWnd, @ps)
x = ps.rcPaint.left
y = ps.rcPaint.top
w = ps.rcPaint.right-x
h = ps.rcPaint.bottom-y
StretchDIBits(ps.hdc, x, y, w, h, x, y, w, h, ScreenPtr, CPtr(BITMAPINFO Ptr, @wndp->bmi), DIB_RGB_COLORS, SRCCOPY)
EndPaint(hWnd, @ps)
Case WM_TIMER
RedrawWindow(hWnd, 0, 0, RDW_INVALIDATE)
Case WM_DESTROY
DeAllocate(wndp)
PostQuitMessage(NULL)
End
End Select
Return DefWindowProc(hWnd, msg, wParam, lParam)
End Function
Sub WinMain(wndSize As UInteger)
Dim As MSG uMsg
Dim As WNDCLASS wcls
With wcls
.style = CS_HREDRAW Or CS_VREDRAW
.lpfnWndProc = Cast(WNDPROC, @WndProc)
.hInstance = hInst
.hIcon = LoadIcon(NULL, IDI_APPLICATION)
.hCursor = LoadCursor(NULL, IDC_ARROW)
.hbrBackground = GetStockObject(WHITE_BRUSH)
.lpszMenuName = NULL
.lpszClassName = StrPtr("GfxClass")
End With
If RegisterClass(@wcls) = FALSE Then
MessageBox(NULL, "Failed to register GfxClass!", "Error!", MB_OK Or MB_ICONERROR)
End
EndIf
ScreenRes GetSystemMetrics(SM_CXSCREEN), GetSystemMetrics(SM_CYSCREEN), 32,, -1
GraphicsHWND = CreateWindowEx(NULL, "GfxClass", "GFX Window", WS_OVERLAPPEDWINDOW, CW_USEDEFAULT, CW_USEDEFAULT, LoWord(wndSize), HiWord(wndSize), NULL, NULL, hInst, NULL)
ShowWindow(GraphicsHWND, SW_NORMAL)
UpdateWindow(GraphicsHWND)
While GetMessage(@uMsg, NULL, NULL, NULL) <> FALSE
TranslateMessage(@uMsg)
DispatchMessage(@uMsg)
Wend
End Sub
Sub ScreenCreate(w As Integer, h As Integer)
ThreadCreate(@WinMain, MAKELPARAM(w, h))
Sleep 100, 1
End Sub
Function ScreenWidth(w As Integer = 0) As Integer
Dim As RECT rc
If w > 0 Then
GetWindowRect(GraphicsHWND, @rc)
MoveWindow(GraphicsHWND, rc.left, rc.top, w, rc.bottom-rc.top, FALSE)
EndIf
GetClientRect(GraphicsHWND, @rc)
Return rc.right
End Function
Function ScreenHeight(h As Integer = 0) As Integer
Dim As RECT rc
If h > 0 Then
GetWindowRect(GraphicsHWND, @rc)
MoveWindow(GraphicsHWND, rc.left, rc.top, rc.bottom-rc.top, h, FALSE)
EndIf
GetClientRect(GraphicsHWND, @rc)
Return rc.bottom
End Function
Code: Select all
#Include "gfx.bi"
ScreenCreate(800, 600)
Dim As Integer x1, y1, x2, y2
Randomize Timer
Color RGB(0, 0, 0), RGB(255, 255, 255)
Cls
Line (100, 100)-(600, 600), RGB(255, 0, 0), BF
Do
x1 = Rnd(1)*ScreenWidth()
y1 = Rnd(1)*ScreenHeight()
x2 = Rnd(1)*ScreenWidth()
y2 = Rnd(1)*ScreenHeight()
Line(x1, y1)-(x2, y2)
Sleep 1000/25
Loop
Re: fb v0.24 examples problems
A small remark about gfx.bi:
To avoid warnings due to the bad-type arguments passed to ThreadCreate:
... (100) warning 3(1): Passing different pointer types, at parameter 1 of THREADCREATE()
... (100) warning 1(1): Passing scalar as pointer, at parameter 2 of THREADCREATE()
We can now use easily Threadcall (from version 0.24.0):
ThreadCreate(@WinMain, MAKELPARAM(w, h))
Threadcall WinMain(MAKELPARAM(w, h))
To avoid warnings due to the bad-type arguments passed to ThreadCreate:
... (100) warning 3(1): Passing different pointer types, at parameter 1 of THREADCREATE()
... (100) warning 1(1): Passing scalar as pointer, at parameter 2 of THREADCREATE()
We can now use easily Threadcall (from version 0.24.0):
Threadcall WinMain(MAKELPARAM(w, h))
Re: fb v0.24 examples problems
Looking good so far.
The next thing is to replace InKey() and/or MultiKey() which no longer seem to work as before. I suspect I will be using WM_KEYDOWN trapping or some other Windows mechanism - we'll see.
Any suggestions before I get too far along would be appreciated. I need to allow the user to interact randomly, but transparently as the window is rapidly repainted. The application is basically a real-time numerical instrument display with a strip chart plot.
Thank you,
Jim
The next thing is to replace InKey() and/or MultiKey() which no longer seem to work as before. I suspect I will be using WM_KEYDOWN trapping or some other Windows mechanism - we'll see.
Any suggestions before I get too far along would be appreciated. I need to allow the user to interact randomly, but transparently as the window is rapidly repainted. The application is basically a real-time numerical instrument display with a strip chart plot.
Thank you,
Jim
Re: fb v0.24 examples problems
Under Windows I think multikey calls GetKeyboardState. There are other choices, all involving a relatively large amount of overhead, and the optimal choice probably depends on how many different keys you need to monitor.
Running on a P3:
I did not try to time this, but I suspect that a WM_KEYDOWN/UP handler would also involve a relatively large amount of overhead.
The newer cycle-count macros are here.
Code: Select all
''=============================================================================
#include "counter.bas"
''=============================================================================
''---------------------------------------------------
'' Increase our priority to minimize interruptions.
''---------------------------------------------------
''-------------------------------------------------------
'' These values not recommended for single core systems.
''-------------------------------------------------------
'#define PP REALTIME_PRIORITY_CLASS
'#define TP THREAD_PRIORITY_TIME_CRITICAL
''---------------------------------------------------------------------
'' These values for safety on my single-core P3 with MSE, etc running.
''---------------------------------------------------------------------
#define PP HIGH_PRIORITY_CLASS
#define TP THREAD_PRIORITY_NORMAL
''=============================================================================
dim as any ptr p = allocate(256)
dim as short r
SetProcessAffinityMask( GetCurrentProcess(), 1)
sleep 5000
for i as integer = 1 to 4
counter_begin( 1000000, PP, TP )
counter_end()
print counter_cycles;" cycles"
counter_begin( 1000000, PP, TP )
r = GetAsyncKeyState( VK_X )
counter_end()
print counter_cycles;" cycles"
counter_begin( 1000000, PP, TP )
r = GetKeyState( VK_X )
counter_end()
print counter_cycles;" cycles"
counter_begin( 1000000, PP, TP )
GetKeyboardState( p )
counter_end()
print counter_cycles;" cycles"
print
next
sleep
Code: Select all
0 cycles
602 cycles
520 cycles
5976 cycles
0 cycles
601 cycles
520 cycles
5975 cycles
0 cycles
602 cycles
519 cycles
5973 cycles
0 cycles
601 cycles
521 cycles
5972 cycles
The newer cycle-count macros are here.
Re: Graphics library that won't suspend while being dragged?
fxm-
I tried your suggestion for gfx.bi,
'-------------------------------------------------------------------
We can now use easily Threadcall (from version 0.24.0):
ThreadCreate(@WinMain, MAKELPARAM(w, h))
Threadcall WinMain(MAKELPARAM(w, h))
'-------------------------------------------------------------------
... but when I did, I got this response from fbc -
'-------------------------------------------------------------------
G:\fb.24\fbc -s console -v -mt -w pedantic -t 2048 -lang fb "gfx2-test.bas"
FreeBASIC Compiler - Version 0.24.0 (08-19-2012) for win32
Copyright (C) 2004-2012 The FreeBASIC development team.
standalone, objinfo (libbfd 217)
compiling: gfx2-test.bas -o gfx2-test.asm (main module)
G:\fb.24\fbgfx_on_windows-fix\gfx.bi(16) warning 15(0): No explicit BYREF or BYVAL, at parameter 1 (hWnd) of WndProc()
G:\fb.24\fbgfx_on_windows-fix\gfx.bi(16) warning 15(0): No explicit BYREF or BYVAL, at parameter 2 (msg) of WndProc()
G:\fb.24\fbgfx_on_windows-fix\gfx.bi(16) warning 15(0): No explicit BYREF or BYVAL, at parameter 3 (wParam) of WndProc()
G:\fb.24\fbgfx_on_windows-fix\gfx.bi(16) warning 15(0): No explicit BYREF or BYVAL, at parameter 4 (lParam) of WndProc()
G:\fb.24\fbgfx_on_windows-fix\gfx.bi(70) warning 15(0): No explicit BYREF or BYVAL, at parameter 1 (wndSize) of WinMain()
G:\fb.24\fbgfx_on_windows-fix\gfx.bi(102) warning 15(0): No explicit BYREF or BYVAL, at parameter 1 (w) of ScreenCreate()
G:\fb.24\fbgfx_on_windows-fix\gfx.bi(102) warning 15(0): No explicit BYREF or BYVAL, at parameter 2 (h) of ScreenCreate()
G:\fb.24\fbgfx_on_windows-fix\gfx.bi(109) warning 15(0): No explicit BYREF or BYVAL, at parameter 1 (w) of ScreenWidth()
Aborting due to runtime error 12 ("segmentation violation" signal)
'-------------------------------------------------------------------
The original gfx.bi compiled and linked without any complaint other than the 'warnings'. Did I miss something?
Thanks,
Jim
I tried your suggestion for gfx.bi,
'-------------------------------------------------------------------
We can now use easily Threadcall (from version 0.24.0):
ThreadCreate(@WinMain, MAKELPARAM(w, h))
Threadcall WinMain(MAKELPARAM(w, h))
'-------------------------------------------------------------------
... but when I did, I got this response from fbc -
'-------------------------------------------------------------------
G:\fb.24\fbc -s console -v -mt -w pedantic -t 2048 -lang fb "gfx2-test.bas"
FreeBASIC Compiler - Version 0.24.0 (08-19-2012) for win32
Copyright (C) 2004-2012 The FreeBASIC development team.
standalone, objinfo (libbfd 217)
compiling: gfx2-test.bas -o gfx2-test.asm (main module)
G:\fb.24\fbgfx_on_windows-fix\gfx.bi(16) warning 15(0): No explicit BYREF or BYVAL, at parameter 1 (hWnd) of WndProc()
G:\fb.24\fbgfx_on_windows-fix\gfx.bi(16) warning 15(0): No explicit BYREF or BYVAL, at parameter 2 (msg) of WndProc()
G:\fb.24\fbgfx_on_windows-fix\gfx.bi(16) warning 15(0): No explicit BYREF or BYVAL, at parameter 3 (wParam) of WndProc()
G:\fb.24\fbgfx_on_windows-fix\gfx.bi(16) warning 15(0): No explicit BYREF or BYVAL, at parameter 4 (lParam) of WndProc()
G:\fb.24\fbgfx_on_windows-fix\gfx.bi(70) warning 15(0): No explicit BYREF or BYVAL, at parameter 1 (wndSize) of WinMain()
G:\fb.24\fbgfx_on_windows-fix\gfx.bi(102) warning 15(0): No explicit BYREF or BYVAL, at parameter 1 (w) of ScreenCreate()
G:\fb.24\fbgfx_on_windows-fix\gfx.bi(102) warning 15(0): No explicit BYREF or BYVAL, at parameter 2 (h) of ScreenCreate()
G:\fb.24\fbgfx_on_windows-fix\gfx.bi(109) warning 15(0): No explicit BYREF or BYVAL, at parameter 1 (w) of ScreenWidth()
Aborting due to runtime error 12 ("segmentation violation" signal)
'-------------------------------------------------------------------
The original gfx.bi compiled and linked without any complaint other than the 'warnings'. Did I miss something?
Thanks,
Jim
Re: Graphics library that won't suspend while being dragged?
Yes, you are right.
I tested it and it works only with fbc 0.25.0 (not with fbc 0.24.0)!
changelog.txt (fbc 0.25.0):
Version 0.25.0:
[fixed]
- internal error in ThreadCall parser, potentially causing compiler crashes or miscompilation
Remark:
With fbc 0.24.0, you can suppress the pointer warning message by modifying these two lines:
Sub WinMain(wndSize As UInteger)
Sub WinMain(wndSize As Any Ptr)
ThreadCreate(@WinMain, MAKELPARAM(w, h))
ThreadCreate(@WinMain, Cast(Any Ptr, MAKELPARAM(w, h)))
I tested it and it works only with fbc 0.25.0 (not with fbc 0.24.0)!
changelog.txt (fbc 0.25.0):
Version 0.25.0:
[fixed]
- internal error in ThreadCall parser, potentially causing compiler crashes or miscompilation
Remark:
With fbc 0.24.0, you can suppress the pointer warning message by modifying these two lines:
Sub WinMain(wndSize As Any Ptr)
ThreadCreate(@WinMain, Cast(Any Ptr, MAKELPARAM(w, h)))
-
- Site Admin
- Posts: 6323
- Joined: Jul 05, 2005 17:32
- Location: Manchester, Lancs
Re: Graphics library that won't suspend while being dragged?
I think the parameters all scalars (as opposed to Strings or user-defined types), so you can get rid of the BYVAL/BYREF messages by putting Byval before each parameter name in the sub/function headers.
Or by removing '-w pedantic' from the compiler command line. Although the pedantic warnings can be useful at times.
Or by removing '-w pedantic' from the compiler command line. Although the pedantic warnings can be useful at times.