Netherguild is a game about assembling an expedition deep into earth, exploring and bonding with your team members-it's also a turn based strategy-roguelite game set in a fantasy world with no magic.

Post news Report RSS Netherguild and the Imprecise Hovering

-Or, "how I fixed hovering over tiles without using colliders." A technical tale from my last update about stubbornness and creative solutions!

Posted by on

Netherguild and the Imprecise Hovering


-Or, "how I fixed hovering over tiles without using colliders." A technical tale from my last update about stubbornness and creative solutions!


Preface


Characters sitting around a bonfire


Netherguild is the turn based strategy game I've been solo developing for the last year and a half. As you can see, it usually sports an isometric camera-

Voxel knight standing on a hill

If you look at the cave floor, you'll notice it's "3D"- it has small, perlin-noise based hills and ditches-
(I talk more about the inspiration behind it in this article: Indiedb.com)

And, since the beginning of my development of Netherguild, I vowed to never use Unity's physics system-be it colliders, rigidbodys, everything- Why? I thought it'd be a fun challenge to try and abstract everything into tiles and only simulate physics using animations or particle effects, also I figured not using this mostly-unnecessary feature will improve performance and reduce the final file size (due to Unity not adding un-included features into the build. I'll be frank here and say I don't know if it would also do that with physics, but I hope so).

All of that culminated into one big problem when it comes to raycasting and letting players precisely select the tile they wish to select-


Problem



Imprecise hovering


Incosistant initial hover


With an absence of colliders, I defaulted into raycasting on a plane. And while that is a great solution in the perfect, clean world of 2D- which the early prototype did use- it really didn't fit the rugged, rough world of 3D tiles.

Isometric Tiles As Plane

Some tiles are poking above the plane and some are below it-

As you can imagine, pretending the floor is uniform when it really isn't is bound to make you fall, and it did make navigation uncomfortable, imprecise and downright bad as soon as you were navigating a more steep area of Netherguild's randomly generated mine level (with bigger differences between tile heights).

Tiles that *should* have obstructed other tiles weren't getting picked up correctly- this method was just imprecise with 3D, and made hovering feel unresponsive.
And, during this update, when @Hallgrim pointed out to me that hovering was inaccurate (in addition to other people before him), I had to face my fears and solve this problem.
But, how?


I mean, I can cast a ray, but how can I know where it should stop? How do I know which length it should be? Will I.... have to use colliders and physics, systems that are just overkill and unnecessary for my game?!?

Dramatic Cat


Solution


My first direction of attack was considering "how can I make a more abstract version of colliders?"- I used this approach for checking mouse-hovering on buildings in the overworld for my game, pretty much just checking if the mouse is within their "fake rects"-

FakeRects


But, am I going to create a big tile manager script that checks if a tile is hiding another tile? how the hell would that even work and be as precise as it should be?

No... There must be a better way!

...

And then, I figured out a new approach-

In Netherguild, what decides a tile's height is a "Heightmap"- currently, it's just perlin noise with an added dictionary for exceptions, like the elevator. Somewhere along the generation process, once a tile is spawned/instantiated it's assigned a tile and height according to this class.

perlinNoise

So... why not cast a ray from the camera in the direction of the mouse on the screen, and proceed along that ray until we're below the tile? As soon as we're below a tile, that's probably the tile we're hovering over!

InitialSketch


But uhh... if I want this to be precise, this is going to be a lot of segments and checks. For example, if I check for every 0.1 units of the tile, in an average distance of 10 it'd usually mean a hundred checks. Per frame. And what if in future maps/levels there'd be even more distance between the camera and the floor? am I going to check 500 times per frame? Hell naw-

There must be a better way!

Enter... math.

Instead of checking for 100 times per frame, which just feels wrong (even if it'll work with modern CPUs) why not get as much precision if not more with 11 checks?
And it works a bit like this:

SketchBetter

I start with a certain length of the ray (10 units). Every time I check along the ray, if the point is above the tile, move the ray forward. If it's below the tile, move the ray upwards. Then, I divide the check length by two (5 units, 2.5 units, 1.25 units).

Doing this ends up giving me a lot of precision when it comes to the exact length of the ray.

WorkingHover


Perfect! Except...

CrazyTiles

Oh no. When I hover "between tiles", at times the hover would flip out and quickly toggle between two tiles. If earlier the it felt unresponsive, now it feels hyper-responsive, and not in a good way.

Solution 2.0


Luckily, this is an easy fix. And! We get to abstract tiles, in a way.

SketchFinal

All I ended up doing, is taking the final "mouse position", and checking for how far away from the center of the tile it is. All there is to it is rounding the X and Y coordinates and subtracting to check the vector magnitude. If it's too far away from the center, the imaginary "collider" isn't hit.

FinalHoverGif

There we go! Works like a charm.


If you enjoyed this weird technical article, why not join Netherguild's discord server and say hello?

Thanks for your time and hope you have a great day (:

Post a comment
Sign in or join with:

Only registered members can share their thoughts. So come on! Join the community today (totally free - or sign in with your social account on the right) and join in the conversation.

Follow Report Profile
Icon
Netherguild
Platforms
Windows, Mac, Linux
Creator
DavidCodeAndArt
Engine
Unity
Contact
Send Message
Homepage
Netherguild.com
Release date
Game watch
Follow
News
Related Games
Netherguild
Netherguild Turn Based Strategy
Related Engines
Unity
Unity Commercial
Related Groups
Linux Gamers
Linux Gamers Fans & Clans with 2,971 members
PC Gamers
PC Gamers Hardware & Tech with 745 members
Unity3d Discussion
Unity3d Discussion Educational with 25 members