Jump to content

[HELP] 'setVehicleComponentRotation' on doors.


Moony

Recommended Posts

I decided to dive into the world of rotations.
I know this might be incomplete and even incorrect:

function openCapo()
	local theVeh = getPedOccupiedVehicle(localPlayer)
	local value1 = guiScrollBarGetScrollPosition(caposcroll)
	if theVeh and value1 then
		setVehicleComponentRotation (theVeh, bonnet_dummy, value1, rY, rZ)
	end
end

I've a GUI already created, and the visibility key bound. The first scrollbar (caposcroll) should affect the bonnet_dummy.
This was made with absolute basic thinking process: "if I want doors to open, I need to get the position of the scrollbar". However, I know I still need to tell the game what's the math.min, what's the math.max, and, I think, to also give the order to respond only when the scrollbar is moved.

I would appreciate a finger to point me in the right direction.

Link to comment
  • Moderators

You need to use onClientGUIChanged event, and check when caposcroll changed.
https://wiki.multitheftauto.com/wiki/OnClientGUIChanged

And if you want to change the door state you should use setVehicleDoorOpenRatio instead of setVehicleComponentRotation.
https://wiki.multitheftauto.com/wiki/SetVehicleDoorOpenRatio

addEventHandler("onClientGUIChanged", caposcroll, function() 
    local value = guiScrollBarGetScrollPosition(source) -- value: 0-100
    -- setVehicleDoorOpenRatio required a ratio between 0-1 instead of 0-100, it need to divide by 100
    
    local vehicle = getPedOccupiedVehicle(localPlayer)
    setVehicleDoorOpenRatio(vehicle, value / 100)
end)

 

Edited by Patrick
Link to comment

Should it look something like this?

function openCapo()
	local theVeh = getPedOccupiedVehicle(localPlayer)
	local value1 = guiScrollBarGetScrollPosition(caposcroll)
	if theVeh and value1 then
		setVehicleDoorOpenRatio(theVeh, value1 / 100)
	end
end
addEventHandler("onClientGUIChanged", caposcroll, openCapo)

DB 3 says the second argument in 'addEventHandler' is nil. Changed it too 'getRootElement()', but it still doesn't work; DB 3 throws nothing.

A similar script I found on MTA's resources plays around with 'triggerServerEvent', and the door ratios are being set server side. It made me wonder how the server.Lua catches the scrollbar ID that moved in order to modify the door number, and if I should too set the movement server-side, having the trigger client-side.

Link to comment

Dear Moony,

I think that the issue that DB 3 shows you could be related to our discussion about without a function header vs. onClientResourceStart located here. If you don't post your entire code, could you please check it if caposcroll is created inside an onClientResourceStart event handler? :) If so then you have to either move the addEventHandler call into the creation function or move the creation code outside of the onClientResourceStart event.

I think this special code pattern of Lua and MTA could be creating quite some confusion in the MTA community.

- Martin

Link to comment
7 minutes ago, The_GTA said:

I think that the issue that DB 3 shows you could be related to our discussion about without a function header vs. onClientResourceStart located here. If you don't post your entire code, could you please check it if caposcroll is created inside an onClientResourceStart event handler? :) If so then you have to either move the addEventHandler call into the creation function or move the creation code outside of the onClientResourceStart event.

Hello again, The_GTA!

Here's the complete code (client-side):

