Jump to content

Veiculo andando sozinho [A até B] (Dúvida)


Recommended Posts

  • Other Languages Moderators
1 hour ago, #Gubiani said:

Estou pensando em fazer um script que faça um ônibus traçar uma rota, sem alguém para dirigir, se puderem me ajudar dando as funções que irei usar para fazer esse script ficarei muito Grato!

Não existe função nativa para fazer isso, mas como vc já deve imaginar, precisaria de um NPC dentro do ônibus para poder controlar a direção do ônibus.

Você pode criar os pontos no mapa, que vão ser os markers de checagem. Ao colidir em um marker, verifica onde está o próximo marker (cada marker tem um ID na rota para ser seguida) e com base na posição desse próximo marker em relação a posição do ônibus, deve fazer o NPC dirigir para a direção correta.

Mas atenção: Você precisará de um onClientRender para fazer o NPC parar de fazer a curva, quando o marker já estiver reto na sua frente. Portanto fazer um sistema desses, além de extremamente complexo, exigirá bastante processamento, mesmo que seja client-side.

Você também precisará diferenciar os markers de parada, que com um setTimer, devem fazer o NPC parar o ônibus por um tempo e depois voltar a acelerar. Jogadores conseguem entrar de G no ônibus ocupado por um NPC, mas não podem roubá-lo.

Certifique-se também de blindar o ônibus e deixar o NPC imortal, caso contrário o onClientRender floodará de erros tentando controlar um NPC morto.

51 minutes ago, Mewjas said:

Não existe uma função específica para o que você que fazer, porém existe o setTrainDirection, não é o que você quer porém define as direção do trem. 

Até então dar para ir os jogadores no G.

Ele não pediu nada relacionado a trens. Isso não resolve nem de perto o problema dele.

Edited by Lord Henry
  • Thanks 1
Link to comment

Muito obrigado @Mewjas e @Lord Henry vou, analisar os dois argumentos, e verei o que eu faço! :)

 No caso ali do NPC dentro do veiculo dirigindo, tem alguma função que eu possa usar para fazer que o ônibus ande e faça curvas? (Ou seja, como vou falar para o jogo acelere o veiculo tanta velocidade, vire aqui vire lá até chegar nos pontos?)

Edited by #Gubiani
Link to comment
7 minutes ago, #Gubiani said:

Muito obrigado @Mewjas e @Lord Henry vou, analisar os dois argumentos, e verei o que eu faço! :)

 No caso ali do NPC dentro do veiculo dirigindo, tem alguma função que eu possa usar para fazer que o ônibus ande e faça curvas? (Ou seja, como vou falar para o jogo acelere o veiculo tanta velocidade, vire aqui vire lá até chegar nos pontos?)

setPedControlState()

Como já mencionado pelo @Lord Henry, usar um ped para dirigir um veículo em determinadas rotas é algo meio complexo de se fazer. Eu sugiro que você faça algo do tipo:

  • Crie um objeto qualquer com visibilidade 0 e colisão desativada;
  • Crie o veículo;
  • Anexe o veículo ao objeto (attachElements);

A movimentação se daria por moveObject, que a cada x tempo atualizaria o objeto (junto com o veículo) para uma determinada posição.

Exemplo:

