#### Howdy, Stranger!

It looks like you're new here. If you want to get involved, click one of these buttons!

# Joystick problem

edited June 2017 in Bugs Posts: 12

I have a small problem with my joystick.
I have a joystick but the knob of the joystick sometimes doesn't go all the way to the edge.
Does anyone know how to solve it
Here is my code:

``````-- Joystick Test
displayMode(FULLSCREEN)
-- Use this function to perform your initial setup
function setup()
print("Hello World!")
joystick = {x, y, xMin, xMax, yMin, yMax, size}
joystick.x = -100
joystick.y = -100
joystick.xMin = 0
joystick.xMax = 250
joystick.yMin = 0
joystick.yMax = 250
joystick.size = 140
joystickKnob = {x, y, size}
joystickKnob.x = -100
joystickKnob.y = -100
joystickKnob.size = 110
end

-- This function gets called once every frame
function draw()
-- This sets a dark background color
background(40, 40, 50)

-- This sets the line thickness

fill(0, 0, 0, 255)
strokeWidth(5)
ellipse(joystick.x, joystick.y, joystick.size)
fill(255, 255, 255, 255)
strokeWidth(0)
ellipse(joystickKnob.x, joystickKnob.y, joystickKnob.size)

end

function touched(touch)
if touch.state == BEGAN and touch.x < joystick.xMax and touch.x > joystick.xMin and touch.y < joystick.yMax and touch.y > joystick.yMin
then
joystick.x = touch.x
joystick.y = touch.y
joystickKnob.x = touch.x
joystickKnob.y = touch.y
end
if touch.state == MOVING
then
if touch.x < joystick.x + joystick.size/2  - joystickKnob.size/2 and touch.x > joystick.x - joystick.size/2 + joystickKnob.size/2
then
joystickKnob.x = touch.x
end
if touch.y < joystick.y + joystick.size/2  - joystickKnob.size/2 and touch.y > joystick.y - joystick.size/2 + joystickKnob.size/2
then
joystickKnob.y = touch.y
end
end
if touch.state == ENDED
then
joystick.x = -100
joystick.y = -100
joystickKnob.x = -100
joystickKnob.y = -100
end
end
``````

The code isn't but the best but I tried.

Tagged:

• edited June 2017 Posts: 12

no clue how to have the code in the box thing. sorry

• Mod
Posts: 9,279

@Flappie To show code correctly, put 3 ~'s on a line by themselves before and after the code.

• Mod
edited June 2017 Posts: 9,279

@Flappie I can't recreate the problem you're having. Can you give more info of how to create your problem. The inner circle always touches the outer circle for me.

EDIT: Nevermind, I see what's happening.

• Mod
Posts: 9,279

@Flappie The problem I see is if you slide your finger too fast going outside the inner circle, then you're not capturing the value of touch. You need to increase the touch area of the inner circle.

• Posts: 12

@dave1707 So what I need to do is add is a little more margin to the inner circle?

• edited June 2017 Posts: 12

I added a margin of 10

``````margin = 10

if touch.state == BEGAN and touch.x < joystick.xMax + **margin** and touch.x > joystick.xMin - **margin** and touch.y < joystick.yMax + **margin** and touch.y > joystick.yMin - **margin**
then
joystick.x = touch.x
joystick.y = touch.y
joystickKnob.x = touch.x
joystickKnob.y = touch.y
end
if touch.state == MOVING
then
if touch.x < joystick.x + joystick.size/2  - joystickKnob.size/2  + **margin** and touch.x > joystick.x - joystick.size/2 + joystickKnob.size/2 - **margin**
then
joystickKnob.x = touch.x
end
if touch.y < joystick.y + joystick.size/2  - joystickKnob.size/2 + **margin** and touch.y > joystick.y - joystick.size/2 + joystickKnob.size/2 - **margin**
then
joystickKnob.y = touch.y
end
end

``````
• Mod
Posts: 9,279

@Flappie The margin doesn't solve the problem. It just allows the inner circle to go beyond the outer circle. You still have the problem that if you move your finger too fast, it doesn't get the latest x,y values to move the inner circle far enough. You need to rethink how you move the inner circle.

• Mod
Posts: 9,279

@Flappie One thing you can try is to accept any x,y values even beyond the outer circle, but limit the position of the inner circle to not go beyond the outer circle.

• Mod
edited June 2017 Posts: 9,279

@Flappie Here's a joystick example based on what I said above. The inner circle moves within the outer circle no matter where the moving finger is. Touch anywhere on the screen to display the joystick to move the sprite.

``````displayMode(FULLSCREEN)

function setup()
inner=80    -- size of inner circle
outer=200   -- size of outer circle
diff=outer/2-inner/2
sx,sy=WIDTH/2,HEIGHT/2
spx,spy=0,0
end

function draw()
background(40, 40, 50)
sprite("Planet Cute:Character Horn Girl",sx,sy)
js()
end

