{-# LANGUAGE UnicodeSyntax #-}moduleSoccerFun.FieldwhereimportSoccerFun.GeometryimportSoccerFun.Types(Other(other))dataField=Field{fwidth∷FieldWidth,-- ^ width of ball field (64m <=width <=75m)flength∷FieldLength-- ^ height of ball field (100m<=height<=110m)}derivingShowtypeFieldWidth=MetretypeFieldLength=MetredefaultField∷FielddefaultField=Field{fwidth=75.0,flength=110.0}inPenaltyArea∷Field→Home→Position→BoolinPenaltyAreafieldhomepos=northEdge<=pypos&&pypos<=southEdge&&ifhome==Westthenpxpos<=westEdgeelsepxpos>=eastEdgewherenorthEdge=(fwidthfield)/2.0-radiusPenaltyAreasouthEdge=(fwidthfield)/2.0+radiusPenaltyAreawestEdge=penaltyAreaDeptheastEdge=(flengthfield)-penaltyAreaDepthdataHome=West|Eastderiving(Eq,Show)instanceOtherHomewhereotherWest=EastotherEast=WestisWest∷Home→BoolisWestWest=TrueisWest_=FalseisEast∷Home→BoolisEastEast=TrueisEast_=False-- | goalPoles yields the py coordinates of the north pole and south pole of the goal (note that north < south).goalPoles∷Field→(Metre,Metre)goalPolesfield=(northPole,southPole)wherenorthPole=((fwidthfield)-goalWidth)/2.0southPole=northPole+goalWidth-- | Official metrics of a ball field:radiusCentreCircle=9.15∷FloatgoalWidth=7.32::FloatgoalHeight=2.44::FloatgoalAreaDepth=5.50::FloatradiusCornerKickArea=0.90::Float-- | not official, taken for renderinggoalPoleWidth=0.4::Float-- | not official, taken for renderingradiusCentreSpot=0.3::FloatradiusPenaltySpot=0.2∷MetreradiusPenaltyArea=9.15∷MetrepenaltyAreaDepth=16.50∷MetrepenaltySpotDepth=11.00∷Metre