Page 1 of 1

Problem with Sprite3D

Posted: Wed Oct 29, 2003 5:26 am
by chris_b
When I run this code I see a red line on the left side of my Sprite3D, because when bilinear filtering is enabled and the sprite is stretched the texture is wrapping around.

It looks like maybe Sprite3D is using Direct3D's Wrap texture addressing mode but I think the Clamp address mode is preferable for #PB_Sprite_Texture if it stops this wrapping problem (Of course I might be completely wrong here, I'm just guessing how Sprite3D and Sprite3DQuality work)

Code: Select all

InitSprite()
InitSprite3D()
InitKeyboard()

OpenScreen(640, 480, 16, "screen")

CreateSprite(0,64,64,#PB_Sprite_Texture)

StartDrawing(SpriteOutput(0))
Box(0,0,32,64,RGB(0,0,64))
Box(32,0,32,64,RGB(255,0,0))
StopDrawing()

CreateSprite3D(0,0)
Sprite3DQuality(1)
ZoomSprite3D(0, 256, 256)

Repeat

FlipBuffers()

ClearScreen(0,0,0)

Start3D()
DisplaySprite3D(0,192,112,255)
Stop3D()

ExamineKeyboard()

Until KeyboardPushed(#PB_Key_Escape)

End

Posted: Tue Dec 23, 2003 10:35 pm
by chris_b
Did no one try running this piece of code?

I still don't know if the problem is with PB or my graphics card...

The sprite should be one half blue, the other half red, but I have an extra red line on the left of my sprite which I think is wrong.

Is it a problem for anyone else that sprite3D textures "wrap around" when the sprite is enlarged?

Posted: Tue Dec 23, 2003 10:40 pm
by Karbon
I get the red line on the left too..

Posted: Tue Dec 23, 2003 10:53 pm
by Num3
Found it....

Just use this...

Code: Select all

StartDrawing(SpriteOutput(0)) 
Box(0,0,32,64,RGB(64,64,64)) 
Box(32,0,31,64,RGB(255,200,100)) ; /// you were writing on pixel line 64 (but the image is 0-63), which clipped over to pixel 0
StopDrawing()  

Posted: Wed Dec 31, 2003 11:53 am
by chris_b
num3 you are mistaken

if you run my original code but with Sprite3DQuality(0) you will see that the red line on the left has not been drawn onto the sprite

it only appears when a 3dsprite is zoomed an bilinear filtering is enabled - which is why I think it is something to do with the texture addressing mode that PureBasic's 3d sprites use, so I think maybe it is only something Fred can solve by adjusting the CreateSprite3D() function.

Posted: Tue Jan 20, 2004 3:20 pm
by chris_b
After reading more about DirectX (and also learning from Danilo how to access the IDirect3DDevice7 interface) I've found a solution to this problem. (Also I realise now that it was wrong to assume that Fred chose which texture addressing mode Sprite3d uses, because wrap is the default mode unless you specify otherwise)

To force clamp texture addressing insert this code after OpenScreen():

Code: Select all

D3Ddevice_interface.IDirect3DDevice7
Start3D()
!extrn _PB_Direct3D_Device
!MOV dword EAX, [_PB_Direct3D_Device]
!MOV dword [v_D3Ddevice_interface],EAX
D3Ddevice_interface\SetTextureStageState(0,12,3)
Stop3D()
This seems to work OK on the machines I've tested it on but maybe it's a good idea to first use D3Ddevice_interface\GetCaps to see if the graphics card supports this texture addressing mode.

(Note: D3Ddevice_interface\GetCaps is also useful to see which Sprite3DBlendingModes are supported. Also it can be used to find the maximum texture sizes, so if you are using Engine3D() related functions you can make your program autiomatically use low resolution textures if high resolution textures are not supported.)