function vehModif ()
	vehmod = guiCreateWindow(0.74, 0.22, 0.25, 0.74, "Modificacion de Vehículo", true)
	guiWindowSetSizable(vehmod, false)
		
	openlabel = guiCreateLabel(0.23, 0.03, 0.52, 0.04, "Aberturas", true, vehmod)
	guiLabelSetColor(openlabel, 51, 194, 203)
	guiLabelSetHorizontalAlign(openlabel, "center", false)
	guiLabelSetVerticalAlign(openlabel, "center")
	
	capolabel = guiCreateLabel(0.27, 0.08, 0.46, 0.02, "Capot", true, vehmod)		
	guiLabelSetHorizontalAlign(capolabel, "center", false)
	guiLabelSetVerticalAlign(capolabel, "center")
	caposcroll = guiCreateScrollBar(0.11, 0.10, 0.79, 0.03, true, true, vehmod)
	
	fllabel = guiCreateLabel(0.27, 0.14, 0.46, 0.02, "Puerta delatera izquierda", true, vehmod)
	guiLabelSetHorizontalAlign(fllabel, "center", false)
	guiLabelSetVerticalAlign(fllabel, "center")
	flscroll = guiCreateScrollBar(0.11, 0.16, 0.79, 0.03, true, true, vehmod)
		
	frlabel = guiCreateLabel(0.27, 0.21, 0.46, 0.02, "Puerta delatera derecha", true, vehmod)
	guiLabelSetHorizontalAlign(frlabel, "center", false)
	guiLabelSetVerticalAlign(frlabel, "center")
	frscroll = guiCreateScrollBar(0.11, 0.23, 0.79, 0.03, true, true, vehmod)
		
	rllabel = guiCreateLabel(0.27, 0.27, 0.46, 0.02, "Puerta trasera izquierda", true, vehmod)
	guiLabelSetHorizontalAlign(rllabel, "center", false)
	guiLabelSetVerticalAlign(rllabel, "center")
	rlscroll = guiCreateScrollBar(0.11, 0.29, 0.79, 0.03, true, true, vehmod)
		
	rrlabel = guiCreateLabel(0.27, 0.34, 0.46, 0.02, "Puerta trasera derecha", true, vehmod)
	guiLabelSetHorizontalAlign(rrlabel, "center", false)
	guiLabelSetVerticalAlign(rrlabel, "center")
	rrscroll = guiCreateScrollBar(0.11, 0.36, 0.79, 0.03, true, true, vehmod)
			
	baullabel = guiCreateLabel(0.27, 0.41, 0.46, 0.02, "Baúl", true, vehmod)
	guiLabelSetHorizontalAlign(baullabel, "center", false)
	guiLabelSetVerticalAlign(baullabel, "center")
	baulscroll = guiCreateScrollBar(0.11, 0.43, 0.79, 0.03, true, true, vehmod)

	guiSetVisible (vehmod, false)
end
addEventHandler ("onClientResourceStart", getRootElement(), vehModif)

function openCapo(caposcroll)
	local theVeh = getPedOccupiedVehicle(localPlayer)
	local value1 = guiScrollBarGetScrollPosition(caposcroll)
	if theVeh and value1 then
		setVehicleDoorOpenRatio(theVeh, value1 / 100)
	end
end
addEventHandler("onClientGUIChanged", caposcroll, openCapo)

function showVehModif()
	if (guiGetVisible(vehmod) == false) then
	guiSetVisible (vehmod, true)
	showCursor (true)
	else
	guiSetVisible (vehmod, false)
	showCursor (false)
	end
end
addCommandHandler("vehmod",showVehModif)
bindKey ("F3", "down", showVehModif)

I still couldn't completely understand the difference of what you told me in the other post. I'm running some tests to understand (this is one of them).

I made sure each part of the script ran with an event handler. Everything works, except for the system applying the change when detecting the scrollbar moving.

Link to comment
2 minutes ago, Moony said:

I still couldn't completely understand the difference of what you told me in the other post. I'm running some tests to understand (this is one of them).

I made sure each part of the script ran with an event handler. Everything works, except for the system applying the change when detecting the scrollbar moving.

No problem. I understand that getting used to this coding pattern takes some time. Let me lend you a hand. :)

Did you know that you can put functions into functions in Lua?

