[Solved] Help with character movement/get position of objects

Hi everyone. I’m working on a new project from the ground up. It’s an infinite runner that has a “top down” view with three “roads” and the idea is that the player moves their character up and down to avoid any obstacles.

Here’s an examples I built with random internet assets (Don’t mind the Kirby, it’s just a place-holder)

As of it is right now, the character only has an up-down movement since the horizontal movement will be the “world” moving from right to left.

My idea was to make the MC(main character), with an input of the W-S keys, go up and down to a fixed position marked by different collision objects via updating its position with the position of that corresponding marker. Thing is I can’t get the position nor world_position of those objects. I tried to see if I was getting the value but all I was getting is either 0,0,0 for a position or “expected vector3 got string”.

I’ve read the different manuals on setting the character position with the mouse input/touch but it didn’t work properly either and also watched plenty tutorials on youtube looking for different approaches, alas I’m in a standstill. Any tips on how to approach this?

Edit: Got the position on touch working as intended with the manual. It was a syntaxis error on my end.

Well done for getting this problem solved!!

In the future, if you post your code

using code gates like this

generally speaking people will very quickly be able to help you out.

A 2D infinite runner is a great first project by the way. You’ll be able to teach yourself how to make something that works and is fun to play without too much stress. Good luck!

2 Likes

I will have that in mind for next time, thank you! And sorry for the inconvinience

I’ve solved the issue with the position values being 0, 0, 0. I was trying to capture the values from an element inside a Game Object (.go) instead to try to get the values from the actual game object inside the collection.

(The objects are top, bottom and center, represented with the square collision boxes)

So the next code does work, both for capturing the position of the different objects and to set the position of the player on the central road

function init(self)
	msg.post(".", "acquire_input_focus")
	top_road = go.get_position("top")
	center_road = go.get_position("center")
	bottom_road = go.get_position("bottom")
	self.moving = false
	go.set_position(center_road)
end

Now just got to try to code the moving up-centre-down movement

Ask if you get stuck! I’d probably use a variable to keep track of on which road the player is and on input modify this variable and use go.animate() to move the player to the new road.

I’m already using the go.animete() and I was thinking to do something similar actually with colliders to check the position of the player and then allowing /blocking their movement.

As it is right now I can make it go to the top and bottom but ignores the central road. I will definitely check how variables work with Defold/Lua, thanks for the tips! : D

This is what I’d do to get started:

function init(self)
	msg.post(".", "acquire_input_focus")
	self.top_road = go.get_position("top")
	self.center_road = go.get_position("center")
	self.bottom_road = go.get_position("bottom")
	
	-- the currenr road of the player
	-- 0 = top
	-- 1 = center
	-- 2 = bottom
	self.road = 1
end


local function move_to_road(self, road)
	-- make sure we're not moving outside the top or bottom road
	if road < 0 or road > 2 then
		return
	end
	
	-- update road
	self.road = road

	-- get position of road to move to
	local y = self.center_road
	if self.road == 0 then
		y = self.top_road
	elseif self.road == 2 then
		y = self.bottom_road
	end

	-- move to the road
	go.animate(".", "position.y", go.PLAYBACK_ONCE_FORWARD, y, go.EASING_LINEAR, 0.5)
end


function on_input(self, action_id, action)
	if action.released then
		if action_id == hash("up") then
			move_to_road(self.road - 1)
		elseif action_id == hash("down") then
			move_to_road(self.road + 1)
		end
	end
end
4 Likes

This is something similar to what I was currently trying to do!

As you can see bellow I was making an array with the idea of giving the value of the elements in the table with the intention that the inputs would either Add or Subtract 1 without being able to go bellow 0 or above 2 and 1 be the default central road, just as you are doing with your code

function init(self)
	msg.post(".", "acquire_input_focus")
	top_road = go.get_position("top")
	center_road = go.get_position("center")
	bottom_road = go.get_position("bottom")
	self.moving = false
	go.set_position(center_road)
end

local roads = {

	[0] = top_road,
	[1] = center_road,
	[2] = bottom_road
} 

Truth be told, I was still debating with myself if I should use the collision boxes to check the position and work around that. This is immensely helpful, thank you!

I’m trying your code and it seems to have an issue with values being read as nil.

When trying to debug the self.road I found that it didn’t contain any value, so I tried to see if removing the self. would help but I got to the same point.

Also I added another function and some code on the go.animate line that wheren’t present

local function moved_to_position(self)
	self.moving = false
end

go.animate(".", "position.y", go.PLAYBACK_ONCE_FORWARD, y, go.EASING_LINEAR, 0.2, 0, moved_to_position)

I think there’s a small error in britzl’s code.

The function is defined with parameters like this:

local function move_to_road(self, road)

But called like this:

move_to_road(self.road - 1)

I would adjust to add the self reference before the road variable:

move_to_road(self, self.road - 1)
2 Likes

Yup, just tried it and it works! But seems to be sending a negative value to the go.animate instead of changing the value

I’ve tried to make a go.set_position with these values and tried to then animated but it doesn’t work either, but we are making progress. Thanks!

I think the above is an issue as well. The roads are defined as full positions, when in the move_road function you only want the y.

I would change it to:

local y = self.center_road.y
	if self.road == 0 then
		y = self.top_road.y
	elseif self.road == 2 then
		y = self.bottom_road.y
	end
2 Likes

I typed that on the fly without testing any of it :slight_smile:

1 Like

Don’t worry about it! In the end this is my project and you’re helping developing the movement of it and I’m really grateful you’re spending your time doing it : D

2 Likes

This did the trick. Thank you so much!

1 Like