--[[
	subjulgue que o script possua uma tabela "rotas" parecida com o seguinte:
local rotas = {
	{posX=0,posY=0,posZ=0,rotX=0,rotY=0,rotZ=0},
	{posX=0,posY=0,posZ=0,rotX=0,rotY=0,rotZ=0},
	-- e várias outras posições
--]]

local veh = createVehicle(id, x, y, z, rx, ry, rz)
local obj = createObject(id, x, y, z, rx, ry, rz)

setElementAlpha(obj, 0)
setElementCollisionsEnabled(obj, false)
attachElements(veh, obj)

local i = 0
att = setTimer(function()
	i = i+1
	moveObject(obj, 1000, rotas[i].posX, rotas[i].posY, rotas[i].posZ)
	setElementRotation(obj, rotas[i].rotX, rotas[i].rotY, rotas[i].rotZ)
end, 1000, #rotas)

Para determinar a rota, precisaria criar um script que facilitaria na formação dessas rotas.

Exemplo:

-- Gerador de rotas
addCommandHandler("rota",
	function(pl,_,acao)
		if not acao then
			file = fileExists ("rotas.lua")
			if file then
				fileDelete("rotas.lua")
			end
			file = fileCreate("rotas.lua")
		
			fileWrite(file,"local rotas = {\n")
			tempo = setTimer(function()
				local pveh = getPedOccupiedVehicle(pl)
				local x,y,z = getElementPosition(pveh)
				local rx,ry,rz = getElementRotation(pveh)
				fileWrite(file, "{posX="..string.format("%.2f",x)..",posY="..string.format("%.2f",y)..",posZ="..string.format("%.2f",z)..",rotX="..string.format("%.2f",rx)..",rotY="..string.format("%.2f",ry)..",rotZ="..string.format("%.2f",rz).."},\n")
			end,1000,0)
			fileWrite(file,"}")
		end
		if (acao == "fim") then
			if isTimer(tempo) then killTimer(tempo) end
			if file then fileClose(file) end
		end
	end
)

Para criar as rotas você deve atuar, ex: pega o ônibus e digita /rota e então faça o caminho que o ônibus deve seguir, após terminar o percurso use (/rota fim), com isso ele criará o arquivo: rotas.lua que você usaria no script.

Infelizmente dessa forma o veículo não anda “normal”, pois estamos movendo um objeto e não o veículo em si, então possivelmente ocorrerá um pouco de teleporte no movimento/rotação. Mas e uma forma viável de fazer o que você quer.

  • Thanks 1
Link to comment
1 hour ago, #Gubiani said:

Caramba, que loucura, nunca vi um programa assim, que crie arquivos e tal, achei muito interessante valeu @MaligNos vou testar em cima dessa base, no primeiro exemplo, eu posso ignorar as rotas e substituir pelo segundo exemplo, ele irá funcionar normal?

Usa o segundo exemplo para criar as rotas, abra o arquivo que ele vai gerar, copie seu conteúdo, e então jogue no começo do primeiro exemplo.
Outra possibilidade seria remover a declaração "local" da linha 11 do segundo código, que então a tabela gerada nele serviria em todo o script, mas desse modo é necessário adicionar o rotas.lua no meta.xml

  • Thanks 1
Link to comment

Tente usar o setElementRotation antes do moveObject, porque provavelmente com o moveObject nesse 1000 milisegundos ele mantêm a rotação inicial e com isso acaba por desfazer o comando de rotação. Ou então faça o que o Lord mencionou, adicione a rotação nos parâmetros do moveObject, mas para isso precisaria adaptar o código para obter o diferencial de rotação de um dado para outro, já que é utilizado a rotação relativa no moveObject e não absoluta como no setElementRotation.

Edited by MaligNos
  • Thanks 1
Link to comment
2 minutes ago, #Gubiani said:

Nossa muito obrigado @MaligNos nem sei como agradecer, funcionou só que ele da o delay do tempo que foi pego as coordenadas, se eu diminuir o tempo de mapeamento acho que fica lisinho, ele conta 1 segundo pra atualizar a rotação dai fica todo travado. Muito obrigado xD

Por nada ^^. Setando a rotação pelo moveObject seria melhor, já que ele vai movendo linearmente até chegar no valor desejado, ai diminuiria uma pouco essa feiura na rotação.

Link to comment
2 minutes ago, MaligNos said:

Por nada ^^. Setando a rotação pelo moveObject seria melhor, já que ele vai movendo linearmente até chegar no valor desejado, ai diminuiria uma pouco essa feiura na rotação.

Mas daí o que eu preciso mudar no script do mapeamento ? Se poder me ajudar a fazer ele verificar a rotação pelo moveObject vou ficar muito grato cara *-*

é só eu adicionar as variáveis de rotação do lado do x, y, z ?

Link to comment

Tenta isso:

local i = 0
att = setTimer(function()
	i = i+1
	if i > 1 then moveObject(obj, 1000, rotas[i].posX, rotas[i].posY, rotas[i].posZ, calculo(rotas[i-1].rotX, rotas[i].rotX), calculo(rotas[i-1].rotY, rotas[i].rotY),calculo(rotas[i-1].rotZ, rotas[i].rotZ))
	else moveObject(obj, 1000, rotas[i].posX, rotas[i].posY, rotas[i].posZ)
	end
end, 1000, #rotas)

function calculo(angulo1, angulo2)
	local dif = angulo2 - angulo1
	dif = (dif + 180) % 360 - 180
	return dif
end

 

  • Thanks 1
Link to comment
13 hours ago, #Gubiani said:

Meu deus surreal isso cara! tu é insaaaanoo!!!! Muito obrigado mesmo ta rodando perfeitamente com esse cálculo ! 

Aproveitando esse tópico tu poderia me explicar o que acontece nesse cálculo que tu fez? ele verifica a rotação?

Como já mencionado, os parâmetros de rotação do moveObject se referem à rotação relativa ao estado inicial, seria basicamente assim: se o objeto possui as rotações (rx = 120, ry = 0, rz = 180) e eu quiser rotacioná-lo para esses outros valores absolutos (rx = 50, ry = 20, rz = 30), eu devo usar o diferencial deles, que seria no caso: (rx = -70, ry = 20, rz = -150). Ai basicamente o moveObject somaria esses valores com a rotação inicial:

  • rx: (120 + (-70)) = 50
  • ry: (0 + 20) = 20
  • rz: (180 + (-150)) = 30

Funcionamento da função com o rx:

function calculo(120,50)
	local dif = 50  120 -- (-70)
	
	-- segundo trecho do cálculo²
	dif = (-70 + 180) % 360  180
	--[[
	dif = 110 % 360 – 180
	dif = 110 – 180
	dif = -70
	--]]
	
	return -70
end

Observações:

  1. O operador “%” refere-se ao resto da divisão.
  2. O segundo trecho do cálculo nem se faz necessário para o nosso caso, ele serve mais para obter a distância mais curta*.

*Vamos utilizar como exemplo os seguintes dados:

  • rotação inicial (absoluta): 350
  • rotação desejada (absoluta): 30
-- Sem o segundo trecho:
function calculo(350,30)
	local dif = 30  350 -- (-320)
	return -320
end


-- Com o segundo trecho:
function calculo(350,30)
	local dif = 30  350 -- (-320)
	dif = (-320 + 180) % 360  180
	--[[
	dif = -140 % 360 – 180
	dif = 220 – 180
	dif = 40
	--]]
	return 40
end

O que daria o seguinte:

  • 1) 350 – 320 = 30
  • 2) 350 + 40 = 390 → 30**

**No segundo caso deu 390, mas queremos o valor 30. Lembre-se que o valor máximo de um ângulo é 360º, então nesse segundo caso ele percorre até os 360 e mais 30 (total de 40 unidades), o que é mais curto do que sair do 350 e voltar até o 30 (320 unidades).

Edited by MaligNos
  • Thanks 1
Link to comment
54 minutes ago, #Gubiani said:

Então basicamente tu ta falando pro computador fazer o calculo para ele percorrer até no máximo 360 graus, e com isso ele conseguir rotacionar?

Com o segundo trecho ele sempre retornará um valor entre -180...180, mas isso nem importa para o nosso caso, tenha conhecimento apenas de como funciona o esquema de valores relativos (diferença) e a lógica de como calculá-los (geralmente apenas simples subtrações).

Edited by MaligNos
  • Thanks 1
Link to comment
On 14/12/2018 at 18:40, MaligNos said:

Com o segundo trecho ele sempre retornará um valor entre -180...180, mas isso nem importa para o nosso caso, tenha conhecimento apenas de como funciona o esquema de valores relativos (diferença) e a lógica de como calculá-los (geralmente apenas simples subtrações).

Certo, muito obrigado!

Link to comment

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...