function vehModif ()
	vehmod = guiCreateWindow(0.74, 0.22, 0.25, 0.74, "Modificacion de Vehículo", true)
	guiWindowSetSizable(vehmod, false)
		
	openlabel = guiCreateLabel(0.23, 0.03, 0.52, 0.04, "Aberturas", true, vehmod)
	guiLabelSetColor(openlabel, 51, 194, 203)
	guiLabelSetHorizontalAlign(openlabel, "center", false)
	guiLabelSetVerticalAlign(openlabel, "center")
	
	capolabel = guiCreateLabel(0.27, 0.08, 0.46, 0.02, "Capot", true, vehmod)		
	guiLabelSetHorizontalAlign(capolabel, "center", false)
	guiLabelSetVerticalAlign(capolabel, "center")
	caposcroll = guiCreateScrollBar(0.11, 0.10, 0.79, 0.03, true, true, vehmod)
	
	fllabel = guiCreateLabel(0.27, 0.14, 0.46, 0.02, "Puerta delatera izquierda", true, vehmod)
	guiLabelSetHorizontalAlign(fllabel, "center", false)
	guiLabelSetVerticalAlign(fllabel, "center")
	flscroll = guiCreateScrollBar(0.11, 0.16, 0.79, 0.03, true, true, vehmod)
		
	frlabel = guiCreateLabel(0.27, 0.21, 0.46, 0.02, "Puerta delatera derecha", true, vehmod)
	guiLabelSetHorizontalAlign(frlabel, "center", false)
	guiLabelSetVerticalAlign(frlabel, "center")
	frscroll = guiCreateScrollBar(0.11, 0.23, 0.79, 0.03, true, true, vehmod)
		
	rllabel = guiCreateLabel(0.27, 0.27, 0.46, 0.02, "Puerta trasera izquierda", true, vehmod)
	guiLabelSetHorizontalAlign(rllabel, "center", false)
	guiLabelSetVerticalAlign(rllabel, "center")
	rlscroll = guiCreateScrollBar(0.11, 0.29, 0.79, 0.03, true, true, vehmod)
		
	rrlabel = guiCreateLabel(0.27, 0.34, 0.46, 0.02, "Puerta trasera derecha", true, vehmod)
	guiLabelSetHorizontalAlign(rrlabel, "center", false)
	guiLabelSetVerticalAlign(rrlabel, "center")
	rrscroll = guiCreateScrollBar(0.11, 0.36, 0.79, 0.03, true, true, vehmod)
			
	baullabel = guiCreateLabel(0.27, 0.41, 0.46, 0.02, "Baúl", true, vehmod)
	guiLabelSetHorizontalAlign(baullabel, "center", false)
	guiLabelSetVerticalAlign(baullabel, "center")
	baulscroll = guiCreateScrollBar(0.11, 0.43, 0.79, 0.03, true, true, vehmod)

	guiSetVisible (vehmod, false)
  
	local function openCapo(caposcroll)
		local theVeh = getPedOccupiedVehicle(localPlayer)
		local value1 = guiScrollBarGetScrollPosition(caposcroll)
		if theVeh and value1 then
			setVehicleDoorOpenRatio(theVeh, value1 / 100)
		end
	end
	addEventHandler("onClientGUIChanged", caposcroll, openCapo)
end
addEventHandler ("onClientResourceStart", getRootElement(), vehModif)

function showVehModif()
	if (guiGetVisible(vehmod) == false) then
	guiSetVisible (vehmod, true)
	showCursor (true)
	else
	guiSetVisible (vehmod, false)
	showCursor (false)
	end
end
addCommandHandler("vehmod",showVehModif)
bindKey ("F3", "down", showVehModif)

This code works (better) because:
1) caposcroll is being created in the same function as it is being used
2) addEventHandler is being called with caposcroll as second argument after caposcroll has been created

Now that we have this issue out of the way, what other issue do you have with this code? ;)

Link to comment
4 minutes ago, The_GTA said:

Now that we have this issue out of the way, what other issue do you have with this code? ;)

I apologize for being a nag. While I understand the pros of function within function, I still can't understand why this scipt isn't working. It shows up, but the sliders are not moving what they should move (left front door).

I confused a few words; I had accidently set the slider labelled as "bonnet" to open the door ("capo" = bonnet). I also just set the ID of the element to open ('2' = front left door). Both things are fixed.

Here's the last version of the script:

Spoiler

