summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--data.js106
-rw-r--r--rules.js104
-rw-r--r--tools/gendata.js18
3 files changed, 140 insertions, 88 deletions
diff --git a/data.js b/data.js
index f265b3b..4d8cc22 100644
--- a/data.js
+++ b/data.js
@@ -3,59 +3,59 @@ seaports:[0,2,8,9,15,29,30,34],
conquerable:[0,1,7,8,9,10,11,12,13,24,25,26,27,28,29,30,31,32,33,34,35,36],
strongholds:[0,1,7,8,9,10,11,12,13,24,25,26,27,32,33,34,35,36],
locales:[
-{"name":"Reval","type":"bishopric","stronghold":3,"walls":4,"vp":2,"region":"Danish Estonia","ways":[[5,25],[3,32]],"box":{"x":601,"y":3564,"w":206,"h":91}},
-{"name":"Wesenberg","type":"castle","stronghold":2,"walls":4,"vp":1,"region":"Danish Estonia","ways":[[5,26],[17,30],[6,31]],"box":{"x":1448,"y":3625,"w":304,"h":60}},
-{"name":"Narwia","type":"town","stronghold":0,"walls":0,"vp":0,"region":"Danish Estonia","ways":[[7,2],[38,2],[49,2],[46,17],[6,27],[33,28]],"box":{"x":2371,"y":3549,"w":123,"h":31}},
-{"name":"Warbola","type":"town","stronghold":0,"walls":0,"vp":0,"region":"Danish Estonia","ways":[[0,32],[4,33],[8,35]],"box":{"x":292,"y":3797,"w":142,"h":31}},
-{"name":"Harrien","type":"region","stronghold":0,"walls":0,"vp":0,"region":"Danish Estonia","ways":[[3,33],[17,34]],"box":{"x":567,"y":3983,"w":200,"h":100}},
-{"name":"Revala","type":"region","stronghold":0,"walls":0,"vp":0,"region":"Danish Estonia","ways":[[0,25],[1,26]],"box":{"x":1030,"y":3410,"w":200,"h":100}},
-{"name":"Wierland","type":"region","stronghold":0,"walls":0,"vp":0,"region":"Danish Estonia","ways":[[2,27],[23,29],[1,31]],"box":{"x":1999,"y":3680,"w":200,"h":100}},
-{"name":"Dorpat","type":"bishopric","stronghold":3,"walls":4,"vp":2,"region":"Crusader Livonia","ways":[[12,0,3],[22,0],[2,2],[38,2],[49,2],[11,3],[23,36]],"box":{"x":1625,"y":4589,"w":253,"h":91}},
-{"name":"Leal","type":"bishopric","stronghold":3,"walls":4,"vp":2,"region":"Crusader Livonia","ways":[[3,35],[15,37]],"box":{"x":108,"y":4266,"w":205,"h":91}},
-{"name":"Riga","type":"bishopric","stronghold":3,"walls":4,"vp":2,"region":"Crusader Livonia","ways":[[13,8]],"box":{"x":273,"y":6231,"w":205,"h":91}},
-{"name":"Adsel","type":"castle","stronghold":2,"walls":4,"vp":1,"region":"Crusader Livonia","ways":[[13,9],[18,44],[21,44],[14,45]],"box":{"x":1504,"y":5612,"w":185,"h":60}},
-{"name":"Fellin","type":"castle","stronghold":2,"walls":4,"vp":1,"region":"Crusader Livonia","ways":[[7,3],[12,3],[15,7],[17,7],[20,38]],"box":{"x":1013,"y":4583,"w":184,"h":61}},
-{"name":"Odenpäh","type":"castle","stronghold":2,"walls":4,"vp":1,"region":"Crusader Livonia","ways":[[7,0,3],[22,0],[11,3],[14,46]],"box":{"x":1378,"y":5103,"w":250,"h":61}},
-{"name":"Wenden","type":"castle","stronghold":2,"walls":4,"vp":1,"region":"Crusader Livonia","ways":[[9,8],[10,9],[19,40],[21,41]],"box":{"x":909,"y":5759,"w":232,"h":60}},
-{"name":"Kirrumpäh","type":"town","stronghold":0,"walls":0,"vp":0,"region":"Crusader Livonia","ways":[[10,45],[12,46],[32,47]],"box":{"x":1877,"y":5389,"w":175,"h":30}},
-{"name":"Pernau","type":"town","stronghold":0,"walls":0,"vp":0,"region":"Crusader Livonia","ways":[[11,7],[17,7],[8,37]],"box":{"x":517,"y":4580,"w":118,"h":30}},
-{"name":"Rositten","type":"town","stronghold":0,"walls":0,"vp":0,"region":"Crusader Livonia","ways":[[21,42],[18,43]],"box":{"x":2046,"y":6307,"w":146,"h":30}},
-{"name":"Jerwen","type":"region","stronghold":0,"walls":0,"vp":0,"region":"Crusader Livonia","ways":[[11,7],[15,7],[1,30],[4,34]],"box":{"x":1064,"y":3946,"w":200,"h":100}},
-{"name":"Lettgallia","type":"region","stronghold":0,"walls":0,"vp":0,"region":"Crusader Livonia","ways":[[16,43],[10,44],[21,44],[39,50],[32,51]],"box":{"x":2048,"y":5777,"w":200,"h":100}},
-{"name":"Metsepole","type":"region","stronghold":0,"walls":0,"vp":0,"region":"Crusader Livonia","ways":[[20,39],[13,40]],"box":{"x":509,"y":5226,"w":200,"h":100}},
-{"name":"Sackala","type":"region","stronghold":0,"walls":0,"vp":0,"region":"Crusader Livonia","ways":[[11,38],[19,39]],"box":{"x":617,"y":4769,"w":200,"h":100}},
-{"name":"Tolowa","type":"region","stronghold":0,"walls":0,"vp":0,"region":"Crusader Livonia","ways":[[13,41],[16,42],[10,44],[18,44]],"box":{"x":1541,"y":5933,"w":200,"h":100}},
-{"name":"Ugaunia","type":"region","stronghold":0,"walls":0,"vp":0,"region":"Crusader Livonia","ways":[[7,0],[12,0],[49,48],[32,49]],"box":{"x":1957,"y":4940,"w":200,"h":100}},
-{"name":"Waiga","type":"region","stronghold":0,"walls":0,"vp":0,"region":"Crusader Livonia","ways":[[6,29],[7,36]],"box":{"x":1535,"y":4113,"w":200,"h":100}},
-{"name":"Novgorod","type":"novgorod","stronghold":3,"walls":3,"vp":3,"region":"Novgorodan Rus","ways":[[27,6],[47,6],[31,23],[41,62],[40,63]],"box":{"x":4318,"y":4315,"w":333,"h":112}},
-{"name":"Ladoga","type":"city","stronghold":3,"walls":3,"vp":2,"region":"Novgorodan Rus","ways":[[31,22],[30,24],[44,59]],"box":{"x":4619,"y":2817,"w":238,"h":90}},
-{"name":"Pskov","type":"city","stronghold":3,"walls":3,"vp":2,"region":"Novgorodan Rus","ways":[[49,4],[39,10],[32,52],[52,68],[37,69]],"box":{"x":2680,"y":5263,"w":205,"h":91}},
-{"name":"Rusa","type":"city","stronghold":3,"walls":3,"vp":2,"region":"Novgorodan Rus","ways":[[24,6],[47,6],[28,13]],"box":{"x":4329,"y":5166,"w":205,"h":92}},
-{"name":"Lovat","type":"traderoute","stronghold":0,"walls":0,"vp":1,"region":"Novgorodan Rus","ways":[[27,13],[36,14]],"box":{"x":4243,"y":5581,"w":187,"h":63}},
-{"name":"Luga","type":"traderoute","stronghold":0,"walls":0,"vp":1,"region":"Novgorodan Rus","ways":[[33,18]],"box":{"x":2667,"y":3295,"w":148,"h":62}},
-{"name":"Neva","type":"traderoute","stronghold":0,"walls":0,"vp":1,"region":"Novgorodan Rus","ways":[[25,24],[51,55],[45,57],[44,58]],"box":{"x":3924,"y":2934,"w":148,"h":62}},
-{"name":"Volkhov","type":"traderoute","stronghold":0,"walls":0,"vp":1,"region":"Novgorodan Rus","ways":[[25,22],[24,23]],"box":{"x":4591,"y":3783,"w":231,"h":63}},
-{"name":"Izborsk","type":"fort","stronghold":1,"walls":3,"vp":1,"region":"Novgorodan Rus","ways":[[14,47],[22,49],[18,51],[26,52]],"box":{"x":2240,"y":5431,"w":241,"h":62}},
-{"name":"Kaibolovo","type":"fort","stronghold":1,"walls":3,"vp":1,"region":"Novgorodan Rus","ways":[[29,18],[42,19],[2,28],[34,53]],"box":{"x":2904,"y":3522,"w":285,"h":62}},
-{"name":"Koporye","type":"fort","stronghold":1,"walls":3,"vp":1,"region":"Novgorodan Rus","ways":[[33,53],[51,54]],"box":{"x":3133,"y":3160,"w":241,"h":62}},
-{"name":"Porkhov","type":"fort","stronghold":1,"walls":3,"vp":1,"region":"Novgorodan Rus","ways":[[47,16],[37,70],[48,71]],"box":{"x":3515,"y":5467,"w":241,"h":63}},
-{"name":"Velikiye Luki","type":"fort","stronghold":1,"walls":3,"vp":1,"region":"Novgorodan Rus","ways":[[28,14],[50,72]],"box":{"x":3706,"y":6347,"w":351,"h":61}},
-{"name":"Dubrovno","type":"town","stronghold":0,"walls":0,"vp":0,"region":"Novgorodan Rus","ways":[[47,15],[26,69],[35,70]],"box":{"x":3153,"y":5214,"w":161,"h":31}},
-{"name":"Gdov","type":"town","stronghold":0,"walls":0,"vp":0,"region":"Novgorodan Rus","ways":[[49,1,2],[2,2],[7,2],[46,65]],"box":{"x":2427,"y":4149,"w":88,"h":30}},
-{"name":"Ostrov","type":"town","stronghold":0,"walls":0,"vp":0,"region":"Novgorodan Rus","ways":[[26,10],[50,11],[18,50]],"box":{"x":2746,"y":5717,"w":115,"h":30}},
-{"name":"Sablia","type":"town","stronghold":0,"walls":0,"vp":0,"region":"Novgorodan Rus","ways":[[42,20],[24,63],[47,64]],"box":{"x":3788,"y":4541,"w":104,"h":31}},
-{"name":"Tesovo","type":"town","stronghold":0,"walls":0,"vp":0,"region":"Novgorodan Rus","ways":[[42,21],[43,61],[24,62]],"box":{"x":3936,"y":4102,"w":121,"h":32}},
-{"name":"Zheltsy","type":"town","stronghold":0,"walls":0,"vp":0,"region":"Novgorodan Rus","ways":[[33,19],[40,20],[41,21],[46,66]],"box":{"x":3501,"y":4176,"w":128,"h":30}},
-{"name":"Ingria","type":"region","stronghold":0,"walls":0,"vp":0,"region":"Novgorodan Rus","ways":[[51,56],[44,60],[41,61]],"box":{"x":3820,"y":3639,"w":200,"h":100}},
-{"name":"Izhora","type":"region","stronghold":0,"walls":0,"vp":0,"region":"Novgorodan Rus","ways":[[30,58],[25,59],[43,60]],"box":{"x":4074,"y":3323,"w":200,"h":100}},
-{"name":"Karelia","type":"region","stronghold":0,"walls":0,"vp":0,"region":"Novgorodan Rus","ways":[[30,57]],"box":{"x":3833,"y":2408,"w":200,"h":100}},
-{"name":"Plyussa River","type":"region","stronghold":0,"walls":0,"vp":0,"region":"Novgorodan Rus","ways":[[2,17],[38,65],[42,66],[52,67]],"box":{"x":2829,"y":4234,"w":200,"h":100}},
-{"name":"Shelon River","type":"region","stronghold":0,"walls":0,"vp":0,"region":"Novgorodan Rus","ways":[[24,6],[27,6],[37,15],[35,16],[40,64]],"box":{"x":3654,"y":4864,"w":200,"h":100}},
-{"name":"Sorot River","type":"region","stronghold":0,"walls":0,"vp":0,"region":"Novgorodan Rus","ways":[[50,12],[35,71]],"box":{"x":3299,"y":5781,"w":200,"h":100}},
-{"name":"Uzmen","type":"region","stronghold":0,"walls":0,"vp":0,"region":"Novgorodan Rus","ways":[[38,1,2],[2,2],[7,2],[26,4],[52,5],[22,48]],"box":{"x":2112,"y":4692,"w":200,"h":100}},
-{"name":"Velikaya River","type":"region","stronghold":0,"walls":0,"vp":0,"region":"Novgorodan Rus","ways":[[39,11],[48,12],[36,72]],"box":{"x":3029,"y":6090,"w":200,"h":100}},
-{"name":"Vod","type":"region","stronghold":0,"walls":0,"vp":0,"region":"Novgorodan Rus","ways":[[34,54],[30,55],[43,56]],"box":{"x":3488,"y":3345,"w":200,"h":100}},
-{"name":"Zhelcha River","type":"region","stronghold":0,"walls":0,"vp":0,"region":"Novgorodan Rus","ways":[[49,5],[46,67],[26,68]],"box":{"x":2782,"y":4586,"w":200,"h":100}},
+{"name":"Reval","type":"bishopric","stronghold":3,"walls":4,"vp":2,"region":"Danish Estonia","ways":[[5,25],[3,32]],"box":{"x":601,"y":3564,"w":206,"h":91},"adjacent":[3,5],"adjacent_by_trackway":[3,5]},
+{"name":"Wesenberg","type":"castle","stronghold":2,"walls":4,"vp":1,"region":"Danish Estonia","ways":[[5,26],[17,30],[6,31]],"box":{"x":1448,"y":3625,"w":304,"h":60},"adjacent":[5,6,17],"adjacent_by_trackway":[5,6,17]},
+{"name":"Narwia","type":"town","stronghold":0,"walls":0,"vp":0,"region":"Danish Estonia","ways":[[7,2],[38,2],[49,2],[46,17],[6,27],[33,28]],"box":{"x":2371,"y":3549,"w":123,"h":31},"adjacent":[6,7,33,38,46,49],"adjacent_by_trackway":[6,33]},
+{"name":"Warbola","type":"town","stronghold":0,"walls":0,"vp":0,"region":"Danish Estonia","ways":[[0,32],[4,33],[8,35]],"box":{"x":292,"y":3797,"w":142,"h":31},"adjacent":[0,4,8],"adjacent_by_trackway":[0,4,8]},
+{"name":"Harrien","type":"region","stronghold":0,"walls":0,"vp":0,"region":"Danish Estonia","ways":[[3,33],[17,34]],"box":{"x":567,"y":3983,"w":200,"h":100},"adjacent":[3,17],"adjacent_by_trackway":[3,17]},
+{"name":"Revala","type":"region","stronghold":0,"walls":0,"vp":0,"region":"Danish Estonia","ways":[[0,25],[1,26]],"box":{"x":1030,"y":3410,"w":200,"h":100},"adjacent":[0,1],"adjacent_by_trackway":[0,1]},
+{"name":"Wierland","type":"region","stronghold":0,"walls":0,"vp":0,"region":"Danish Estonia","ways":[[2,27],[23,29],[1,31]],"box":{"x":1999,"y":3680,"w":200,"h":100},"adjacent":[1,2,23],"adjacent_by_trackway":[1,2,23]},
+{"name":"Dorpat","type":"bishopric","stronghold":3,"walls":4,"vp":2,"region":"Crusader Livonia","ways":[[12,0,3],[22,0],[2,2],[38,2],[49,2],[11,3],[23,36]],"box":{"x":1625,"y":4589,"w":253,"h":91},"adjacent":[2,11,12,22,23,38,49],"adjacent_by_trackway":[12,22,23]},
+{"name":"Leal","type":"bishopric","stronghold":3,"walls":4,"vp":2,"region":"Crusader Livonia","ways":[[3,35],[15,37]],"box":{"x":108,"y":4266,"w":205,"h":91},"adjacent":[3,15],"adjacent_by_trackway":[3,15]},
+{"name":"Riga","type":"bishopric","stronghold":3,"walls":4,"vp":2,"region":"Crusader Livonia","ways":[[13,8]],"box":{"x":273,"y":6231,"w":205,"h":91},"adjacent":[13],"adjacent_by_trackway":[]},
+{"name":"Adsel","type":"castle","stronghold":2,"walls":4,"vp":1,"region":"Crusader Livonia","ways":[[13,9],[18,44],[21,44],[14,45]],"box":{"x":1504,"y":5612,"w":185,"h":60},"adjacent":[13,14,18,21],"adjacent_by_trackway":[14,18,21]},
+{"name":"Fellin","type":"castle","stronghold":2,"walls":4,"vp":1,"region":"Crusader Livonia","ways":[[7,3],[12,3],[15,7],[17,7],[20,38]],"box":{"x":1013,"y":4583,"w":184,"h":61},"adjacent":[7,12,15,17,20],"adjacent_by_trackway":[20]},
+{"name":"Odenpäh","type":"castle","stronghold":2,"walls":4,"vp":1,"region":"Crusader Livonia","ways":[[7,0,3],[22,0],[11,3],[14,46]],"box":{"x":1378,"y":5103,"w":250,"h":61},"adjacent":[7,11,14,22],"adjacent_by_trackway":[7,14,22]},
+{"name":"Wenden","type":"castle","stronghold":2,"walls":4,"vp":1,"region":"Crusader Livonia","ways":[[9,8],[10,9],[19,40],[21,41]],"box":{"x":909,"y":5759,"w":232,"h":60},"adjacent":[9,10,19,21],"adjacent_by_trackway":[19,21]},
+{"name":"Kirrumpäh","type":"town","stronghold":0,"walls":0,"vp":0,"region":"Crusader Livonia","ways":[[10,45],[12,46],[32,47]],"box":{"x":1877,"y":5389,"w":175,"h":30},"adjacent":[10,12,32],"adjacent_by_trackway":[10,12,32]},
+{"name":"Pernau","type":"town","stronghold":0,"walls":0,"vp":0,"region":"Crusader Livonia","ways":[[11,7],[17,7],[8,37]],"box":{"x":517,"y":4580,"w":118,"h":30},"adjacent":[8,11,17],"adjacent_by_trackway":[8]},
+{"name":"Rositten","type":"town","stronghold":0,"walls":0,"vp":0,"region":"Crusader Livonia","ways":[[21,42],[18,43]],"box":{"x":2046,"y":6307,"w":146,"h":30},"adjacent":[18,21],"adjacent_by_trackway":[18,21]},
+{"name":"Jerwen","type":"region","stronghold":0,"walls":0,"vp":0,"region":"Crusader Livonia","ways":[[11,7],[15,7],[1,30],[4,34]],"box":{"x":1064,"y":3946,"w":200,"h":100},"adjacent":[1,4,11,15],"adjacent_by_trackway":[1,4]},
+{"name":"Lettgallia","type":"region","stronghold":0,"walls":0,"vp":0,"region":"Crusader Livonia","ways":[[16,43],[10,44],[21,44],[39,50],[32,51]],"box":{"x":2048,"y":5777,"w":200,"h":100},"adjacent":[10,16,21,32,39],"adjacent_by_trackway":[10,16,21,32,39]},
+{"name":"Metsepole","type":"region","stronghold":0,"walls":0,"vp":0,"region":"Crusader Livonia","ways":[[20,39],[13,40]],"box":{"x":509,"y":5226,"w":200,"h":100},"adjacent":[13,20],"adjacent_by_trackway":[13,20]},
+{"name":"Sackala","type":"region","stronghold":0,"walls":0,"vp":0,"region":"Crusader Livonia","ways":[[11,38],[19,39]],"box":{"x":617,"y":4769,"w":200,"h":100},"adjacent":[11,19],"adjacent_by_trackway":[11,19]},
+{"name":"Tolowa","type":"region","stronghold":0,"walls":0,"vp":0,"region":"Crusader Livonia","ways":[[13,41],[16,42],[10,44],[18,44]],"box":{"x":1541,"y":5933,"w":200,"h":100},"adjacent":[10,13,16,18],"adjacent_by_trackway":[10,13,16,18]},
+{"name":"Ugaunia","type":"region","stronghold":0,"walls":0,"vp":0,"region":"Crusader Livonia","ways":[[7,0],[12,0],[49,48],[32,49]],"box":{"x":1957,"y":4940,"w":200,"h":100},"adjacent":[7,12,32,49],"adjacent_by_trackway":[7,12,32,49]},
+{"name":"Waiga","type":"region","stronghold":0,"walls":0,"vp":0,"region":"Crusader Livonia","ways":[[6,29],[7,36]],"box":{"x":1535,"y":4113,"w":200,"h":100},"adjacent":[6,7],"adjacent_by_trackway":[6,7]},
+{"name":"Novgorod","type":"novgorod","stronghold":3,"walls":3,"vp":3,"region":"Novgorodan Rus","ways":[[27,6],[47,6],[31,23],[41,62],[40,63]],"box":{"x":4318,"y":4315,"w":333,"h":112},"adjacent":[27,31,40,41,47],"adjacent_by_trackway":[40,41]},
+{"name":"Ladoga","type":"city","stronghold":3,"walls":3,"vp":2,"region":"Novgorodan Rus","ways":[[31,22],[30,24],[44,59]],"box":{"x":4619,"y":2817,"w":238,"h":90},"adjacent":[30,31,44],"adjacent_by_trackway":[44]},
+{"name":"Pskov","type":"city","stronghold":3,"walls":3,"vp":2,"region":"Novgorodan Rus","ways":[[49,4],[39,10],[32,52],[52,68],[37,69]],"box":{"x":2680,"y":5263,"w":205,"h":91},"adjacent":[32,37,39,49,52],"adjacent_by_trackway":[32,37,52]},
+{"name":"Rusa","type":"city","stronghold":3,"walls":3,"vp":2,"region":"Novgorodan Rus","ways":[[24,6],[47,6],[28,13]],"box":{"x":4329,"y":5166,"w":205,"h":92},"adjacent":[24,28,47],"adjacent_by_trackway":[]},
+{"name":"Lovat","type":"traderoute","stronghold":0,"walls":0,"vp":1,"region":"Novgorodan Rus","ways":[[27,13],[36,14]],"box":{"x":4243,"y":5581,"w":187,"h":63},"adjacent":[27,36],"adjacent_by_trackway":[]},
+{"name":"Luga","type":"traderoute","stronghold":0,"walls":0,"vp":1,"region":"Novgorodan Rus","ways":[[33,18]],"box":{"x":2667,"y":3295,"w":148,"h":62},"adjacent":[33],"adjacent_by_trackway":[]},
+{"name":"Neva","type":"traderoute","stronghold":0,"walls":0,"vp":1,"region":"Novgorodan Rus","ways":[[25,24],[51,55],[45,57],[44,58]],"box":{"x":3924,"y":2934,"w":148,"h":62},"adjacent":[25,44,45,51],"adjacent_by_trackway":[44,45,51]},
+{"name":"Volkhov","type":"traderoute","stronghold":0,"walls":0,"vp":1,"region":"Novgorodan Rus","ways":[[25,22],[24,23]],"box":{"x":4591,"y":3783,"w":231,"h":63},"adjacent":[24,25],"adjacent_by_trackway":[]},
+{"name":"Izborsk","type":"fort","stronghold":1,"walls":3,"vp":1,"region":"Novgorodan Rus","ways":[[14,47],[22,49],[18,51],[26,52]],"box":{"x":2240,"y":5431,"w":241,"h":62},"adjacent":[14,18,22,26],"adjacent_by_trackway":[14,18,22,26]},
+{"name":"Kaibolovo","type":"fort","stronghold":1,"walls":3,"vp":1,"region":"Novgorodan Rus","ways":[[29,18],[42,19],[2,28],[34,53]],"box":{"x":2904,"y":3522,"w":285,"h":62},"adjacent":[2,29,34,42],"adjacent_by_trackway":[2,34]},
+{"name":"Koporye","type":"fort","stronghold":1,"walls":3,"vp":1,"region":"Novgorodan Rus","ways":[[33,53],[51,54]],"box":{"x":3133,"y":3160,"w":241,"h":62},"adjacent":[33,51],"adjacent_by_trackway":[33,51]},
+{"name":"Porkhov","type":"fort","stronghold":1,"walls":3,"vp":1,"region":"Novgorodan Rus","ways":[[47,16],[37,70],[48,71]],"box":{"x":3515,"y":5467,"w":241,"h":63},"adjacent":[37,47,48],"adjacent_by_trackway":[37,48]},
+{"name":"Velikiye Luki","type":"fort","stronghold":1,"walls":3,"vp":1,"region":"Novgorodan Rus","ways":[[28,14],[50,72]],"box":{"x":3706,"y":6347,"w":351,"h":61},"adjacent":[28,50],"adjacent_by_trackway":[50]},
+{"name":"Dubrovno","type":"town","stronghold":0,"walls":0,"vp":0,"region":"Novgorodan Rus","ways":[[47,15],[26,69],[35,70]],"box":{"x":3153,"y":5214,"w":161,"h":31},"adjacent":[26,35,47],"adjacent_by_trackway":[26,35]},
+{"name":"Gdov","type":"town","stronghold":0,"walls":0,"vp":0,"region":"Novgorodan Rus","ways":[[49,1,2],[2,2],[7,2],[46,65]],"box":{"x":2427,"y":4149,"w":88,"h":30},"adjacent":[2,7,46,49],"adjacent_by_trackway":[46]},
+{"name":"Ostrov","type":"town","stronghold":0,"walls":0,"vp":0,"region":"Novgorodan Rus","ways":[[26,10],[50,11],[18,50]],"box":{"x":2746,"y":5717,"w":115,"h":30},"adjacent":[18,26,50],"adjacent_by_trackway":[18]},
+{"name":"Sablia","type":"town","stronghold":0,"walls":0,"vp":0,"region":"Novgorodan Rus","ways":[[42,20],[24,63],[47,64]],"box":{"x":3788,"y":4541,"w":104,"h":31},"adjacent":[24,42,47],"adjacent_by_trackway":[24,47]},
+{"name":"Tesovo","type":"town","stronghold":0,"walls":0,"vp":0,"region":"Novgorodan Rus","ways":[[42,21],[43,61],[24,62]],"box":{"x":3936,"y":4102,"w":121,"h":32},"adjacent":[24,42,43],"adjacent_by_trackway":[24,43]},
+{"name":"Zheltsy","type":"town","stronghold":0,"walls":0,"vp":0,"region":"Novgorodan Rus","ways":[[33,19],[40,20],[41,21],[46,66]],"box":{"x":3501,"y":4176,"w":128,"h":30},"adjacent":[33,40,41,46],"adjacent_by_trackway":[46]},
+{"name":"Ingria","type":"region","stronghold":0,"walls":0,"vp":0,"region":"Novgorodan Rus","ways":[[51,56],[44,60],[41,61]],"box":{"x":3820,"y":3639,"w":200,"h":100},"adjacent":[41,44,51],"adjacent_by_trackway":[41,44,51]},
+{"name":"Izhora","type":"region","stronghold":0,"walls":0,"vp":0,"region":"Novgorodan Rus","ways":[[30,58],[25,59],[43,60]],"box":{"x":4074,"y":3323,"w":200,"h":100},"adjacent":[25,30,43],"adjacent_by_trackway":[25,30,43]},
+{"name":"Karelia","type":"region","stronghold":0,"walls":0,"vp":0,"region":"Novgorodan Rus","ways":[[30,57]],"box":{"x":3833,"y":2408,"w":200,"h":100},"adjacent":[30],"adjacent_by_trackway":[30]},
+{"name":"Plyussa River","type":"region","stronghold":0,"walls":0,"vp":0,"region":"Novgorodan Rus","ways":[[2,17],[38,65],[42,66],[52,67]],"box":{"x":2829,"y":4234,"w":200,"h":100},"adjacent":[2,38,42,52],"adjacent_by_trackway":[38,42,52]},
+{"name":"Shelon River","type":"region","stronghold":0,"walls":0,"vp":0,"region":"Novgorodan Rus","ways":[[24,6],[27,6],[37,15],[35,16],[40,64]],"box":{"x":3654,"y":4864,"w":200,"h":100},"adjacent":[24,27,35,37,40],"adjacent_by_trackway":[40]},
+{"name":"Sorot River","type":"region","stronghold":0,"walls":0,"vp":0,"region":"Novgorodan Rus","ways":[[50,12],[35,71]],"box":{"x":3299,"y":5781,"w":200,"h":100},"adjacent":[35,50],"adjacent_by_trackway":[35]},
+{"name":"Uzmen","type":"region","stronghold":0,"walls":0,"vp":0,"region":"Novgorodan Rus","ways":[[38,1,2],[2,2],[7,2],[26,4],[52,5],[22,48]],"box":{"x":2112,"y":4692,"w":200,"h":100},"adjacent":[2,7,22,26,38,52],"adjacent_by_trackway":[22]},
+{"name":"Velikaya River","type":"region","stronghold":0,"walls":0,"vp":0,"region":"Novgorodan Rus","ways":[[39,11],[48,12],[36,72]],"box":{"x":3029,"y":6090,"w":200,"h":100},"adjacent":[36,39,48],"adjacent_by_trackway":[36]},
+{"name":"Vod","type":"region","stronghold":0,"walls":0,"vp":0,"region":"Novgorodan Rus","ways":[[34,54],[30,55],[43,56]],"box":{"x":3488,"y":3345,"w":200,"h":100},"adjacent":[30,34,43],"adjacent_by_trackway":[30,34,43]},
+{"name":"Zhelcha River","type":"region","stronghold":0,"walls":0,"vp":0,"region":"Novgorodan Rus","ways":[[49,5],[46,67],[26,68]],"box":{"x":2782,"y":4586,"w":200,"h":100},"adjacent":[26,46,49],"adjacent_by_trackway":[26,46]},
],
ways:[
{"type":"trackway","locales":[7,12,22],"name":"Crossroads"},
diff --git a/rules.js b/rules.js
index 65eab04..0bde619 100644
--- a/rules.js
+++ b/rules.js
@@ -16,7 +16,6 @@ const P2 = RUSSIANS
// NOTE: With Hidden Mats option, the player order of feed/pay may matter.
const FEED_PAY_DISBAND = true // feed, pay, disband in one go
-const AUTO_TAX = false
let game = null
let view = null
@@ -144,6 +143,9 @@ const LOC_ZHELTSY = find_locale("Zheltsy")
const LOC_TESOVO = find_locale("Tesovo")
const LOC_SABLIA = find_locale("Sablia")
+const AOW_TEUTONIC_RAIDERS = find_card("T2")
+const AOW_RUSSIAN_RAIDERS = find_card("R14")
+
const NOBODY = -1
const NOWHERE = -1
const NOTHING = -1
@@ -2260,6 +2262,20 @@ function do_action_forage() {
// === ACTION: RAVAGE ===
+function has_teutonic_raiders(lord) {
+ if (game.active === TEUTONS)
+ if (lord_has_capability(lord, AOW_TEUTONIC_RAIDERS))
+ return count_lord_horses(lord) > 0
+ return false
+}
+
+function has_russian_raiders(lord) {
+ if (game.active === RUSSIANS)
+ if (lord_has_capability(lord, AOW_RUSSIAN_RAIDERS))
+ return get_lord_forces(lord, LIGHT_HORSE) + get_lord_forces(lord, ASIATIC_HORSE) > 0
+ return false
+}
+
function can_ravage_locale(loc) {
return (
is_enemy_territory(loc) &&
@@ -2270,42 +2286,79 @@ function can_ravage_locale(loc) {
}
function can_action_ravage() {
- let where = get_lord_locale(game.who)
+ let here = get_lord_locale(game.who)
- // TODO: cost 2 if enemy lord is adjacent in 2nd ed
- // TODO: adjacent ability
+ // TODO: cost 2 if enemy lord is adjacent (2nd ed)
- if (can_ravage_locale(where))
+ if (can_ravage_locale(here))
return true
+ if (has_teutonic_raiders(game.who)) {
+ for (let there of data.locales[here].adjacent_by_trackway)
+ if (can_ravage_locale(there) && !has_enemy_lord(there))
+ return true
+ }
+
+ if (has_russian_raiders(game.who)) {
+ for (let there of data.locales[here].adjacent_by_trackway)
+ if (can_ravage_locale(there) && !has_enemy_lord(there))
+ return true
+ }
+
return false
}
function do_action_ravage() {
push_undo()
- game.state = "ravage"
+ if (has_teutonic_raiders(game.who) || has_russian_raiders(game.who)) {
+ game.state = "ravage"
+ } else {
+ let here = get_lord_locale(game.who)
+ ravage_location(here, here)
+ }
}
states.ravage = {
prompt() {
view.prompt = `Ravage: Choose enemy territory to ravage!`
- let where = get_lord_locale(game.who)
+ let here = get_lord_locale(game.who)
- // TODO: adjacent from abilities
+ if (can_ravage_locale(here))
+ gen_action_locale(here)
+
+ if (has_teutonic_raiders(game.who)) {
+ for (let there of data.locales[here].adjacent_by_trackway)
+ if (can_ravage_locale(there) && !has_enemy_lord(there))
+ gen_action_locale(there)
+ }
- gen_action_locale(where)
+ if (has_russian_raiders(game.who)) {
+ for (let there of data.locales[here].adjacent_by_trackway)
+ if (can_ravage_locale(there) && !has_enemy_lord(there))
+ gen_action_locale(there)
+ }
},
- locale(loc) {
- log(`Ravaged at %${loc}`)
- add_ravaged_marker(loc)
- add_lord_assets(game.who, PROV, 1)
- if (!is_region(loc))
- add_lord_assets(game.who, LOOT, 1)
- game.count += 1
- game.state = "actions"
+ locale(there) {
+ let here = get_lord_locale(game.who)
+ ravage_location(here, there)
},
}
+function ravage_location(here, there) {
+ log(`Ravaged at %${there}`)
+
+ // TODO: Raiders - ranged ravage with/without loot
+ if (here !== there) {
+ }
+
+ add_ravaged_marker(there)
+ add_lord_assets(game.who, PROV, 1)
+ if (!is_region(there))
+ add_lord_assets(game.who, LOOT, 1)
+ game.count += 1
+ game.state = "actions"
+}
+
// === ACTION: TAX ===
function can_action_tax() {
@@ -2323,22 +2376,7 @@ function can_action_tax() {
function do_action_tax() {
push_undo()
- if (AUTO_TAX) {
- tax_with_lord(game.who)
- } else {
- game.state = "tax"
- }
-}
-
-states.tax = {
- prompt() {
- view.prompt = `Tax: Choose seat to Tax.`
- let here = get_lord_locale(game.who)
- gen_action_locale(here)
- },
- locale(loc) {
- tax_with_lord(game.who)
- },
+ tax_with_lord(game.who)
}
function tax_with_lord(lord) {
diff --git a/tools/gendata.js b/tools/gendata.js
index d9bf342..11623b0 100644
--- a/tools/gendata.js
+++ b/tools/gendata.js
@@ -4,6 +4,8 @@
const fs = require('fs')
+function cmpnum(a,b) { return a - b }
+
// :r !python3 genboxes.py
const boxes = {
"Wesenberg": [1448,3625,304,60],
@@ -301,6 +303,20 @@ function dumplist(name, list) {
print("],")
}
+locales.forEach(loc => {
+ loc.adjacent = []
+ loc.adjacent_by_trackway = []
+ for (let [to, way] of loc.ways) {
+ if (!loc.adjacent.includes(to))
+ loc.adjacent.push(to)
+ if (ways[way].type === "trackway")
+ if (!loc.adjacent_by_trackway.includes(to))
+ loc.adjacent_by_trackway.push(to)
+ }
+ loc.adjacent.sort(cmpnum)
+ loc.adjacent_by_trackway.sort(cmpnum)
+})
+
function seats(list) {
return list.split(", ").map(name => locmap[name]).sort((a,b)=>a-b)
}
@@ -589,8 +605,6 @@ let lords = [
let AOW = {}
let cards = []
-function cmpnum(a,b) { return a - b }
-
function arts_of_war_event(name, event, when) {
let c = { name, event, when, capability: null, this_lord: false, lords: null }
cards.push(c)