How to implement shaky mouse cursor to my project?

Hi

I want to add a scene to my FPS project where the player has to make a decision and pick one of two options on screen. The trick is that I want to have a feature which when hovered over one option, makes the mouse cursor shake and forces it to go to the second option, so the payer has to fight with it to select the former. I can’t really find an example, but I’m almost 100% sure I saw something like that in a game. Is it possible to do in Blueprints?

I would appreciate any help.

[…]when hovered over one
option, makes the mouse cursor shake
and forces it to go to the second
option, so the payer has to fight with
it to select the former.

Uncommon, for sure.

Could you clarify one thing - are the options a part of the interface or part of the world?

Whichever is easier, I guess. I have no clue from which angle to approach this problem, so I’m open to any suggestions.

Perhaps a transparent widget with 2 buttons would work, but that still needs the mouse shake feature.

At the most basic level you could try something like that:

Create an offset every .5s:

When mouse is over the widget:

Image from Gyazo

For something a tad more complex - cursor gravitating towards a specific screen coordinate, you’d need to translate widget geometry from absolute to local and back. And this can get annoying with nested elements.

I’d probably work in some kind of interpolation into this to make it less frustrating than it is atm. I’d smash my mouse if I encountered this in any game - you sure about this feature being a sound idea?! :smiley:

I tried it and to be honest it works better than I expected. The shake would still need to be more frequent and the green “yes” button should have some kind of gravity pull affecting the cursor, so it looks like it’s fighting with the player.

I want to implement a “big decision” moment to the project and I really need to show how the main character wants to kill the bad guy, but knows he can’t because (insert a reason here). So in that case there would be a “kill” and “spare” options and the cursor would automatically go to “kill” and shake when hovered over “spare”. It’s just something I want to try out as a storytelling practice.

Thank you, Everynone. For now it’s a good start and I think I can make something out of it.

I had a more serious go at this, still not perfect, though for reasons stated somewhere below.


A more uniform, clamped random vector for the mouse wiggle:

This has changed a wee bit:

Image from Gyazo

Imagine there is a spring (with infinite minimum length) with one end anchored to the centre of the red button and the other end attached to the cursor. It will try to pull the cursor along its compression vector. The further we are from the desired location (spring resting state 0,0,0), the stronger the pull; the attract force can be interrupted by the mouse input and the random mouse wiggle we add every frame.

We calculate the l_mAttractVector which describes the distance and direction mouse cursor needs to travel in order to reach desitnation.

Using a vSpring for this rather than a v2dInterp To because of how horribly linear pixel interpolation is for 2d axes. Still not perfect here for other reasons but feels much more natural.

The big gotcha here is trying to move something in screenspace by less than 1pixel - it will not move. When we get close to the spring resting state the attract force becomes so low that it falls below 1 for one of the axes; this results in the next frame sampling stale data for the interpolation. And stuff gets stuck in place.

We brute-force hack around this here by clamping the min vector length to 1.45 (slightly longer than a diagonal of a square at 1.42).

How to improve it:

  • interpolate the mouse wiggle vector size rather than make a new one several times per second; we could scale it in a random direction every frame and let the vector build up up to a clamped range. This would make fighting for input more clever and responsive. Currently it’s more of a brute force approach similar to burst firing and accounting for directional recoil of a gun.

  • ensure that attract force never drops below 1px / frame in any of the axes - ideally by accumulating the attract force in a variable until it reaches a threshold and only then applying it

and the cursor would automatically go
to “kill” and shake when hovered over
“spare”.

Just saw that I missed that one, bummer. It can be done by adding the mouse wiggle only when the mouse coordinates are in specific range - it’s just comparing coords. And a bit of extra logic to dictate when the whole thing kicks in.

Another way would be to make Buttons user widgets, override Mouse Move for that particular element and bump the cursor by a random value.

I can’t thank you enough. Unfortunately, this is getting too complicated for me, so I will have to spend some more time digging in the documentations to fully understand it. Also, UE4 crashed on me twice while I was recreating your blueprint and I need to cool off a bit.

I noticed that you use a lot of Vector2D nodes. Why is that? I don’t usually see them in tutorials and other UE4 videos.

Edit:
After recreating your blueprint I met a roadblock. I can’t connect VSping State to Vector Spring Interp node. It says “only exactly matching structures are considered compatible” when I try to plug it in.

I noticed that you use a lot of
Vector2D nodes. Why is that? I don’t
usually see them in tutorials and
other UE4 videos.

It’s a struct made out of 2 floats. Just a like a vector is a struct made out of 3 floats. I used vector 2d because screen coordinates require a lot of XY, you can use 2 floats for this but it’s more compact this way, less blueprint spaghetti:

300878-annotation-2020-04-29-204230.jpg

After recreating your blueprint I met
a roadblock. I can’t connect VSping
State to Vector Spring Interp node. It
says “only exactly matching structures
are considered compatible” when I try
to plug it in.

Because it’s not a vector 2d:

300879-vtooltip.jpg

You can hover over pins to see what type they are - this is a Vector Spring State Structure - it holds a bunch of PID data.

You can always right click pins and promote them - this automates variable creation, and they’re always correct type, too:

300880-promote.jpg

You can always right click pins and promote them - this automates variable creation, and they’re always correct type, too:

That fixed it. They had the same color, so it threw me off guard.

Everything works now and it almost looks like I wanted. I adjusted some of the values (MouseOffsetMagnitude to 20 and MouseChaos to 0.05), so now it feels challenging to keep the cursor on the correct button, but it’s not frustrating.

I’ll see what else can be done to improve this blueprint, but to be honest it looks great right now.

Ha, that’s wicked! Good luck with the rest!

Ha, that’s wicked! Good luck with the rest!

but it’s not frustrating.

Nah, I was half joking. It sounds like it could be cool if implemented properly and used in moderation. Especially when paired with some other visual cues that the player’s character has a mind of their own.

Many games made dying and losing fun (in a way), so yeah, definitely can be a made into a feature / minigame rather than a nuisance.