function vehModif ()
	-- Creation of all GUI elements --
	vehmod = guiCreateWindow(0.74, 0.22, 0.25, 0.74, "Modificacion de Vehículo", true)
	guiWindowSetSizable(vehmod, false)
		
	openlabel = guiCreateLabel(0.23, 0.03, 0.52, 0.04, "Aberturas", true, vehmod)
	guiLabelSetColor(openlabel, 51, 194, 203)
	guiLabelSetHorizontalAlign(openlabel, "center", false)
	guiLabelSetVerticalAlign(openlabel, "center")
	
	capolabel = guiCreateLabel(0.27, 0.08, 0.46, 0.02, "Capot", true, vehmod)		
	guiLabelSetHorizontalAlign(capolabel, "center", false)
	guiLabelSetVerticalAlign(capolabel, "center")
	caposcroll = guiCreateScrollBar(0.11, 0.10, 0.79, 0.03, true, true, vehmod)
	
	fllabel = guiCreateLabel(0.27, 0.14, 0.46, 0.02, "Puerta delatera izquierda", true, vehmod)
	guiLabelSetHorizontalAlign(fllabel, "center", false)
	guiLabelSetVerticalAlign(fllabel, "center")
	flscroll = guiCreateScrollBar(0.11, 0.16, 0.79, 0.03, true, true, vehmod)
		
	frlabel = guiCreateLabel(0.27, 0.21, 0.46, 0.02, "Puerta delatera derecha", true, vehmod)
	guiLabelSetHorizontalAlign(frlabel, "center", false)
	guiLabelSetVerticalAlign(frlabel, "center")
	frscroll = guiCreateScrollBar(0.11, 0.23, 0.79, 0.03, true, true, vehmod)
		
	rllabel = guiCreateLabel(0.27, 0.27, 0.46, 0.02, "Puerta trasera izquierda", true, vehmod)
	guiLabelSetHorizontalAlign(rllabel, "center", false)
	guiLabelSetVerticalAlign(rllabel, "center")
	rlscroll = guiCreateScrollBar(0.11, 0.29, 0.79, 0.03, true, true, vehmod)
		
	rrlabel = guiCreateLabel(0.27, 0.34, 0.46, 0.02, "Puerta trasera derecha", true, vehmod)
	guiLabelSetHorizontalAlign(rrlabel, "center", false)
	guiLabelSetVerticalAlign(rrlabel, "center")
	rrscroll = guiCreateScrollBar(0.11, 0.36, 0.79, 0.03, true, true, vehmod)
			
	baullabel = guiCreateLabel(0.27, 0.41, 0.46, 0.02, "Baúl", true, vehmod)
	guiLabelSetHorizontalAlign(baullabel, "center", false)
	guiLabelSetVerticalAlign(baullabel, "center")
	baulscroll = guiCreateScrollBar(0.11, 0.43, 0.79, 0.03, true, true, vehmod)
	guiSetVisible (vehmod, false)
	
	-- Fn that detects when the scrollbar moves, and what it should do (set ratio of door (which door?))
	local function openFL(flscroll)
		local theVeh = getPedOccupiedVehicle(localPlayer)
		local value1 = guiScrollBarGetScrollPosition(flscroll)
		if theVeh and value1 then
			setVehicleDoorOpenRatio(theVeh, value1 / 100, 2) -- <- Forgot to add the part ID. **2 = front left door**
		end
	end
	addEventHandler("onClientGUIChanged", flscroll, openFL)
end
addEventHandler ("onClientResourceStart", getRootElement(), vehModif)

-- Sets GUI visible/invisible with 'F3' and when a command.
function showVehModif()
	if (guiGetVisible(vehmod) == false) then
	guiSetVisible (vehmod, true)
	showCursor (true)
	else
	guiSetVisible (vehmod, false)
	showCursor (false)
	end
end
addCommandHandler("vehmod",showVehModif)
bindKey ("F3", "down", showVehModif)

 

The two prefix letters of the '-scroll' represent the door (i.e. fr- = frontleft-).

Still, nothing's happening.

Do I have to set the movement server-side? This is all happening client-side.

 

Link to comment

Don't worry about being a what you call "nag". There are hurdles imposed by both the MTA system as well as the steep learning curve.

Here is my fixed script portion (line 43+):

	-- Fn that detects when the scrollbar moves, and what it should do (set ratio of door (which door?))
	local function openFL()
		local theVeh = getPedOccupiedVehicle(localPlayer)
		local value1 = guiScrollBarGetScrollPosition(flscroll)
		if theVeh and value1 then
			setVehicleDoorOpenRatio(theVeh, 2, value1 / 100) -- <- Forgot to add the part ID. **2 = front left door**
		end
	end
	addEventHandler("onClientGUIScroll", flscroll, openFL, false)

Changes:
1) in order to detect scrolling you have to use the "onClientGUIScroll" event. the "onClientGUIChanged" event is reserved for textual changes only.
2) you mixed up the second and third parameters of setVehicleDoorOpenRatio. The second is actually the part ID, the third the ratio. You obviously were in a hurry when you forgot to add the part ID.
3) I added the "false" for the addEventHandler function call to prevent event propagation (read the wiki to understand the recommendation).
 

The script has been tested. :)

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