Leaderboard
Popular Content
Showing content with the highest reputation on 30/10/19 in Posts
-
MTA-Communication-Enhancement This is an enhancement that allows you to communicate between clientside and serverside a bit easier. If you know how to work with events, then you probably do not need this, but it has some nice features which allows you to sit back and write less code + achieve some nice results. Note: It is important to keep in mind that this is an enhancement. Which means it is just an layer on top of the basic functionalities of MTA. And most enhancements come with a cost, in this case that is bit of performance. I will keep the information of topic to the minimal, as I have written most of the information already on the repository. You can find the repository here. Examples Syntax Installation What can you do with it? Calling from clientside to serverside Client callServer("hello") Server function hello () outputChatBox("Hello client!") end Calling from serverside to clientside Server addCommandHandler("callclient", function (player) -- An addCommandHandler is needed, because the client hasn't loaded it's scripts yet. callClient(player, "hello") end, false, false) Client function hello () outputChatBox("Hello server!") end Ok, ok, that was boring. The next one this is a bit nicer! Hello are you there? Just Call-me-back... I miss(ed) you too Callback Client callServer( "callbackMe", "argument", function (argument) -- < This is the callback function outputChatBox(argument) end ) Server function callbackMe (argument) return argument .. " < I looked at it :)" end Callback + internal arguments Sometimes you have arguments that you simply can't send over. > functions Or arguments that shouldn't be send over. > LARGE quantities of database data Internal arguments can be used to pass information to a callback without exposing it to the other side(client/server). Client callServer( "callbackMe", -------------------------------- -- arguments that are send over "argument", -- -------------------------------- function (internalArgument, argument) -- < This is the callback function. outputChatBox(internalArgument) outputChatBox(argument) end, -------------------------------- -- arguments that are not send over "internalArgument" -- < internal argument -- -------------------------------- ) Server function callbackMe (argument) return argument .. " < I looked at it :D" end Ha! Serverside what is that? No need for complicated things! Communicate between clients without writing a single line of serverside. Magic! Note: There is serverside used behind the scenes, you just don't have to write it. Client function smile (player) outputChatBox((isElement(player) and getPlayerName(player) or "[unknown]") .. " has send you a: :)") local x, y, z = getElementPosition(localPlayer) setElementPosition(localPlayer, x, y, z + 100) end addRemoteClientAccessPoint(smile) -- < This function allows other clients to call this function. --------------------------------------- -- -- function getPlayerFromPartialName(name) local name = name and name:gsub("#%x%x%x%x%x%x", ""):lower() or nil if name then for _, player in ipairs(getElementsByType("player")) do local name_ = getPlayerName(player):gsub("#%x%x%x%x%x%x", ""):lower() if name_:find(name, 1, true) then return player end end end end -- Author: TAPL -- https://wiki.multitheftauto.com/wiki/GetPlayerFromPartialName -- -- --------------------------------------- addCommandHandler("smile", function (cmd, playerName) local player = getPlayerFromPartialName(playerName) if player then outputChatBox("Sending smile!") callRemoteClient(player, "smile", player) else outputChatBox("Can't find player!") end end) Turtle, I will wait for you to catch up. So don't worry, you are still cute. Await functions When a player has joined the server, he or she doesn't have download + loaded his scripts yet. This means that you can't deliver your love letter yet and all your work will be for nothing. But what if you don't have to worry about that? You can just wait now! Server addEventHandler("onPlayerJoin", root, function () callClientAwait(source, "testCallClientAwait") end) Client function testCallClientAwait () outputChatBox("Yes this works!") end Security Worried about security issues? Remote calls for C++/MTA functions have been blocked. There is a whitelist feature included, if enabled your code can only remote-call whitelisted functions. (this is disabled by default) Read the docs for that. Here and here1 point
-
Yes. But it is very far from finished, as you can see i am still working on the engine.1 point
-
يخوي والله ماشرحت لنا وش تبي تسوي بالضبط انت تبي تضيف حالة ستاتس جديدة؟ ولا تبي تعدل على حقت الريس ولا تبي تضيف صورة بس؟ تبي تضيف صورة بس ولا تبي تضيف حالات جديدة؟ اشرح لنا اذا تبي تشيل التكست وتخلي الصورة لازم تدور dxDrawText بالسكور بورد واذا كان الكلمون ستات لا تخليه يسوي دراو للتكست وخليه يسوي للصورة بالنسبة للكود يلي عطيتك اياه عدلته معليش كان فيه خطأ بسيط1 point
-
I am still working on the water shader. I managed to add specular lighting, shore foam and screen space reflections, but the reflections are currently inaccurate and require additional work. That stuff is not easy. But i think the outcome speaks for itself, it looks absolutely amazing. DEFAULT GTA, NO SHADER: WATER SHADER WITH SHORE FADING, SHORE FOAM, SPECULAR SUN LIGHTING, CAUSTICS, SCREEN-SPACE REFLECTIONS + DETAIL SHADER + GODRAY SUN SHADER + DYNAMIC SKY SHADER1 point
-
1 point
-
1 point
-
Fora os erros mencionados acima, você também pode evitar esse setElementData que de forma desnecessária vai utilizar rede para atualizar no servidor. Em vez disso você pode usar uma simples variável como a do próprio botão. A função 'openButton' deveria ficar assim: function openButton() if botao then outputChatBox("| ERRO | O botão já está aberto.") else outputChatBox("Você abriu o botão.") showCursor(true) botao = guiCreateButton(0.5, 0.5, 0.09, 0.05,"Enviar mensagem", true) botaoedit = guiCreateEdit(0.59, 0.5, 0.15, 0.05, "Escreva uma mensagem aqui.", true) guiEditSetMaxLength(botaoedit, 37) addEventHandler("onClientGUIClick", botao, onClickButton, false) -- use 'false' depois da função se o evento for adicionado só para 1 único elemento end end addCommandHandler("abrirbotao", openButton) E o comando de 'tirar': function breakButton() if botao and isElement(botao) then -- verificar se existe o botão, isto é, ele está na tela destroyElement(botao) -- remover elemento destroyElement(botaoedit) botao = nil -- limpar referência na memória botaoedit = nil showCursor(false) outputChatBox("Botão e edit removidos") else outputChatBox("Erro: O Botão não está na tela, use /abrirbotao") end end addCommandHandler("tirar", breakButton) Função do "onClientGUIClick": function onClickButton(button) if (button == "left") then -- aqui se refere ao botão do mouse que vc clicou, não o botão do jogo showCursor(false) local texto = guiGetText(botaoedit) if texto == "" then -- essa condição verifica se o campo de edição está vazio, se sim notifica o jogador return outputChatBox("Digite algum texto!") end outputChatBox(texto) destroyElement(botao) destroyElement(botaoedit) -- vc também pode usar source aqui, a 'source' deste evento é o elemento da GUI clicado, neste caso, o botão botao = nil botaoedit = nil --[[ Em vez de fazer sumir o botão/edit, irei destruir os elementos, vc pode optar por isso quando por exemplo criar poucos elementos cegui e quiser uma otimização ]] end end (leia os comentários pelo código) (código não-testado)1 point
-
Na terceira função, não é if (botao == "left") then e sim if (button == "left") then, pois foi oq vc definiu nos parâmetros da function. (o que vc definiu dentro do parênteses após o nome da function.) O addEventHandler ("onClientGUIClick") sempre dará erro, pois vc está tentando adicionar uma função de clique antes de criar o botão. O botão será criado somente depois quando aquela primeira função for chamada. Para resolver isso vc tem 2 opções. Mover o addEventHandler para dentro daquela primeira função, depois de criar o botão. E em vez de usar button no segundo argumento, use botao no lugar. Manter o addEventHandler ali fora mas sem definir um botão específico. Dai use guiRoot no lugar de button. Dessa forma a função ativará ao clicar em qualquer guiCreateButton deste resource. E então dentro dessa função vc pode verificar if (source == botao) then para fazer funcionar somente no botão específico.1 point
-
When I join MTA Servers, I get fps drops, I see my fps 60 then it lows to 15 and this really affects on me while I am playing. Help me please. how can I solve this problem?1 point
-
1 point
-
player não está definido, use localPlayer a linha 5 e 9 não é necessária use tonumber(id); o id será uma string e terá que ser convertido para number certifique-se que testeMecanico esteja definido falta um end pelo que vejo E indente seu código por favor1 point
-
Olá. Bom, os comandos /register e /unregister pertencem ao resource admin. Logo, é nele que você vai precisar fazer as alterações. Eu gostaria de saber mais detalhes sobre essa trapaça que você anda tendo problemas, quem sabe daria pra corrigir isso sem desativar os comandos. Voltando ao assunto do post, para desativar esses comandos você deve abrir o arquivo admin_server.lua que está dentro da pasta server do resource admin. Abra-o com o notepad++ de preferência e procure (Ctrl+F) por: "register" Selecione toda a função desse register e dê Ctrl+Q. Isso transformará toda a função em comentário e não será mais lida pelo resource. (é melhor do que simplesmente deletar a função, caso dê alguma merda dai vc ainda tem a função escrita para reativar depois.) Depois faça a mesma coisa com os demais comandos, procure-os com Ctrl+F e deixe as funções deles como comentários. Salva o script e dá /restart admin no server. Me diga se deu certo ou se deu algum erro. Abraço.1 point
