I am new to Mathematica, and am having trouble implementing confining boundary conditions for a random walk simulation confining the walker to a pre-defined region (periodic boundary conditions would be interesting as well). Right now the walker does not cross the boundary and instead makes an alternative step. I am not sure how to add an extra case where, should a step be directed outside the boundary (say the right wall) the walker would have four choices up, down, left or just remain at its current position (skip a step).
Clear[randomWalk]
randomWalk[steps_Integer, start_, region_] /; start ∈ region :=
DynamicModule[
{stepTypes, stepList, alternativeStep, stepChoice,
positions, edgePositions, pointPrimitives, text},
stepTypes = Flatten[Permutations[#, {2}] & /@ {{0, 1}, {0, -1}}, 1];
stepList = RandomChoice[stepTypes, steps];
alternativeStep[currentPosition_, nextStep_] :=
RandomChoice[Select[Complement[stepTypes, {nextStep}], (currentPosition + # ∈ region &)]];
stepChoice[currentPosition_, nextStep_, nearEdgePosition_] :=
If[currentPosition + nextStep ∈ region,
currentPosition + nextStep,
(Sow[nearEdgePosition];
currentPosition + alternativeStep[currentPosition, nextStep])];
{positions, edgePositions} =
FoldList[
stepChoice[#1, Sequence @@ #2] &,
start,
MapIndexed[List, stepList]] // Reap;
pointPrimitives[n_Integer] :=
{If[MemberQ[Flatten @ edgePositions, n], Red, Black],
Point[positions[[n]]]};
text[n_Integer] :=
Text[
Style[Row @ {n, ": ", positions[[n]]},
If[MemberQ[Flatten @ edgePositions, n], Red, Black], Bold, 15],
{Right, Top}, {1., 1.}];
Manipulate[
Graphics[{
Gray, region, AbsolutePointSize[5],
White, Line[positions],
pointPrimitives[i],
text[i]},
Frame -> True,
ImagePadding -> 25],
{i, 1, Length[positions], 1}]]
randomWalk[500, {12, 12}, Rectangle[{0, 0}, {25, 25}]]