-
Posts
1,803 -
Joined
-
Last visited
-
Days Won
8
Everything posted by Citizen
-
You have to login the player with the internal system at the same time using the logIn function. You will also need to register the player using the addAccount function. And finally logout the player from the internal account system when he logs off. Check the modification I made to playerLogin, registerPlayer and the handler of onPlayerLogOut (I added comments): local blockedUsernames = {["console"] = true,["admin"]= true,["moderator"]= true,["guest"]= true,["none"]= true,["sams"]= true,["[sams]"]= true,["sa agencia de casas"]= true,["sa_agencia_de_casas"] = true} function playerLogin(username,password,serial) if getElementData(source,"loggedIn") then return triggerClientEvent(source,"SAlogin.errorBox",source,"Ya estas logeado.") end local ip = getPlayerIP(source) local playername = getPlayerName(source) local playerQuery = executeSQLQuery("SELECT id, loggedin FROM user_data WHERE username = ? AND pwsalted = ? LIMIT 1",username,password) if playerQuery and #playerQuery > 0 then if (playerQuery[1].loggedin == 1) then return triggerClientEvent(source,"SAlogin.errorBox",source,"Tu cuenta ya se encuentra en uso.") end local account = setElementData(source,"username",username) local id = setElementData(source,"id",playerQuery[1].id) local internalAccount = getAccount( username, password ) -- gets the internal player account local internalLoggin = logIn( source, internalAccount, password ) -- logs in the player using the internal account if account and id and internalLoggin then local thetime = getRealTime() local MM = thetime.month+1 if MM < 10 then MM = "0"..MM end local DD = thetime.monthday if DD < 10 then DD = "0"..DD end local thedate = (thetime.year+1900).."-"..MM.."-"..DD local ip = getPlayerIP(source) local serial = getPlayerSerial(source) executeSQLQuery("UPDATE user_data SET lastlogin = '"..thedate.."', ip = '"..ip.."', serial = '"..serial.."', loggedin = 1 WHERE username = '"..username.."'") outputChatBox("Usted se a logeado con el nombre de usuario: "..username,source,0,255,255) setElementData(source,"loggedIn",true) triggerEvent("onPlayerLogIn",source,playerQuery[1].id,username) triggerClientEvent(source,"SAlogin.clearLoginGUI",source) outputServerLog(("SAlogin: %s has successfully logged in as %q. (IP: %s Serial: %s)"):format(playername,username,ip,serial)) triggerClientEvent(source,"SAlogin.hideLogin",source,true) else triggerClientEvent(source,"SAlogin.errorBox",source,"Error de login.") end elseif playerQuery then triggerClientEvent(source,"SAlogin.errorBox",source,"Contraseña no especificada.") outputServerLog(("SAlogin: %s failed to log in as %q. Wrong password. (IP: %s Serial: %s)"):format(playername,username,ip,serial)) else triggerClientEvent(source,"SAlogin.errorBox",source,"Ocurrio un error, por favor intentalo de nuevo") end end addEvent("SAlogin.playerLogin",true) addEventHandler("SAlogin.playerLogin",root,playerLogin) function registerPlayer(username,password,email) if username and password and email then if not blockedUsernames[username] then if not username:match("[%s%p]") then local accountQuery = executeSQLQuery("SELECT id FROM user_data WHERE username=? LIMIT 1",username) if accountQuery and #accountQuery == 0 then local sqlAccount = executeSQLInsert("user_data","'"..username.."','"..password.."','"..email.."',0,0,1000,0","'username','pwsalted','email','wanted','jailed','money', 'loggedin'") local internalAccount = addAccount( username, password ) -- creates the internal player account if sqlAccount and internalAccount then triggerClientEvent(source,"SAlogin.showLogin",source) triggerClientEvent(source,"SAlogin.errorBox",source,"Registro de la cuenta terminada. Su nombre de usuario es "..username..". Recuerdalo.") else triggerClientEvent(source,"SAlogin.errorBox",source,"Error en registro de cuenta") end elseif accountQuery and #accountQuery > 0 then triggerClientEvent(source,"SAlogin.errorBox",source,"Este nombre de cuenta ya esta registrado") else triggerClientEvent(source,"SAlogin.errorBox",source,"Error en registro de cuenta") end else triggerClientEvent(source,"SAlogin.errorBox",source,"El nombre de usuario que se registra no debe tener ningun espacio o puntuacion") end else triggerClientEvent(source,"SAlogin.errorBox",source,"Esta nombre de usuario esta bloqueado") end end end addEvent("SAlogin.playerRegisterAccount",true) addEventHandler("SAlogin.playerRegisterAccount",root,registerPlayer) function markAsLogOut() local id = getElementData(source,"id") if id then executeSQLUpdate("user_data","loggedin = 0","id = "..id) end end addEventHandler("onPlayerQuit", root,markAsLogOut) addEvent("onPlayerLogOut",true) addEventHandler("onPlayerLogOut",root,function() setElementData(source,"loggedIn",false) local username = getElementData(source,"username") local id = getElementData(source,"id") if id then executeSQLUpdate("user_data","loggedin = 0","id = "..id) logOut( source ) -- logs the player off from its internal account end if not username then username = "N/A" end local ip = getPlayerIP(source) local serial = getPlayerSerial(source) if ip and serial then outputServerLog("SAlogin: "..getPlayerName(source).." ha cerrado la sesion '"..username.."' (IP: "..ip.." Serial: "..serial..")") end setElementData(source,"username",nil) setElementData(source,"id",nil) triggerClientEvent(source,"SAlogin.showLogin",source) killPed(source) fadeCamera(source,false) setElementInterior(source,0) setElementDimension(source,0) end) executeSQLQuery("CREATE TABLE IF NOT EXISTS user_data (id INTEGER PRIMARY KEY AUTOINCREMENT, username TEXT, pwsalted TEXT, groups TEXT, email TEXT, money INTEGER, wanted TINYINT, jailed BOOLEAN, lastnick TEXT, lastlogin TEXT, loggedin INTEGER, ip TEXT, serial TEXT)")
-
If this is the exact error you get, then you forgot an 'e' when you call triggerServerEvent in client/main.lua. It's onRequestLogin, not onRquestLogin.
-
Just stick with plain functions, why would you complicate it with the use of an event ? Other than that, then yeah it will work. Create a setMaxVelocity function if you want which takes 2 params: vehicle and maxVelocity. That function will call setVehicleHandling( vehicle, "maxVelocity", maxVelocity). Or create an updateMaxVelocity function which will only take 1 param: vehicle That function will take its health, calculate the new velocity and then apply it to the vehicle. You will call that updateMaxVelocity when the onVehicleDamage event is triggered
-
No, you removed the content of the command which has no effect now. More like this: addCommandHandler ( Command, -- Adding The Command Handler function ( player, cmd ) local accName = getAccountName ( getPlayerAccount ( player ) ) if isObjectInACLGroup ("user."..accName, aclGetGroup ( "Fundador" ) ) or isObjectInACLGroup ("user."..accName, aclGetGroup ( "Admin" ) ) or isObjectInACLGroup ("user."..accName, aclGetGroup ( "Staff" ) ) then triggerClientEvent(player,"jailShow",player) else outputChatBox(" Access Denied ",player,255,0,0) end end )
-
Modify the if statement like so: if isObjectInACLGroup ("user."..accName, aclGetGroup ( "Fundador" ) ) or isObjectInACLGroup ("user."..accName, aclGetGroup ( "Admin" ) ) or isObjectInACLGroup ("user."..accName, aclGetGroup ( "Staff" ) ) then EDIT: You edited your thread to add the scripts. You have to modify the line 53: if hasObjectPermissionTo ( player, "function.banPlayer" ) then
-
An empty else is no needed and you are comparing a team element (left) with a team name (right). Also, this event doesn't support cancelation (as 3FreT pointed out) so you have to use setElementModel with the previous model. This event will give you only one parameter which is the previous model so your "player" is wrong, you wanted to use source instead in your getPlayerTeam function call: function staffskin(prevSkin) if getPlayerTeam(source) == getTeamFromName("Staff") then setElementModel(source, prevSkin) end end addEventHandler("onElementModelChange", getRootElement(), staffskin) Also as this event will also be triggered for other elements like objects, cars etc, you need to check if source is a player element or you will get warnings or errors: function staffskin(prevSkin) if getElementType(source) == "player" and getPlayerTeam(source) == getTeamFromName("Staff") then setElementModel(source, prevSkin) end end addEventHandler("onElementModelChange", getRootElement(), staffskin) So this code will prevent any skin change if the player is in the "Staff" team, is it really what you wanted to do ?
-
Hmmm no, with getVehicleHandling you can get the maxVelocity of the vehicle (which is the source of the onVehicleDamage event) then calculate the new maxVelocity reduced by the percentage you want to apply according to its health and then set it back using the setVehicleHandling function. There is no difference between vehicle models you need to care of.
-
Oui mais il faudra les mettre dans le bon dossier, par défaut: C:\Program Files (x86)\MTA San Andreas 1.5\mods\deathmatch\resources Attention de ne pas les mettre dans le dossier "resources" du serveur (sinon ça ne fonctionnera pas) qui lui se trouve ici: C:\Program Files (x86)\MTA San Andreas 1.5\server\mods\deathmatch\resources Mais ça veut dire que chaque joueur va devoir faire la manipulation sur leur MTA et ce n'est pas du tout une bonne idée si tu veux avoir des nouveaux joueurs. Pour être sûr de donner les ressources nécessaires aux autres joueurs, il faut identifier la liste des ressources qui se lancent avec le serveur en regardant les <resource src="UneRessource" startup="1" /> qui se trouvent dans la conf du serveur (mtaserver.conf) et ensuite aller les chercher dans le dossier du serveur suivant: C:\Program Files (x86)\MTA San Andreas 1.5\server\mods\deathmatch\resource-cache\http-client-files C'est dans ce dossier que normalement les joueurs téléchargent les ressources via le port 22005 lorsqu'ils se connectent. Une autre solution serait d’héberger les fichiers autre part et le spécifier dans la conf du serveur (mtaserver.conf). En effet l'option httpdownloadurl te permet de spécifier une autre adresse pour télécharger les ressources. Mais ça demande beaucoup plus de travail que de simplement ouvrir le port 22005 ...
-
This is the ip of the http server, not the client connected on it ...
-
2 possibilités: - Ton gars qui se connecte utilise le même pc qui héberge le serveur (du coup il est en local/ il est sur le même pc). - Ton gars possède déjà toutes les ressources utilisé par le serveur et sont déjà à jour donc il n'a pas besoin de les télécharger à nouveau.
-
Bah dans ce cas, demande à celui qui s'occupe du serveur d'ouvrir le port 22005 en TCP. Me donner l'ip ne servira à rien. Seul l'admin du serveur linux peut le faire.
-
Bah il faut d'abord m'expliquer l’environnement technique ton serveur est hébergé où et sur quel système d'exploitation ?
-
Quasiment sûr que c'est le port 22005 qui n'est pas ouvert, fait le test ici (avec le serveur qui tourne): Server port test for MTA:SA Si tout est au vert, ça peut venir d'une mauvaise configuration donc il faudra nous montrer ton mtaserver.conf
-
Comment un français est-il censé jouer sur un serveur totalement arabe ??? How a french player is supposed to play on an arabic server ???
-
I'm not at home actually so here is a draft of what you can use: Client side script: -- You can modify below: local speedUnit = "km/h" -- Possible values: "km/h", "mph" or "m/s" local minSpeed = 5 -- minimum speed before falling local exceptionList = { -- Boats: 472, 473, 493, 595, 484, 430, 453, 452, 446, 454, -- add other vehicles here if needed } -- Function responsible for the "fall animation" -- fromSpeed is the speed the player is falling from function makeLocalPlayerFall( fromSpeed ) -- ultra basic fall animation (edit for more complex one): setElementVelocity( localPlayer, 0, 0, 1 ) end -- !! DO NOT MODIFY BELOW !! -- -- Maybe an infinite timer of 1 second won't make any difference but would reduce hardware consumption addEventHandler("onClientRender", root, function () local veh = getPedContactElement( localPlayer ) if not veh or isVehicleInExceptionList( veh ) then return end local speed = getElementSpeed( veh, speedUnit ) if speed >= minSpeed then makeLocalPlayerFall( speed ) end end) function isVehicleInExceptionList( veh ) if not exceptionList then return false end local model = getElementModel( veh ) for k, m in ipairs ( exceptionList ) do if model == m then return true end end return false end -- Taken from: [url=https://wiki.multitheftauto.com/wiki/GetElementSpeed]https://wiki.multitheftauto.com/wiki/GetElementSpeed[/url] function getElementSpeed(theElement, unit) -- Check arguments for errors assert(isElement(theElement), "Bad argument 1 @ getElementSpeed (element expected, got " .. type(theElement) .. ")") assert(getElementType(theElement) == "player" or getElementType(theElement) == "ped" or getElementType(theElement) == "object" or getElementType(theElement) == "vehicle", "Invalid element type @ getElementSpeed (player/ped/object/vehicle expected, got " .. getElementType(theElement) .. ")") assert((unit == nil or type(unit) == "string" or type(unit) == "number") and (unit == nil or (tonumber(unit) and (tonumber(unit) == 0 or tonumber(unit) == 1 or tonumber(unit) == 2)) or unit == "m/s" or unit == "km/h" or unit == "mph"), "Bad argument 2 @ getElementSpeed (invalid speed unit)") -- Default to m/s if no unit specified and 'ignore' argument type if the string contains a number unit = unit == nil and 0 or ((not tonumber(unit)) and unit or tonumber(unit)) -- Setup our multiplier to convert the velocity to the specified unit local mult = (unit == 0 or unit == "m/s") and 50 or ((unit == 1 or unit == "km/h") and 180 or 111.84681456) -- Return the speed by calculating the length of the velocity vector, after converting the velocity to the specified unit return (Vector3(getElementVelocity(theElement)) * mult).length end Test it for me please (errors/warnings will be visible with /debugscript 3).
-
Pretty sure he wants that if the vehicle is moving, then any player standing on it should fall like in recent GTAs to be more realistic.
-
Note for your future scripts: don't create functions with already used names as you will replace the original one (talking about removeWorldModel)
-
Try to add ",false" without the quotes to all your onClientGUIClick: addEventHandler("onClientGUIClick", GUIEditor.button[1], clientSubmitChangepw, false) Also, when something doesn't work without any error or warning, then you can use outputChatBoxs to know where the code execution is going and where it stops. This is part of your job which is "debugging" your code. Note: I didn't say it was the error neither the only one. But try that first and use outputChatBox everywhere you can.
-
I tested my code and I actually did 2 typos (line 12 and 14), but now it's working (this is a client-side function and it's not exported ofc): client: addEventHandler("onClientRender", root, function () for k, veh in ipairs(getElementsByType("vehicle")) do local frozenPos = getElementData(veh, "_turretFrozenPos") if frozenPos then setVehicleTurretPosition(veh, frozenPos[1], frozenPos[2]) end end end) function setVehicleTurretFrozen(vehicle, frozen) if not vehicle or getElementType(vehicle) ~= "vehicle" then return false end if frozen == nil or type(frozen) ~= "boolean" then return false end local model = getElementModel(vehicle) if model ~= 432 and model ~= 601 then return false end local value = nil if frozen then value = {getVehicleTurretPosition(vehicle)} end return setElementData(vehicle, "_turretFrozenPos", value) end Sorry for the delay ! Best regards, Citizen
-
I don't understand when you say "when I stop it" but I understood (I guess) that you want to be able to totaly freeze a turret when you stop the engine of the vehicle. So I made a reusable function (setVehicleTurretFrozen) to freeze a turret (will work if my attempt proposition from the previous post is working): addEventHandler("onClientRender", root, function () for k, veh in ipairs(getElementsByType("vehicle")) do local frozenPos = getElementData(veh, "_turretFrozenPos") if frozenPos then setVehicleTurretPosition(veh, frozenPos[1], frozenPos[2]) end end end) function setVehicleTurretFrozen(vehicle, frozen) if not vehicle or getElementType(vehicle) ~= "vehicle" then return false end if frozen == nil or type(frozen) ~= "bool" then return false end local model = getElementModel(veh) if model ~= 432 and model ~= 601 then return false end local value = nil if frozen then value = {getVehicleTurretPosition(vehicle)} end return setElementData(vehicle, "_turretFrozenPos", value) end Syntax: bool setVehicleTurretFrozen(vehicle turretVehicle, bool frozen) Returns: Returns true if the turret has been successfully frozen, false otherwise.
-
Please don't post if you don't know, you can make a dev wasting his time with your wrong "solutions". I never tried to do that but my first attempt would be to use the getVehicleTurretPosition to get the rotations and if it is over the MAX_VALUE you want, then set it to MAX_VALUE using setVehicleTurretPosition . Just do that in an onClientRender. (Same for the MIN_VALUE). This should take I guess less than 10 lines of code.
-
Make sure both files are in your meta.xml and as far as I remember, the "test" command name is kinda internally protected, try this instead just to see if it works: addCommandHandler ( "lol", random_sound )
-
In some parts of your code, veiculo[owner] is used as a vehicle, and, in some other parts, as a timer which doesn't make sense. I would go like this: -- onDestroyVehicle ---------------------------------------------------------------------------------------- addEventHandler("onVehicleExit", root, function() if not isVehicleCreatedByPlayer( source ) or not isVehicleEmpty( vehicle ) then return -- It's not a vehicle created by a player or the vehicle is not empty then cancel end local destroyTimer = setTimer( function( vehicle ) if isElement( vehicle ) then destroyElement( vehicle ) end end, 5000, 1, vehicle) setElementData(vehicle, "destroyTimer", destroyTimer) end) addEventHandler("onVehicleEnter", root, function() if not isVehicleCreatedByPlayer( source ) then return end local destroyTimer = getElementData(source, "destroyTimer") if isTimer(destroyTimer) then killTimer(destroyTimer) removeElementData(source, "destroyTimer") end end) function getVehicleCreatedByPlayer( player ) for p, v in pairs( veiculo ) do if p == player then return v end end return nil end function getVehicleOwner( vehicle ) for p, v in pairs( veiculo ) do if v == vehicle then return p end end return nil end function isVehicleCreatedByPlayer( vehicle ) local owner = getVehicleOwner( vehicle ) return owner and getElementType(owner) == "player" end -- From [url=https://wiki.multitheftauto.com/wiki/IsVehicleEmpty]https://wiki.multitheftauto.com/wiki/IsVehicleEmpty[/url] function isVehicleEmpty( vehicle ) if not isElement( vehicle ) or getElementType( vehicle ) ~= "vehicle" then return true end local passengers = getVehicleMaxPassengers( vehicle ) if type( passengers ) == 'number' then for seat = 0, passengers do if getVehicleOccupant( vehicle, seat ) then return false end end end return true end ----------------------- function destroirCarro() local vehicle = getVehicleCreatedByPlayer( source ) if vehicle and isElement( vehicle ) then destroyElement( vehicle ) end end addEventHandler("onPlayerLogout", root, destroirCarro) addEventHandler("onPlayerQuit", root, destroirCarro) addEventHandler("onPlayerWasted", root, destroirCarro) -- onVehicleExplode function VehicleExplode() if not isVehicleCreatedByPlayer( source ) then return end local owner = getVehicleOwner( source ) setTimer( function( vehicle, owner ) destroyElement( vehicle ) veiculo[owner] = nil end, 5000, 1, source, owner ) end addEventHandler("onVehicleExplode", root, VehicleExplode)
-
Alright, then as a quick solution, I would add the "propertyName" for the function to know where to check the value in: local weaponsTable = { {name="Soldier",weaponsID={31,22,16},weaponsAmmo = {1000,50,1}}, {name="Soldier2",weaponsID={31,22,16},weaponsAmmo = {2000,100,2}} } function giveWeaponsByLevel(player) local armyLevel = "Soldier" -- first index(1) local index = table.getIndexByValue(weaponsTable, "name", armyLevel) -- index should be 1 local name, weaponID, weaponsAmmo = unpack(weaponsTable[index]) for i=1,#weaponID do giveWeapon(player, weaponID[i], weaponsAmmo[i]) end end function table.getIndexByValue(t, propertyName, value) for i, v in ipairs(t) do if v[propertyName] == value then return i end end end But a cleaner version (not saying it's the best) would be to something more like the following: local weaponsTable = { ["Soldier"] = { { id = 31, ammos = 1000 }, { id = 22, ammos = 50 }, { id = 16, ammos = 1 } }, ["Soldier2"] = { { id = 31, ammos = 2000 }, { id = 22, ammos = 100 }, { id = 16, ammos = 2 } } } function giveWeaponsByLevel( player ) local armyLevel = "Soldier" local weapons = weaponsTable[armyLevel] for k, weapon in ipairs(weapons) do giveWeapon(player, weapon.id, weapon.ammos) end end
-
You are already checking it before doing the addEventHandler so if the image is drawn, then it means that you already passed that check. By the way if you do the check in the renderDisplay() function, then you don't even need the show() and add() functions anymore.