Jump to content

[Help] Use mysql instead Get & Set accountdata


SinaAmp

Recommended Posts

  • Moderators
Posted
2 hours ago, SinaAmp said:

I get element data from client side which is static for setting up timer

Isn't that cause of the problem?

Probably, can you show me that clientside part just to be sure?

Posted

here:

Spoiler
function checkHunger()
	local Hunger = tonumber(getElementData(localPlayer, "Hunger"))
	if Hunger and Hunger >= 0 then
		setElementData(localPlayer, "Hunger", Hunger - 1)
	end
	if Hunger <= 20 then
		outputChatBox("You need to feed as fast as possible.", 255, 0, 0)
		playSoundFrontEnd(40)
	end
	if Hunger == 0 then	
		if not isPedDead(localPlayer) then
			local hp = getElementHealth(localPlayer)
			setElementHealth(localPlayer, hp - 30)
		end
	end
end
setTimer(checkHunger, 60000, 0)

function onClientPlayerSpawn()
	setElementData(source, "Hunger", 100)
end
addEventHandler("onClientPlayerSpawn", root, onClientPlayerSpawn)

function checkThirst()
	local Thirst = tonumber(getElementData(localPlayer, "Thirst"))
	if Thirst and Thirst >= 0 then
		setElementData(localPlayer, "Thirst", Thirst - 1)
	end
	if Thirst <= 20 then
		outputChatBox("You need to drink something as fast as possible.", 255, 0, 0)
		playSoundFrontEnd(40)
	end
	if Thirst == 0 then	
		if not isPedDead(localPlayer) then
			local hp = getElementHealth(localPlayer)
			setElementHealth(localPlayer, hp - 30)
		end
	end
end
setTimer(checkThirst, 60000, 0)

function onClientPlayerSpawn()
	setElementData(source, "Thirst", 100)
end
addEventHandler("onClientPlayerSpawn", root, onClientPlayerSpawn)

 

 

  • Moderators
Posted
2 hours ago, SinaAmp said:
setTimer(checkThirst, 60000, 0)

This update rate is fine, unless you have about/more than ~40 players in your server.

 

Fix for that:

Client (set Thirst with sync disabled)

Thirst = Thirst - 1
setElementData(localPlayer, "Thirst", Thirst, false)

+

https://wiki.multitheftauto.com/wiki/TriggerServerEvent

