crap, nothing works anymore. strange ballgaining bugs
[fp1415-soccerfun.git] / src / Team_MartLubbers.icl
1 implementation module Team_MartLubbers
2
3 import Footballer
4 import FootballerFunctions
5
6 Names:: [String]
7 Names = [
8 "Odin",
9 "Frigg",
10 "Thor",
11 "Balder",
12 "Njord",
13 "Freyr",
14 "Freyja",
15 "Tyr",
16 "Bragi",
17 "Heimdall",
18 "Hoder",
19 "Vidar",
20 "Vale",
21 "Ullr",
22 "Forseti"]
23
24 Team_MartLubbers :: !Home !FootballField -> Team
25 Team_MartLubbers home field
26 | home==West = westTeam
27 | otherwise = eastTeam
28 where
29 eastTeam = mirror field westTeam
30 westTeam = [keeper : fielders]
31 clubname = base_TeamName_MartLubbers +++ if (home == West) "_W" "_E"
32 keeper = Aesir clubname home field {zero & px=scale -0.5 field.flength} 1 "Thor"
33 fielders = [Aesir clubname home field {px=scale (-0.5*dx) field.flength,py=scale (0.5*dy) field.fwidth} nr name
34 \\ (dx,dy) <- west_positions_fielders
35 & nr <- [2..]
36 & name <- Names
37 ]
38 west_positions_fielders = [(0.20, 0.40)
39 ,(0.20,-0.40)
40 ,(0.23, 0.00)
41 ,(0.50, 0.45)
42 ,(0.50,-0.45)
43 ,(0.60, 0.00)
44 ,(0.70, 0.35)
45 ,(0.70,-0.35)
46 ,(0.90, 0.05)
47 ,(0.90,-0.05)
48 ]
49
50
51 :: Mem = {home :: !Home, origpos :: Position, seed :: !RandomSeed}
52
53 mirrorMem :: !Mem !FootballField -> Mem
54 mirrorMem mm field = {mm & home=other mm.home, origpos=mirror field mm.origpos}
55
56 Aesir :: !ClubName !Home !FootballField !Position !PlayersNumber !String -> Footballer
57 Aesir club home field position nr name
58 = { playerID = {clubName=club,playerNr=nr}
59 , name = name +++ "_" <+++ nr
60 , length = min_length
61 , pos = position
62 , nose = zero
63 , speed = zero
64 , skills = (Running, Kicking, Tackling)
65 , effect = Nothing
66 , stamina = max_stamina
67 , health = max_health
68 , brain = {memory=if (home == West) mm (mirrorMem mm field), ai = mind field}
69 }
70 where
71 mm = {home=West, origpos=position, seed=nullRandomSeed}
72
73 nextRandomNumber :: !Mem -> (Int, !Mem)
74 nextRandomNumber mm=:{seed} = let (i, newseed) = random seed in (i rem 100, {mm & seed=newseed})
75
76 mind :: !FootballField !(!BrainInput, !Mem) -> (!BrainOutput, !Mem)
77 mind field (x=:{referee,football,others,me}, mm=:{home,origpos})
78 # (i, mm) = nextRandomNumber mm
79 // In case of the end of the half, mirror memory
80 | any (isEndHalf) referee = mind field ({x & referee=filter (\x.not (isEndHalf x)) referee}, mirrorMem mm field)
81 // In case of a pause or end, just halt
82 | any (isPauseGame) referee || any (isGameOver) referee = halt (x, mm)
83 // Keeper
84 | me.playerID.playerNr == 1
85 | i_have_ball = kick closest_free_teammate (x, mm)
86 | ball_in_reach maxCatchReach = (CatchBall, mm)
87 | ball_in_reach maxKickReach = kick closest_free_teammate (x, mm)
88 | ball_their_half = halt (x, mm)
89 | ball_within_16
90 | we_have_ball = stayInGoal (x, mm)
91 | ballIsFree football
92 | isClosest others me ballPos.pxy = halt (x, mm)
93 | otherwise = stayInGoal (x, mm)
94 | otherwise
95 | length (filter player_within_16 them) == 1
96 | (dist me.pos ballPos.pxy) < (maxCatchReach me) = (CatchBall, mm)
97 | otherwise = fix ballPos.pxy (maxCatchReach me) (x, mm)
98 | otherwise = stayInGoal (x, mm)
99 | otherwise
100 | we_have_ball = halt (x, mm)
101 | otherwise = stayInGoal (x, mm)
102 // Defense
103 | me.playerID.playerNr > 7
104 | ball_their_half
105 | i_have_ball = kick closest_free_teammate (x, mm)
106 | otherwise = fix {origpos & px=origpos.px + (scale 0.5 ballPos.pxy.px)} prec (x, mm)
107 | otherwise
108 // TODO I have the ball
109 | i_have_ball = moveForward i (x, mm)
110 // TODO we have the ball
111 | we_have_ball = fix {px=ballPos.pxy.px, py=origpos.py} prec (x, mm)
112 // they have the ball
113 | otherwise = obtainBall i (x, mm)
114 // Attacker
115 | otherwise
116 | i_have_ball = moveForward i (x, mm)
117 | ballIsFree football
118 | ball_in_reach maxGainReach = (GainBall, mm)
119 | isClosest us me ballPos.pxy = fix ballPos.pxy prec (x, mm)
120 | otherwise = fix {px=ballPos.pxy.px + (m 10.0), py=origpos.py} prec (x, mm)
121 | we_have_ball = fix {px=ballPos.pxy.px + (m 10.0), py=origpos.py} prec (x, mm)
122 | otherwise = obtainBall i (x, mm)
123 where
124 obtainBall :: Int -> FootballerAI m
125 obtainBall i
126 | ball_in_reach maxTackleReach && length has_ball > 0
127 | i < 15 = \(_,mm).(Tackle (hd has_ball).playerID (ms 10.0), mm)
128 | otherwise = \(_,mm).(GainBall, mm)
129 | ball_in_reach maxGainReach = \(_,mm).(GainBall, mm)
130 | isClosest us me ballPos.pxy = fix ballPos.pxy prec
131 | otherwise = fix (attract prec closest_free_player ballPos.pxy) prec
132
133 moveForward :: Int -> FootballerAI m
134 moveForward i = kick closest_free_teammate
135
136 stayInGoal = fix (attract goal_area_depth our_goal ballPos.pxy) prec
137 closest_free_player = (closest them me.pos).pos // TODO
138 closest_free_teammate
139 | length players_closer_to_goal > 0 = (closest players_closer_to_goal me.pos).pos
140 | otherwise = their_goal
141
142 players_closer_to_goal = filter (\x.not (closerToHome home x.pos.px me.pos.px)) us
143 player_within_16 p = inPenaltyArea field home p.pos
144 ball_within_16 = inPenaltyArea field home ballPos.pxy
145
146 has_ball = filter (\x.ballIsGainedBy x.playerID football) others
147 we_have_ball = any (\x.sameClub me x) has_ball
148 they_have_ball = any (\x.not (sameClub me x)) has_ball
149 i_have_ball = ballIsGainedBy me.playerID football
150
151 ball_their_half = closerToHome home zero ballPos.pxy.px
152 ball_in_reach distfunc = (dist me.pos ballPos) < (distfunc me)
153
154 our_goal = (centerOfGoal home field)
155 their_goal = (centerOfGoal (other home) field)
156 ballPos = (getBall x).ballPos
157 them = me opponents others
158 us = me team others
159 prec = maxGainReach me
160
161 closest :: [Footballer] Position -> Footballer
162 closest xs p = minListBy (\x y.(dist x.pos p) < (dist y.pos p)) xs
163
164 isClosest :: [Footballer] Footballer Position -> Bool
165 isClosest xs x p = closest [x:xs] p == x
166
167 closerToHome :: !Home -> a a -> Bool | Ord a
168 closerToHome East = (>)
169 closerToHome West = (<)
170
171 distToLine :: Position Position Position -> Metre
172 distToLine a b c = (abs (((b.px-a.px)*(a.py-c.py))-((a.px-c.px)*(b.py-a.py))))/d
173 where
174 (*) m1 m2 = (m (toReal m1)/(toReal m2))
175 (/) m1 m2 = (m (toReal m1)/(toReal m2))
176 d = sqrt(((b.px-a.px)*(b.px-a.px))+((b.py-a.py)*(b.py-a.py)))
177
178 base_TeamName_MartLubbers :: String
179 base_TeamName_MartLubbers = "Æsir"