Stop walking into walls! Some text-based rogue-likes don't let you walk into walls, and give you your move back if you try to. Why do that when you can make the player move in the closest valid direction?

The challenge

Write a program of function that, given a direction and a 3 by 3 grid of characters, outputs the same grid after the player has taken a step.

For example,

9
#..
.@#
#.#


becomes

#.@
..#
#.#


Input


The direction is given by a single digit from 1 to 9, each corresponding to 8 cardinal directions and standing still. This is derived from the relative locations of the numbers on a keypad:

NW   N   NE
..\  |  /
...7 8 9
W- 4 5 6 -E
...1 2 3
../  |  \
SW   S   SE
However, you may also use the numbers 123, 456, 789 instead of 789, 456, 123. In other words, you may swap the top and bottom 2 rows or numbers if you so choose. These are the only 2 acceptable index combinations.
The 3 by 3 grid will consist of 3 distinct, printable ASCII characters representing walkable floor, walls, and the player. (In the test cases, . is used for floor, #s are walls, and @ is the player)
You may choose what characters your program uses, but you must state them in your answer and they must be consistent over multiple trials.
The character representing the character will always be in the middle of the 3 by  3 grid, and the direction will always be between 1 and 9 (incl.)
You may take input in any order
The 3 by 3 grid can be input as a char array, a string array, a 9 length string, or another reasonable alternative.


Output


Return from a function, or output to StdOut or closest alternative
Trailing spaces and newlines are allowed
You must use the same character representations as the input
The same formats allowed for inputs are allowed for outputs


How the player moves

If the specified direction is blocked by a wall (e.g. if the above example had direction 6), then look at the 2 closest directions:


If one (and only one) direction is free, move the player in that direction.
If no directions are free, look at the next closest 2 directions (excluding direction 5). If you have wrapped all the way around and found no open direction (player surrounded by walls), do not move the player
If both of the directions are open, pick one to move to at random (although not necessarily uniformly).


If the given direction is a 5, do not move the player

Test cases

(# = wall, . = floor, @ = player)


Input:

9
#..
.@#
#.#

Output:

#.@
..#
#.#


Input:

3
#..
.@#
#.#

Output:

#..
..#
#@#


Input:

7
##.
#@#
..#

Output:

##@      ##.
#.#  or  #.#
..#      @.#


Input:

5
...
.@.
...

Output:

...
.@.
...


Input:

2
###
#@#
###

Output:

###
#@#
###


Scoring

This is code-golf, so the shortest answer in bytes wins.
JavaScript (ES6), 192 163 bytes

a=&gt;b=&gt;a[(a[4]=0)+--b]?(A=(c,d)=&gt;c==b|(e=a[c])-(f=a[d])|!e?(a[c-b?(e?e&lt;f:new Date&amp;1)?c:d:4]=2,a):A(+g[c],+h[d]))(+(g="3016X2785")[b],+(h="1250X8367")[b]):(a[b]=2,a)


Notes

This function uses a special input format. The first input is an array of integers (0 for floor, 1 for wall and 2 for player) representing the map. The second input is the (flipped) direction: 1 is north-west, 2 is north, 3 is north-east, 4 is west etc. The inputs should be given through currying syntax (Z(a)(b)).

Test cases

The maps and directions have been modified to suit my input format.



Z=
a=&gt;b=&gt;a[(a[4]=0)+--b]?(A=(c,d)=&gt;c==b|(e=a[c])-(f=a[d])|!e?(a[c-b?(e?e&lt;f:new Date&amp;1)?c:d:4]=2,a):A(+g[c],+h[d]))(+(g="3016X2785")[b],+(h="1250X8367")[b]):(a[b]=2,a)

testcases = [
    [[1,0,0,0,2,1,1,0,1], 3],
    [[1,0,0,0,2,1,1,0,1], 9],
    [[1,1,0,1,2,1,0,0,1], 1],
    [[0,0,0,0,2,0,0,0,0], 5],
    [[1,1,1,1,2,1,1,1,1], 2]
]
for (test of testcases) {
    console.log(Z(test[0])(test[1]))
}