Overkillz Posted October 7, 2019 Share Posted October 7, 2019 Hello guys, today I've just started to work with shaders and renderTargets. I want to draw individually on each rendertarget but my question is: Do I have to create inside the table each shader or create a global one for all of them ? Which one is the best way ? Here is a example about what I say -- METHOD #1 { player = player, shader = dxCreateShader(shaderFile), renderTarget = dxCreateRenderTarget(arg1, arg2, true) } { player = player2, shader = dxCreateShader(shaderFile), renderTarget = dxCreateRenderTarget(arg1, arg2, true) } { player = player3, shader = dxCreateShader(shaderFile), renderTarget = dxCreateRenderTarget(arg1, arg2, true) } -- METHOD #2 globalShader = dxCreateShader(shaderFile) { player = player, renderTarget = dxCreateRenderTarget(arg1, arg2, true) } { player = player2, renderTarget = dxCreateRenderTarget(arg1, arg2, true) } { player = player3, renderTarget = dxCreateRenderTarget(arg1, arg2, true) } Thanks for reading. Regards. Link to comment
Moderators IIYAMA Posted October 7, 2019 Moderators Share Posted October 7, 2019 @Overkillz You can do it with 1 shader, and just before drawing, switch the texture value of it foreach player. But I am not sure, how high the performance penalty is. So both ways will work, but I am not sure which one is the best one. 1 Link to comment
Awang Posted October 7, 2019 Share Posted October 7, 2019 I suggest you to make shaders for every player or you can optimalize the method by create shaders for players who are in streamed in and destroy for who are exiting from the streaming range. Because MTA only can use 1 core of your CPU in client side, its a good tactic to depend more on memory instead on CPU by making texture moving in the render function before every player. local streamed_players = {} function render() for player in pairs(streamed_players) do -- Do what you want with the shader and renderTarget end end addEventHandler( "onClientElementStreamIn",root,function() if getElementType(source) == "player" then streamed_players[source] = {shader = dxCreateShader(shaderFile), renderTarget = dxCreateRenderTarget(arg1, arg2, true)} end end) addEventHandler( "onClientElementStreamOut",root,function() if getElementType(source) == "player" then streamed_players[source] = nil end end) About RenderTargets, some videocard not really like them, so I suggest you, if you want to just put some material together and after you not want to really change them, than you can read the texture from the target and save out into a simple texture. local target = dxCreateRenderTarget(arg1, arg2, true) dxSetRenderTarget(target) dxDrawImage(...) dxDrawText(...) dxSetRenderTarget() local texture = dxCreateTexture(dxGetTexturePixels(target)) target = nil Basically, you burn together the textures and after you save out, but you cant change it after all. 1 Link to comment
Overkillz Posted October 7, 2019 Author Share Posted October 7, 2019 (edited) @IIYAMA Yes, its working pretty well, but Im not sure if that its causing the problem about what Im talking at the following lines @Awang Well, basically I have been doing what you have just said. But I have a weird bug. I tried to do a simple (very simple) version of the code. Why the image is being drawn on the car and the screen ? I just want to draw it on the car but, weird ... function loadMain() theVehicle = createVehicle(411,0,0,5) theShader = dxCreateShader("lights.fx") theRenderTarget = dxCreateRenderTarget(960, 540, true) engineApplyShaderToWorldTexture(theShader, "decalmap", theVehicle) drawContentInRT(theRenderTarget) end function drawContentInRT(rt) if rt then dxSetRenderTarget(rt, true) dxDrawImage(480,220,210,210,"img/test1.png",0,0,0,tocolor(255,255,255,255)) dxDrawImage(510,220,210,210,"img/test2.png",0,0,0,tocolor(255,255,255,255)) dxSetRenderTarget() dxSetShaderValue(theShader, "gTexture", rt) addEventHandler("onClientRender",root,renderContent) end end function renderContent() if theRenderTarget then dxDrawImage(0,0,960,540,theRenderTarget,0,0,0,tocolor(255,255,255,255)) end end loadMain() --## SHADER texture gTexture; technique hello { pass P0 { Texture[0] = gTexture; } } Edited October 7, 2019 by Overkillz 1 Link to comment
Moderators IIYAMA Posted October 7, 2019 Moderators Share Posted October 7, 2019 (edited) 25 minutes ago, Overkillz said: Why the image is being drawn on the car and the screen ? I just want to draw it on the car but, weird ... Just don't render it with renderContent. Shaders applied to game elements do not require updates every frame. (Unless you want to update them with Lua > update the texture or update the shader values) Edited October 7, 2019 by IIYAMA 1 Link to comment
Overkillz Posted October 7, 2019 Author Share Posted October 7, 2019 (edited) 9 minutes ago, IIYAMA said: Just don't render it with renderContent. Shaders applied to game elements do not require updates every frame. (Unless you want to update them with Lua) @IIYAMA Oh ! Wasn't aware about it. I thought that game elements needed to be like a normal draw (Rendered each frame). Thats are even better news for me respecting the CPU Usage I have the last question. onClientRestore must be present on the code when the player minimize and restore to prevent issues ? Edited October 7, 2019 by Overkillz Adding a question 1 Link to comment
Moderators IIYAMA Posted October 7, 2019 Moderators Share Posted October 7, 2019 6 minutes ago, Overkillz said: I have the last question. onClientRestore must be present on the code when the player minimize and restore to prevent issues ? To be honest, I haven't encountered any issues with it yet. But I am pretty sure that it can have issues when memory has been wiped because of an <unknown situation>. I would suggest following Awang his suggestion: 3 hours ago, Awang said: About RenderTargets, some videocard not really like them, so I suggest you, if you want to just put some material together and after you not want to really change them, than you can read the texture from the target and save out into a simple texture. If applied, you probably do not need that onClientRestore event. It might also improve performance, because it is static. local texture = dxCreateTexture(dxGetTexturePixels(rt)) dxSetShaderValue(theShader, "gTexture", texture) 2 Link to comment
Recommended Posts
Create an account or sign in to comment
You need to be a member in order to leave a comment
Create an account
Sign up for a new account in our community. It's easy!
Register a new accountSign in
Already have an account? Sign in here.
Sign In Now