function js()
if show then
v1=vec2(cx,cy)
d=v1:dist(vec2(x,y))    -- distance from center to touch point
if d<diff then      -- touch is within outer circle
px,py=x,y
else
a=diff/d     -- touch is outside outer circle
px=(x-cx)*a+cx     -- calculate inner circle position
py=(y-cy)*a+cy
end
stroke(255)
strokeWidth(4)
noFill()
ellipse(cx,cy,outer)     -- draw outer circle
fill(255)
ellipse(px,py,inner)     -- draw inner circle
v1=vec2(px,py)
d1=v1:dist(vec2(cx,cy))     -- determine distance to calculate speed
sp=d1/4+1
spx=(px-cx)/sp
spy=(py-cy)/sp
sx=sx+spx    -- calculate x speed of Sprite
sy=sy+spy    -- calculate y speed of Sprite
elseif math.abs(spx+spy)>.1 then
spx=spx*.98 -- slow the sprite
spy=spy*.98
sx=sx+spx
sy=sy+spy
end
end

function touched(t)
if t.state==BEGAN then  -- get beginning touch points
cx,cy=t.x,t.y
x,y=cx,cy
show=true   -- set to show joystick
end
if t.state==MOVING then   -- get moving touch points
x,y=t.x,t.y
end
if t.state==ENDED then   -- stop showing joystick
show=false
end
end
``````
• Posts: 12

I'm not a very good programmer so I don't know what it does. So could you tell me how it works and what it does?

• Mod
Posts: 9,279

@Flappie I added comments to my above program. As you get more experience at coding, reading other people's code will get easier to understand.

• Posts: 12

Thank you

• Posts: 12

Another question: How do you make it slow down instead of instantly stopping when released? Thank you in advance

• Posts: 12
• Mod
Posts: 9,279

@Flappie Sorry, I got distracted by other things and forgot about your question. Thanks for reminding me. I changed my code above to slow the Sprite instead of stopping it once the joystick is released.

• Posts: 12

Now when you jerk the joystick from one side to the other it doesn't have a nice transistion. How do you make it slow down and then go to the other side?

• Mod
Posts: 9,279

@Flappie That's going to be a bit harder.

• Mod
Posts: 9,279

@Flappie Actually, the easiest way would be to switch the Sprite to use a physics object and use acceleration to vary the speed and direction. How much do you know about the physics engine.

• Mod
Posts: 9,279

@Flappie Here's a version that uses the physics engine. This works the way you were describing, but I'm not sure how well.

``````displayMode(FULLSCREEN)

function setup()
physics.continuous=true
inner=80    -- size of inner circle
outer=200   -- size of outer circle
diff=outer/2-inner/2
lvx,lvy=0,0
p=physics.body(CIRCLE,0)
p.x=WIDTH/2
p.y=HEIGHT/2
p.gravityScale=0
p.linearDamping=1.5
end

function draw()
background(40, 40, 50)
sprite("Planet Cute:Character Horn Girl",p.x,p.y)
js()
end

function js()
if show then
v1=vec2(cx,cy)
d=v1:dist(vec2(x,y))    -- distance from center to touch point
if d<diff then      -- touch is within outer circle
px,py=x,y
else
a=diff/d     -- touch is outside outer circle
px=(x-cx)*a+cx     -- calculate inner circle position
py=(y-cy)*a+cy
end
stroke(255)
strokeWidth(4)
noFill()
ellipse(cx,cy,outer)     -- draw outer circle
fill(255)
ellipse(px,py,inner)     -- draw inner circle
lvx=lvx+(px-cx)/15
lvy=lvy+(py-cy)/15
p.linearVelocity=vec2(lvx,lvy)
end
end

function touched(t)
if t.state==BEGAN then  -- get beginning touch points
cx,cy=t.x,t.y
x,y=cx,cy
lvx=p.linearVelocity.x
lvy=p.linearVelocity.y
show=true   -- set to show joystick
end
if t.state==MOVING then   -- get moving touch points
x,y=t.x,t.y
end
if t.state==ENDED then   -- stop showing joystick
show=false
lvx,lvy=0,0
end
end
``````
• Posts: 12

Yesssss, thank you.

• edited July 2017 Posts: 12

I now have another problem. When I type this:

``````    r.x=100
r.xSize=100
r.y=100
r.ySize=100
r=physics.body(POLYGON,vec2(rx,ry),vec2(rx+rxSize,ry),vec2(rx,ry+rySize),vec2(rx+rxSize,ry+rySize))
``````

It says there is an error. What did I do wrong?

• Mod
Posts: 9,279

@Flappie You have to define the physics body before you can start assigning values to its variables.

• Mod
Posts: 9,279

Here's an example of defining a polygon.

``````displayMode(FULLSCREEN)

function setup()
floor=physics.body(EDGE,vec2(0,20),vec2(WIDTH,20))
floor.type=STATIC
floor.x=0
floor.y=0

p=physics.body(POLYGON,vec2(0,-100),vec2(0,100),vec2(50,100),vec2(50,-100))
p.x=WIDTH/2
p.y=600
p.angle=58
p.restitution=0.7
end

function draw()
background(0)
stroke(255)
strokeWidth(2)
line(0,20,WIDTH,20)
polygon(p)
end

function polygon(p)
pushMatrix()
translate(p.x, p.y)
rotate(p.angle)
for i = 1, #p.points do
local a = p.points[i]
local b = p.points[(i % #p.points)+1]
line(a.x, a.y, b.x, b.y)
end
popMatrix()
end
``````
• Posts: 12

Is it also possible to have variables for the polygon instead of typing it in manually?

• Mod
Posts: 9,279

You can have variables, but the variables then need values to define the shape of the polygon.