Jump to content

Lord Henry

Other Languages Moderators
  • Posts

    3,936
  • Joined

  • Last visited

  • Days Won

    176

Everything posted by Lord Henry

  1. Aqui está: (client-side) -- Obs: Essa função ativa mesmo com o veículo blindado. -- Obs2: Essa função ativa mesmo que não haja dano no veículo, por exemplo ao arranhar o assoalho do veículo em algo. -- Se quer que a função ative somente ao dar dano no veículo, utilize onClientVehicleDamage (não ativará se o veículo estiver blindado) addEventHandler("onClientVehicleCollision", root, function() if source == getPedOccupiedVehicle(localPlayer) then -- Se o veículo que bateu for o que o localPlayer estiver dentro, então: local sx, sy, sz = getElementVelocity (source) -- Obtém a velocidade x, y, z do veículo. local kmhs = math.floor(((sx^2 + sy^2 + sz^2)^(0.5)*(1.61))*100) -- Calcula e converte a velocidade em km/h if kmhs >= 70 then -- Se estava a 70 km/h ou mais quando colidiu, então: local random = math.random(100) -- Gera um número pseudo-aleatório entre 1 e 100. print("Bateu com força. Random gerado: "..random) if random <= 40 then -- Se o número gerado for menor ou igual a 40, então: (40% de chance) local fl, rl, fr, rr = getVehicleWheelStates (source) -- Obtém o estado de todos os pneus do veículo. local pneus = {fl, rl, fr, rr} -- Cria uma tabela com os estados de cada pneu. local tire = math.random(4) -- Gera um número pseudo-aleatório entre 1 e 4. Vai determinar qual pneu será furado. if pneus[tire] == 0 then -- Se o estado do pneu escolhido for inflado, então: pneus[tire] = 1 -- Muda esse estado para furado. outputChatBox("Pneu "..tire.." do seu carro furou!") end setVehicleWheelStates (source, pneus[1], pneus[2], pneus[3], pneus[4]) -- Seta o novo estado dos pneus. end end end end) Obs: Uma batida pode furar vários pneus, pois essa função é ativada várias vezes numa única batida. Se quiser evitar, adicione um timer anti-spam na função para não funcionar durante X segundos após furar um pneu.
  2. onClientVehicleCollision não funciona server-side só funciona client-side.
  3. 2 coisas que vc precisa estar atento: Você declarou os parâmetros do setVehicleWheelStates incorretamente. Da forma que você fez, ele vai definir um estado aleatório do pneu dianteiro esquerdo, os demais nunca serão alterados pois sempre estarão no estado 0 (inflados). Esteja ciente de que onClientVehicleCollision não detecta colisões caso o objeto do cenário que o veículo bateu seja destruído. Ou seja, não detecta ao destruir postes, nem cercas ao colidir.
  4. De acordo com a Wiki do setElementBonePosition é necessário que você use a função dentro de um onClientPedsProcessed.
  5. Eu testei e funciona. Ele inicia o fogo para explodir, depois conserta, depois inicia o fogo e fica nesse loop até você descapotar o carro. Mas não explode.
  6. Tente isso: -- SERVER-SIDE function vehicleHPVerify(loss) if getElementHealth(source) - loss < 300 then -- setVehicleDamageProof (source, true) -- Neste caso não funciona. Faz com que este evento não seja mais acionado. setVehicleEngineState (source, false) setElementHealth(source, 300) local thePlayer = getVehicleController (source) if thePlayer then outputChatBox ("Seu veículo quebrou o motor. Chame um mecânico.", thePlayer) end cancelEvent() end end addEventHandler ("onVehicleDamage", root, vehicleHPVerify) function antiVehicleEngine (cmd) if cmd == "motor" then local theVehicle = getPlayerOccupiedVehicle (source) if theVehicle then if getPedOccupiedVehicleSeat (source) == 0 then if getElementHealth (theVehicle) <= 300 then setVehicleEngineState (theVehicle, false) cancelEvent() end end end end end addEventHandler ("onPlayerCommand", root, antiVehicleEngine) addEventHandler("onVehicleEnter", root, function(thePlayer) if getElementHealth(source) <= 300 then setVehicleEngineState(source, false) outputChatBox ("Este veículo está com o motor quebrado. Chame um mecânico.", thePlayer) end end)
  7. @JPzin deixa o like nas respostas, já que eu fiz o resource inteiro pra vc kkkkkkkk
  8. Desta forma: Client-side: local screenW, screenH = guiGetScreenSize() local painel = false -- Layout Fixo: (centralizado) local layout = { -- posX, posY, sizeX, sizeY, colorRGBA, text, textColorRGBA, fontSize, fontFamily, alignX, alignY {-320, -180, 640, 360, tocolor(75, 75, 75, 255)}, -- Window {-320, -190, 426, 20, tocolor(23, 209, 248, 255)}, -- Tittle Line {-300, -160, 600, 60, tocolor(20, 20, 20, 255), "Arsenal", tocolor(255, 255, 255, 255), 3, "bankgothic", "center", "center"}, -- Tittle {-300, -80, 186, 100, tocolor(43, 43, 43, 255), "M4", tocolor(255, 255, 255, 255), 2, "pricedown", "center", "center"}, -- Button 1 {-300, 40, 186, 100, tocolor(43, 43, 43, 255), "AK", tocolor(255, 255, 255, 255), 2, "pricedown", "center", "center"}, -- Button 2 {-93, -80, 186, 100, tocolor(43, 43, 43, 255), "GLOCK", tocolor(255, 255, 255, 255), 2, "pricedown", "center", "center"}, -- Button 3 {-93, 40, 186, 100, tocolor(43, 43, 43, 255), "Skin 1", tocolor(255, 255, 255, 255), 2, "pricedown", "center", "center"}, -- Button 4 {114, -80, 186, 100, tocolor(43, 43, 43, 255), "Skin 2", tocolor(255, 255, 255, 255), 2, "pricedown", "center", "center"}, -- Button 5 {114, 40, 186, 100, tocolor(43, 43, 43, 255), "VEICULO", tocolor(255, 255, 255, 255), 2, "pricedown", "center", "center"}, -- Button 6 {-320, 140, 640, 40, false, "Para fechar aperte 'Backspace'", tocolor(255, 255, 255, 255), 2, "default", "center", "center"}, -- Close info } function paineldx () for i, infos in ipairs (layout) do -- Para cada item da tabela layout, faça: local posX, posY, sizeX, sizeY, colorRGBA, text, textColorRGBA, fontSize, fontFamily, alignX, alignY = unpack (infos) -- Separa as infos em variáveis. -- Layout Fixo: posX = (screenW / 2) + posX -- Faz com que o centro da tela seja a posição 0, 0. Centralizando as posições. posY = (screenH / 2) + posY -- Converte as posições centralizadas da tabela para posições absolutas. if colorRGBA then -- Só faz dxDrawRectangle se tiver o parâmetro colorRGBA. Se não tiver, é só um texto isolado. if i >= 4 and i <= 9 then -- Se for um botão, então: (se for do item 4 até o 9) if isMouseInPosition (posX, posY, sizeX, sizeY) then -- Se o mouse está em cima do botão, então: colorRGBA = tocolor(0, 0, 0, 255) -- Torna a cor do botão preto. end end dxDrawRectangle(posX, posY, sizeX, sizeY, colorRGBA, false) end if text then -- Só faz dxDrawText se tiver o parâmetro texto. sizeX = posX + sizeX sizeY = posY + sizeY dxDrawText(text, posX, posY, sizeX, sizeY, textColorRGBA, fontSize, fontFamily, alignX, alignY) end end end addEvent("HitM", true) addEventHandler("HitM", root, function() -- Função chamada pelo servidor quando este jogador colide no marker do server. if not painel then addEventHandler("onClientRender", root, paineldx) painel = true showCursor(true) end end) bindKey("backSpace", "down", function() -- Tecla que fecha o painel. if painel then removeEventHandler("onClientRender", root, paineldx) painel = false showCursor(false) end end) addEventHandler("onClientClick", root, function(button, state) if button == "left" and state == "down" then if painel then for i, infos in pairs (layout) do -- Neste caso uso pairs pois a ordem dos itens não importa. local posX, posY, sizeX, sizeY = unpack (infos) -- Separa as infos em variáveis. -- Layout Fixo: posX = (screenW / 2) + posX -- Converte a posição centralizada da tabela para posição absoluta. posY = (screenH / 2) + posY if isMouseInPosition(posX, posY, sizeX, sizeY) then if i == 4 then -- Se for o botão de M4, então: triggerServerEvent("setarAlgo", localPlayer, "weapon", 31, 9999) -- giveWeapon (source, 31, 9999) -- Não funciona client-side. elseif i == 5 then -- Se for o botão de AK, então: triggerServerEvent("setarAlgo", localPlayer, "weapon", 30, 9999) elseif i == 6 then -- Se for o botão de Glock, então: triggerServerEvent("setarAlgo", localPlayer, "weapon", 24, 9999) elseif i == 7 then -- Se for o botão de Skin 1, então: triggerServerEvent("setarAlgo", localPlayer, "skin", 28) elseif i == 8 then -- Se for o botão de Skin 2, então: triggerServerEvent("setarAlgo", localPlayer, "skin", 29) elseif i == 9 then -- Se for o botão de Vehicle, então: triggerServerEvent("setarAlgo", localPlayer, "vehicle", 560) end end end end end end) function isMouseInPosition (x, y, width, height) -- Função útil. if not isCursorShowing() then return false end local sx, sy = guiGetScreenSize() local cx, cy = getCursorPosition() local cx, cy = (cx * sx), (cy * sy) return ((cx >= x and cx <= x + width) and (cy >= y and cy <= y + height)) end Server-side: local m1 = createMarker(2027.903, 1545.603, 10.819 -1, "cylinder", 1.5, 0,195,255, 100) local vehicles = {} addEventHandler("onMarkerHit", m1, function(hit) if getElementType(hit) == "player" then -- Se quem colidiu no marker for um jogador, então: if isObjectInACLGroup ("user."..getAccountName (getPlayerAccount (hit)), aclGetGroup ("Admin")) then -- Se o jogador está na ACL Admin, então: setTimer(triggerClientEvent, 250, 1, hit, "HitM", hit) else outputChatBox("Acesso negado.", hit, 255, 0, 0) end end end) addEvent("setarAlgo", true) addEventHandler("setarAlgo", root, function (tipo, id, ammo) -- Função chamada pelo client. Seta algo no jogador. if tipo == "weapon" then giveWeapon(client, id, ammo, true) elseif tipo == "skin" then setElementModel (client, id) elseif tipo == "vehicle" then local x, y, z = getElementPosition(client) if isElement (vehicles[client]) then -- Se já existe um veículo criado por este jogador, então: destroyElement(vehicles[client]) -- Destrói esse veículo antes de criar outro. end vehicles[client] = createVehicle(id, x, y, z + 1) -- Cria o veículo em cima do jogador. end end) function limpaVehicle() -- Destrói o veículo criado pelo jogador quando ele sair do servidor. if isElement (vehicles[source]) then destroyElement(vehicles[source]) vehicles[source] = nil end end addEventHandler("onPlayerQuit", root, limpaVehicle) addEventHandler("onPlayerDisconnect", root, limpaVehicle)
  9. @JPzin comece fazendo o seguinte: Corrija a indentação dos seus códigos para que eles fiquem legíveis. Para aprender a indentar código, veja este tópico. Troque todos os getRootElement() por root. Depois de fazer o básico, aí sim você pode começar a corrigir o painel. De cara, a função giveWeapon é server-side. Portanto não vai funcionar no seu script client-side. Vi que seu painel foi feito usando escala relativa para tentar manter o painel no mesmo tamanho em qualquer resolução, porém isso dará problema com os textos pois eles não acompanham a escala da tela e precisam que você declare tamanhos diferentes na fonte. Ou você faz um painel de tamanho fixo (no máximo 640x480), evitando problemas com os textos e evitando trabalho. Ou você calcula a resolução do jogador e aplica no tamanho da fonte junto, o que dará mais trabalho. Ao usar escala relativa, você também precisa se preocupar com a proporção da tela, algumas resoluções são mais quadradas (4:3), outras são mais retangulares (16:9), causando distorções no painel e deixando ele mais esticado ou comprimido na horizontal. Nestes casos, você precisa definir tamanhos de fonte diferente na horizontal também, saiba mais em dxDrawText. Evite repetição de código. Crie uma tabela com todas as posições e tamanhos de cada botão junto com os textos. Então dentro da função do onClientRender você apenas faz um "loop ipairs" entre os itens dessa tabela, gerando os botões com as propriedades da tabela. Na função do onClientClick, você usa a mesma tabela para verificar qual botão foi clicado, criando uma condição para cada índice da tabela. Ex: Se clicou no item 1 da tabela, faz tal coisa. Senão, se clicou no item 2 da tabela, faz outra coisa e assim por diante. Para facilitar na hora de fazer manutenção no painel, deixe cada dxDraw com comentários no final da linha dizendo o que é cada item. Por exemplo, no final da linha do primeiro dxDrawRectangle, adicione o comentário: -- Janela Só então, depois do painel pronto, você deve criar feedback visual ao passar o mouse pelas áreas clicáveis. Já que o objetivo de um painel DX é ser mais bonito do que funcional. Se fosse pra ser mais funcional do que bonito, você deveria usar CEGUI em vez de DXGUI. Ao passar o mouse em cima de um botão, mude a cor dele para o jogador saber que é uma área clicável. Ou então mude a cor do texto do botão.
  10. Não crie diversos tópicos com assuntos parecidos. Irei fechar este tópico. Caso ainda precise de ajuda neste painel, continue no outro post sobre o outro painel DX.
  11. Crie uma variável com valor 0. Por exemplo playersArena = 0 Sempre que um jogador entrar, aumente em +1 nessa variável: playersArena = playersArena + 1 Sempre que um jogador sair ou desconectar do servidor, diminua em -1 essa variável: playersArena = playersArena - 1 Dai no texto, apenas mostre o valor dessa variável com um tostring(playersArena).
  12. Dê um nome para a função que você quer repetir e também deixe o timer numa variável. Ao desligar o infravermelho, cancele o timer usando killTimer na variável dele e depois execute essa função que seria chamada só mais tarde pelo timer.
  13. Olha... vc só mudou 1 variável. Mas não trocou os getElementData/setElementData para getPlayerMoney/setPlayerMoney. Além disso, getPlayerMoney e setPlayerMoney devem ser feitos server-side somente. Então você precisará de triggerServerEvent ali no script client-side para chamar um evento lá no server-side para mexer no dinheiro no jogador. Até pq tentar setar dinheiro no jogador via client-side só mudará na Hud, mas não vai mudar no servidor, então o dinheiro que aparece na Hud não será a quantidade real que ele tem no servidor.
  14. Você não precisa upar as imagens no drive. Você pode upá-las no imgur.com e mandar o link direto da publicação aqui.
  15. Mostre o que você já tentou fazer.
  16. Após analisar seu código, fiz um exemplo parecido com sua ideia. Independente da resolução, ele vai ter a mesma proporção e distância da borda da tela. local screen = Vector2 (guiGetScreenSize()) -- local screen.x, screen.y = guiGetScreenSize() local offset = screen.y * 0.01852 -- Distância relativa da borda da tela. (0 = colado na borda) --[[ ~20px = 0.01852 ~15px = 0.01389 ~10px = 0.00926 ]] local bgScale, circleScale = (screen.y * 0.04), 0.9 -- Raio dos círculos background relativos à tela | Raio dos círculos em relação aos círculos background. -- (1 = tamanho Y da tela | 1 = tamanho igual aos círculos de background) local iconScale = bgScale * 0.5 -- Tamanho relativo dos ícones em relação ao tamanho dos backgrounds. (1 = tamanho igual aos círculos de background) local circleAngle = 270 -- Ângulo que os backgrounds e os círculos começam a ser preenchidos. (0 = direita, 90 = abaixo, 180 = esquerda, 270 = acima) addEventHandler("onClientRender", root, function() local health = getElementHealth(localPlayer) local armor = getPedArmor(localPlayer) dxDrawCircle (offset + bgScale, screen.y - bgScale - offset, bgScale, 0, 360, tocolor(28, 28, 28, 170)) -- bg Health dxDrawCircle (offset + bgScale, screen.y - bgScale - offset, bgScale * circleScale, 0 + circleAngle, (360 * (health/100)) + circleAngle, tocolor(255, 32, 32)) -- Health -- dxDrawImage (ícone da vida) if armor > 0 then -- Faz com que o círculo de armor só apareça se não estiver em 0. dxDrawCircle ((offset + bgScale) + (bgScale * 1.4), screen.y - bgScale - offset, bgScale, 0, 360, tocolor(28, 28, 28, 170)) -- bg Armor dxDrawCircle ((offset + bgScale) + (bgScale * 1.4), screen.y - bgScale - offset, bgScale * circleScale, 0 + circleAngle, (360 * (armor/100)) + circleAngle, tocolor(255, 255, 255)) -- Armor -- dxDrawImage (ícone do colete) end end)
  17. Mande uma imagem da sua tela inteira mostrando o painel. Não temos como testar sem as imagens das fontes e sem as funções úteis.
  18. objeto = createObject (1337, 2502, -1667, 12.36) -- Cria um objeto qualquer na Grove Street. addEventHandler("onClientRender", root, function() -- for _, objeto in ipairs(getElementsByType("object")) do -- DESATIVADOS APENAS PARA TESTES. -- if (getElementData(objeto,"objeto.element")) then -- local ID = getElementData(objeto, "objeto.id") -- local PD = getElementData(objeto, "objeto.produtos") local ID = 1337 -- APENAS PARA TESTES local PD = 1234567890 -- APENAS PARA TESTES local localPos = {getElementPosition(localPlayer)} local objetoPos = {getElementPosition(objeto)} local worldPosition = {getScreenFromWorldPosition(objetoPos[1], objetoPos[2], objetoPos[3] + 0.50)} local distance = getDistanceBetweenPoints3D(localPos[1], localPos[2], localPos[3], objetoPos[1], objetoPos[2], objetoPos[3]) if distance <= 15 then if worldPosition[1] and worldPosition[2] then dxDrawText("ID: "..ID.." | PD: "..PD, worldPosition[1], worldPosition[2], worldPosition[1], worldPosition[2], tocolor(255, 255, 255, 255), 1.0 , "default-bold", "center") end end -- end -- end -- DESATIVADOS APENAS PARA TESTES. end)
  19. O seu 4º e 5º parâmetros não fazem sentido. (10, 20) Também não faz sentido vc colocar "center" fora de aspas duplas. Este parâmetro é uma string, portanto precisa estar entre aspas, exatamente como mencionei na minha resposta anterior. O primeiro "center" faz ele centralizar o texto na horizontal, o segundo "center" faz ele centralizar na vertical, mas não é necessário centralizar na vertical nesse caso, pois é só aumentar o diminuir aquele offset do + 0.50 para mudar a altura do texto. Então utilize apenas o primeiro "center" e delete o que tem depois.
  20. Adicione o parâmetro , "center" depois do nome da fonte ali no dxDrawText.
  21. Cadê o onClientPedsProcessed? Ele é necessário para atualizar a posição dos ossos a cada frame. Veja o exemplo da própria Wiki.
  22. A culpa é inteiramente da administração do servidor. As possíveis causas são as seguintes: 1) Não desenvolveram uma segurança decente para o servidor, permitindo que os jogadores violem os banimentos. 2) Desenvolveram resources com brechas de segurança que tornaram o servidor violável pelos clientes. 3) Deram permissão admin para algum resource desconhecido que está colocando usuários não autorizados na ACL Group Console.
×
×
  • Create New...