(https://wiki.multitheftauto.com/wiki/TriggerLatentServerEvent)

+
Server (set Thirst with sync disabled)

setElementData(client, "Thirst", Thirst, false)

 

 

 

  • Thanks 1
Posted

@IIYAMA sorry for late response

i think my way of creating hunger and thirst system with get/setelementdata is complatly wrong

and that cause of performance issues in future

may i use only triggerevents and a variable to process

  • Like 1
Posted

@IIYAMA i tryed  to do this method can you please review my code

i commented near the lines i had problem [ -- this ]

server:

function AccDatacallback(AccData, player, account, AccName)
	local result = dbPoll( AccData, 0 )
	if(result) then
      if(#result > 0) then
         for _,row in ipairs(result) do
            local Hunger = row["Hunger"]
            local Thirst = row["Thirst"]
            break
         end
      end
   end
end
function afterlogin (_,Acc)
    local AccName = getAccountName(Acc)
    dbQuery(AccDatacallback,{source, account, AccName},db,"SELECT Hunger,Thirst FROM stats WHERE Account=?", AccName)
end
addEventHandler ("onPlayerLogin",root, afterlogin)

-- function to send hunger and thirst to client for process 

function sendhsdata (_, Acc, Hunger ,Thirst) -- ***this***
   local AccName = getAccountName(Acc)
   local hsdata = dbPoll(dbQuery(db,"SELECT Hunger,Thirst FROM stats WHERE Account=?", AccName), -1)
   local Hunger = hsdata["Hunger"] -- ***this***
   local Thirst = hsdata["Thirst"] -- ***this***
end
addEvent( "onSendData", true ) -- ***this***
addEventHandler( "onSendData", root, sendhsdata) -- ***this***



-- Data saving function
function saveAccountData (player)
   local playerAccount = getPlayerAccount(player) 
   if(playerAccount) then
      if(isGuestAccount(playerAccount)) then return end
   end
   local AccName = getAccountName(playerAccount)
   local Hungers = triggerClientEvent(player, "onSendPData", playersource, PHunger) -- ***this***
   local Thirsts = triggerClientEvent(player, "onSendPData", playersource, PThirst) -- ***this***
   dbExec(db,"UPDATE stats SET Hunger=?, Thirst=? WHERE Account=?",Hungers, Thirsts, AccName)
end

addEventHandler ( 'onPlayerQuit', root, function ( )
    saveAccountData(source)
end )

client:

function checkHunger(PHunger)
	local Hunger = triggerServerEvent("onSendData", resourceRoot, Hunger) -- ***this***
	if Hunger and Hunger >= 0 then
		PHunger = Hunger - 1 -- ***this***
	end
	if Hunger <= 20 then
		outputChatBox("You need to feed as fast as possible.", 255, 0, 0)
		playSoundFrontEnd(40)
	end
	if Hunger == 0 then	
		if not isPedDead(localPlayer) then
			local hp = getElementHealth(localPlayer)
			setElementHealth(localPlayer, hp - 30)
		end
	end
end
setTimer(checkHunger, 60000, 0)
addEvent( "onSendPHData", true ) -- ***this***
addEventHandler( "onSendPHData", localPlayer, checkHunger ) -- ***this***



function onClientPlayerSpawn()
	setElementData(source, "Hunger", 100)
end
addEventHandler("onClientPlayerSpawn", root, onClientPlayerSpawn)




function checkThirst(PThirst) -- ***this***
	local Thirst = triggerServerEvent("onSendData", resourceRoot, Thirst) -- ***this***
	if Thirst and Thirst >= 0 then
		PThirst = Thirst - 1 -- ***this***
	end
	if Thirst <= 20 then
		outputChatBox("You need to drink something as fast as possible.", 255, 0, 0)
		playSoundFrontEnd(40)
	end
	if Thirst == 0 then	
		if not isPedDead(localPlayer) then
			local hp = getElementHealth(localPlayer)
			setElementHealth(localPlayer, hp - 30)
		end
	end
end
setTimer(checkThirst, 60000, 0)
addEvent( "onSendPTData", true ) -- ***this***
addEventHandler( "onSendPTData", localPlayer, checkThirst ) -- ***this***



function onClientPlayerSpawn()
	setElementData(source, "Thirst", 100)
end
addEventHandler("onClientPlayerSpawn", root, onClientPlayerSpawn)

 

  • Moderators
Posted
35 minutes ago, SinaAmp said:
local Thirst = triggerServerEvent("onSendData", resourceRoot, Thirst) -- ***this***

triggerServerEvent is unable to receive data.

 

If you take a look at the syntax of that function, you will see that it only returns a boolean(true/false):

676649160_Schermafbeelding2022-02-07om19_04_15.png.d0f41e82a6696070acef6b5216c742be.png

https://wiki.multitheftauto.com/wiki/TriggerServerEvent

 

You can make it possible using this library, but that wouldn't create a solid system. The server should be in charge of the hunger and Thirst values.

 

What you want is the following:

Server

  • A timer (or multiple timers)
  • This one gets the Hunger and Thirst
  • Updates the Hunger and Thirst (-1) according to your needs.
  • Sets the health or kills the player.
  • triggerClientEvent (or elementdata with https://wiki.multitheftauto.com/wiki/AddElementDataSubscriber + setElementData [syncMode is "subscribe"])

 

Client

  • Just updates the UI to show the player his hunger and thirst values.

 

 

 

 

  • Like 1
Posted

sorry @IIYAMA i can't understand why should i use triggerClientEvent in server side when i use your library and calc hunger and thirst in server side

i dont know how to get my processed hunger and thirst from server side

please look at this:

server:

Spoiler
function AccDatacallback(AccData, player, account, AccName)
	local result = dbPoll( AccData, 0 )
	if(result) then
      if(#result > 0) then
         for _,row in ipairs(result) do
            Hunger = row["Hunger"]
            Thirst = row["Thirst"]
            break
         end
      end
   end
end
function afterlogin (_,Acc)
    local AccName = getAccountName(Acc)
    dbQuery(AccDatacallback,{source, account, AccName},db,"SELECT Hunger,Thirst FROM stats WHERE Account=?", AccName)
end
addEventHandler ("onPlayerLogin",root, afterlogin)

-- calc hunger and thirst

function checkHunger(player, PHunger)
	if Hunger and Hunger >= 0 then
		PHunger = Hunger - 1
	end
	if PHunger <= 20 then
		outputChatBox("You need to feed as fast as possible.", 255, 0, 0)
	end
	if PHunger == 0 then	
		if not isPedDead(Player) then
			local hp = getElementHealth(Player)
			setElementHealth(Player, hp - 30)
		end
	end
end
setTimer(checkHunger, 30000, 0)



function checkThirst(player, PThirst)
	if Thirst and Thirst >= 0 then
		PThirst = Thirst - 1
	end
	if PThirst <= 20 then
		outputChatBox("You need to drink something as fast as possible.", 255, 0, 0)
		playSoundFrontEnd(40)
	end
	if PThirst == 0 then	
		if not isPedDead(Player) then
			local hp = getElementHealth(Player)
			setElementHealth(Player, hp - 30)
		end
	end
end
setTimer(checkThirst, 30000, 0)



-- Data saving function
   function saveAccountData (player)
      local playerAccount = getPlayerAccount(player) 
      if(playerAccount) then
         if(isGuestAccount(playerAccount)) then return end
      end
      local AccName = getAccountName(playerAccount)
      local Hungers = PHunger
      local Thirsts = PThirst
      dbExec(db,"UPDATE stats SET Hunger=?, Thirst=? WHERE Account=?",Hungers, Thirsts, AccName)
   end
   
   addEventHandler ( 'onPlayerQuit', root, function ( )
       saveAccountData(source)
   end )

 

client:

Spoiler
callserver ("checkHunger","PHunger")

 

 

  • Moderators
Posted
28 minutes ago, SinaAmp said:

when i use your library

First of all, you do not need to use my library. Only if you are going to make use of callbacks.

 

29 minutes ago, SinaAmp said:

i dont know how to get my processed hunger and thirst from server side

You do not get the hunger, you send it using triggerClientEvent.

 

 

for _,row in ipairs(result) do

    Hunger = row["Hunger"]

    Thirst = row["Thirst"]

    break

end

local row = result[1]
Hunger = row["Hunger"]
Thirst = row["Thirst"]

      

 

32 minutes ago, SinaAmp said:
function checkHunger(player, PHunger)
	if Hunger and Hunger >= 0 then
		PHunger = Hunger - 1
	end
	if PHunger <= 20 then
		outputChatBox("You need to feed as fast as possible.", 255, 0, 0)
	end
	if PHunger == 0 then	
		if not isPedDead(Player) then
			local hp = getElementHealth(Player)
			setElementHealth(Player, hp - 30)
		end
	end
end
setTimer(checkHunger, 30000, 0)

You should get here the current hunger values from the database.

https://wiki.multitheftauto.com/wiki/DbPrepareString

Finish the code yourself.

local players = getElementsByType("player")

local queryString = dbPrepareString( db, "SELECT Hunger,Thirst FROM stats WHERE Account IN ( "

-- loop with player account names
queryString = queryString .. dbPrepareString( db, "?, ",  AccName)
-- loop end

queryString = queryString .. " )"
  
 
local handle = dbQuery( db, queryString )
  
-- Receive data here and combine the correct database data with the player.

 

 

 

 

  • Moderators
Posted
10 hours ago, SinaAmp said:

why i need to get hunger and thirst in 'checkhunger' function when i got them from 'afterlogin' function?

 

Because you didn't save it there. You have not written a (memory) cache for your database.

Posted

i got this error repeatly

Database result uncollected after 5 minutes. [Query: SELECT Hunger,Thirst FROM stats WHERE Account IN ( NULL,  )]

  • Moderators
Posted
48 minutes ago, SinaAmp said:

i got this error repeatly

Database result uncollected after 5 minutes. [Query: SELECT Hunger,Thirst FROM stats WHERE Account IN ( NULL,  )]

That happens when you fire a query (with a callback) and restart/stop the resource directly after that.

Posted

edited server side:

Spoiler
-- calc hunger and thirst

function checkHunger(playersource,PHunger)
	local players = getElementsByType("player")
	local queryString = dbPrepareString( db, "SELECT Hunger,Thirst FROM stats WHERE Account IN ( ")
	queryString = queryString .. dbPrepareString( db, "?, ",  AccName)
	queryString = queryString .. " )"
	local handle = dbQuery( db, queryString )
	setTimer(function()
	if Hunger and Hunger >= 0 then
		local row = handle[1]
        Hunger = row["Hunger"]
		PHunger = Hunger - 1
		outputDebugString(PHunger)
	end
	if PHunger <= 20 then
		outputChatBox("You need to feed as fast as possible.", 255, 0, 0)
	end
	if PHunger == 0 then	
		if not isPedDead(Player) then
			local hp = getElementHealth(Player)
			setElementHealth(Player, hp - 30)
		end
	end
end,30000,0)
end
triggerClientEvent("onGetData", root,PHunger)

 

but i got this error:

server triggered client side event but event is not added

  • Moderators
Posted
20 minutes ago, SinaAmp said:

server triggered client side event but event is not added

 

20 minutes ago, SinaAmp said:
triggerClientEvent("onGetData", root,PHunger)

You are sending a message to all clients/players directly when the server is executing the script. The clients/players haven't loaded their scripts yet, to receive the message.

Posted (edited)

sorry i wasted your time @IIYAMAthank you for help

addEventHandler("onPlayerResourceStart", root, function(hungerandthirst)
	if loadedResource == resource then
		triggerClientEvent(source, "onGetData", resourceRoot,PHunger)
	end
end)

@Burak5312 bro can you complete this part?

Edited by SinaAmp
  • Like 1
  • Moderators
Posted
32 minutes ago, SinaAmp said:

sorry i wasted your time @IIYAMAthank you for help

No worries. BTW, you can only send the hunger value when you know which account this player has logged in to. There is a chance that the player hasn't logged in yet when the resource has been loaded.

On closer inspection it might be better to try it on onPlayerLogin and using a login panel to delay the user-interaction.

addEventHandler ("onPlayerLogin",root, afterlogin)

 

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 account

Sign in

Already have an account? Sign in here.

Sign In Now
  • Recently Browsing   0 members

    • No registered users viewing this page.
×
×
  • Create New...