diff --git a/Making a Wargame.ipynb b/Making a Wargame.ipynb index 26a820a..614b7f2 100644 --- a/Making a Wargame.ipynb +++ b/Making a Wargame.ipynb @@ -720,7 +720,189 @@ }, "outputs": [], "source": [ - "#%load strategygame.kv" + "%%file strategygame.kv\n", + "#:import math math\n", + "\n", + ":\n", + " id: _game\n", + " main_map: _main_map\n", + " map_rows: 30\n", + " map_cols: 10\n", + " BoxLayout:\n", + " orientation: 'horizontal'\n", + " GridLayout:\n", + " id: _main_map\n", + " game: _game\n", + " cols: root.map_cols\n", + " size_hint: .75, 1\n", + " BoxLayout:\n", + " orientation: 'vertical'\n", + " size_hint: .25, 1\n", + " Label:\n", + " id: _stats\n", + " text: 'status'\n", + " size_hint: 1, .66\n", + " canvas.before:\n", + " Color:\n", + " rgba: .49, .49, .81, 1\n", + " Rectangle:\n", + " pos: _stats.pos\n", + " size: _stats.size\n", + " Button:\n", + " text: 'mini-map'\n", + " size_hint: 1, .33\n", + " background_color: .75, .71, .99, 1\n", + "\n", + "\n", + ":\n", + " canvas:\n", + " Color:\n", + " rgba: (1,1,1,1)\n", + " Line:\n", + " points: (self.x, self.y, self.right, self.top)\n", + " width: 2\n", + ":\n", + " canvas:\n", + " Color:\n", + " rgba: (1,1,1,1)\n", + " Line:\n", + " points: (self.x, self.top, self.right, self.y)\n", + " width: 2\n", + ":\n", + " canvas:\n", + " Color:\n", + " rgba: (1,1,1,1)\n", + " Line:\n", + " points: (self.x, self.y, self.x, self.top)\n", + " width: 2\n", + ":\n", + " canvas:\n", + " Color:\n", + " rgba: (1,1,1,1)\n", + " Line:\n", + " points: (self.right, self.y, self.right, self.top)\n", + " width: 2\n", + "\n", + ":\n", + " size_hint: 1, None\n", + " height: self.width / math.sqrt(3)\n" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": { + "collapsed": true + }, + "outputs": [], + "source": [ + "%%file main.py\n", + "import collections\n", + "import random\n", + "\n", + "from kivy import app, properties\n", + "from kivy.uix import button, label\n", + "from kivy.uix.floatlayout import FloatLayout\n", + "\n", + "MapCoords = collections.namedtuple('MapCoords', ['row', 'col'])\n", + "\n", + "\n", + "class StrategyGame(FloatLayout):\n", + " main_map = properties.ObjectProperty(None)\n", + " map_rows = properties.NumericProperty(0)\n", + " map_cols = properties.NumericProperty(0)\n", + "\n", + " def __init__(self, **kwargs):\n", + " super(StrategyGame, self).__init__(**kwargs)\n", + "\n", + " number_of_regions = self.map_rows * self.map_cols\n", + " for region in xrange(0, number_of_regions):\n", + " row = region / self.map_cols\n", + " col = region % self.map_cols\n", + "\n", + " # Add hex cells to make up the map.\n", + " hex_cell = self.pick_hex_cell(row=row, col=col)\n", + " self.main_map.add_widget(hex_cell)\n", + "\n", + " # Add overlay conditionally.\n", + " if (row % 6 == 2 and col % 2 == 0) or (row % 6 == 5 and col % 2 == 1):\n", + " print('({}, {})'.format(row, col))\n", + " self.add_widget(HexMapControlCell(hex_bind=hex_cell))\n", + "\n", + " @staticmethod\n", + " def pick_hex_cell(row, col):\n", + " row_mod = row % 6\n", + " if col % 2 == 0:\n", + " if row_mod == 0:\n", + " return BU()\n", + " elif row_mod in (1, 2):\n", + " return L()\n", + " elif row_mod == 3:\n", + " return TD()\n", + " elif row_mod in (4, 5):\n", + " return R()\n", + " else:\n", + " if row_mod == 0:\n", + " return TD()\n", + " elif row_mod in (1, 2):\n", + " return R()\n", + " elif row_mod == 3:\n", + " return BU()\n", + " elif row_mod in (4, 5):\n", + " return L()\n", + "\n", + "\n", + "class HexMapCell(label.Label):\n", + " def __init__(self, row=0, col=0, **kwargs):\n", + " super(HexMapCell, self).__init__(**kwargs)\n", + " self.coords = MapCoords(row, col)\n", + "\n", + "\n", + "class BU(HexMapCell):\n", + " pass\n", + "\n", + "\n", + "class TD(HexMapCell):\n", + " pass\n", + "\n", + "\n", + "class L(HexMapCell):\n", + " pass\n", + "\n", + "\n", + "class R(HexMapCell):\n", + " pass\n", + "\n", + "\n", + "class HexMapControlCell(button.Button):\n", + " def __init__(self, hex_bind=None, **kwargs):\n", + " super(HexMapControlCell, self).__init__(**kwargs)\n", + " self.hex_bind = hex_bind\n", + " self.background_color = random.random(), random.random(), random.random(), 1\n", + " self.bind(pos=self.reposition_control_cell, size=self.resize_control_cell)\n", + " self.text = '({}, {})'.format(self.hex_bind.coords.row, self.hex_bind.coords.col)\n", + "\n", + " def reposition_control_cell(self, obj, value):\n", + " self.pos = self.hex_bind.pos\n", + "\n", + " def resize_control_cell(self, obj, value):\n", + " self.height = self.hex_bind.height * 2\n", + " self.width = self.hex_bind.width * 2\n", + "\n", + "\n", + "class StrategyGameApp(app.App):\n", + " def build(self):\n", + " return StrategyGame()\n", + "\n", + "if __name__ == '__main__':\n", + " StrategyGameApp().run()\n" + ] + }, + { + "cell_type": "markdown", + "metadata": {}, + "source": [ + "**Warning** if you run this your will get an error!!" ] }, { @@ -744,7 +926,194 @@ "collapsed": true }, "outputs": [], - "source": [] + "source": [ + "%%file strategygame.kv\n", + "#:import math math\n", + "#:include debug.kv\n", + "\n", + ":\n", + " id: _game\n", + " main_map: _main_map\n", + " map_rows: 30\n", + " map_cols: 10\n", + " BoxLayout:\n", + " orientation: 'horizontal'\n", + " GridLayout:\n", + " id: _main_map\n", + " game: _game\n", + " cols: root.map_cols\n", + " size_hint: .75, 1\n", + " BoxLayout:\n", + " orientation: 'vertical'\n", + " size_hint: .25, 1\n", + " Label:\n", + " id: _stats\n", + " text: 'status'\n", + " size_hint: 1, .66\n", + " canvas.before:\n", + " Color:\n", + " rgba: .49, .49, .81, 1\n", + " Rectangle:\n", + " pos: _stats.pos\n", + " size: _stats.size\n", + " Button:\n", + " text: 'mini-map'\n", + " size_hint: 1, .33\n", + " background_color: .75, .71, .99, 1\n", + "\n", + ":\n", + " pos_hint: {'center_x':.5, 'center_y':.5}\n", + " canvas.after:\n", + " Color:\n", + " rgba: 1,1,1,1\n", + " Ellipse:\n", + " segments: 6\n", + " pos: self.pos\n", + " size: min(self.width, self.height), min(self.width, self.height)\n", + "\n", + ":\n", + " size_hint: 1, None\n", + " height: self.width / math.sqrt(3)" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": { + "collapsed": false + }, + "outputs": [], + "source": [ + "%%file main.py\n", + "import collections\n", + "import random\n", + "import math\n", + "from kivy import app, properties\n", + "from kivy.uix import button, label\n", + "from kivy.uix.floatlayout import FloatLayout\n", + "from kivy.graphics import Color, Ellipse, Line\n", + "from kivy.logger import Logger\n", + "\n", + "MapCoords = collections.namedtuple('MapCoords', ['row', 'col'])\n", + "\n", + "\n", + "class StrategyGame(FloatLayout):\n", + " main_map = properties.ObjectProperty(None)\n", + " map_rows = properties.NumericProperty(0)\n", + " map_cols = properties.NumericProperty(0)\n", + "\n", + " def __init__(self, **kwargs):\n", + " super(StrategyGame, self).__init__(**kwargs)\n", + "\n", + " number_of_regions = self.map_rows * self.map_cols\n", + " for region in xrange(0, number_of_regions):\n", + " row = region / self.map_cols\n", + " col = region % self.map_cols\n", + "\n", + " # Add hex cells to make up the map.\n", + " hex_cell = self.pick_hex_cell(row=row, col=col)\n", + " self.main_map.add_widget(hex_cell)\n", + "\n", + " # Add overlay conditionally.\n", + " if (row % 6 == 1 and col % 2 == 1) or (row % 6 == 4 and col % 2 == 0):\n", + " print('({}, {})'.format(row, col))\n", + " #radius = math.sqrt(hex_cell.width**2 + hex_cell.height**2)\n", + " radius = 2*hex_cell.height\n", + " with hex_cell.canvas.after:\n", + " Color(1,0,1,1)\n", + " hex_cell.ell = Line(circle=(hex_cell.x, hex_cell.y,radius, 0, 360, 6), width=2)\n", + " hex_cell.bind(pos=hex_cell.update_pos, size=hex_cell.update_pos)\n", + "\n", + "\n", + " @staticmethod\n", + " def pick_hex_cell(row, col):\n", + " row_mod = row % 6\n", + " if col % 2 == 0:\n", + " if row_mod == 0:\n", + " return BU()\n", + " elif row_mod in (1, 2):\n", + " return L()\n", + " elif row_mod == 3:\n", + " return TD()\n", + " elif row_mod in (4, 5):\n", + " return R()\n", + " else:\n", + " if row_mod == 0:\n", + " return TD()\n", + " elif row_mod in (1, 2):\n", + " return R()\n", + " elif row_mod == 3:\n", + " return BU()\n", + " elif row_mod in (4, 5):\n", + " return L()\n", + "\n", + "\n", + "\n", + "class HexMapCell(label.Label):\n", + " def __init__(self, row=0, col=0, **kwargs):\n", + " super(HexMapCell, self).__init__(**kwargs)\n", + " self.coords = MapCoords(row, col)\n", + "\n", + " def update_pos(self, instance, value):\n", + " Logger.info(\"StratGame: {}\".format(instance))\n", + " #radius = math.sqrt(self.width**2 + self.height**2)\n", + " radius = 2*self.height\n", + " self.ell.circle = (self.x, self.y, radius, 0, 360, 6)\n", + "\n", + "\n", + "\n", + "class BU(HexMapCell):\n", + " pass\n", + "\n", + "\n", + "class TD(HexMapCell):\n", + " pass\n", + "\n", + "\n", + "class L(HexMapCell):\n", + " pass\n", + "\n", + "\n", + "class R(HexMapCell):\n", + " pass\n", + "\n", + "\n", + "\n", + "class HexMapControlCell(button.Button):\n", + " def __init__(self, hex_bind=None, **kwargs):\n", + " super(HexMapControlCell, self).__init__(**kwargs)\n", + " self.hex_bind = hex_bind\n", + " self.background_color = random.random(), random.random(), random.random(), 1\n", + " self.bind(pos=self.reposition_control_cell, size=self.resize_control_cell)\n", + " self.text = '({}, {})'.format(self.hex_bind.coords.row, self.hex_bind.coords.col)\n", + "\n", + " def reposition_control_cell(self, obj, value):\n", + " self.pos = self.hex_bind.pos\n", + "\n", + " def resize_control_cell(self, obj, value):\n", + " self.height = self.hex_bind.height * 2\n", + " self.width = self.hex_bind.width * 2\n", + "\n", + "\n", + "class StrategyGameApp(app.App):\n", + " def build(self):\n", + " return StrategyGame()\n", + "\n", + "if __name__ == '__main__':\n", + " StrategyGameApp().run()\n" + ] + }, + { + "cell_type": "markdown", + "metadata": {}, + "source": [ + "What did we learn? \n", + "\n", + "* angle 0 appears to be straight up for a circle or ellipse\n", + "* The radius of the hexagon is 2*height\n", + "* Make sure you fix the aspect ratio of the rectangles you're basing things now\n", + "* " + ] } ], "metadata": { diff --git a/main.py b/main.py index f29b13c..9cfe363 100644 --- a/main.py +++ b/main.py @@ -1,9 +1,11 @@ import collections import random - +import math from kivy import app, properties from kivy.uix import button, label from kivy.uix.floatlayout import FloatLayout +from kivy.graphics import Color, Ellipse, Line +from kivy.logger import Logger MapCoords = collections.namedtuple('MapCoords', ['row', 'col']) @@ -26,9 +28,15 @@ class StrategyGame(FloatLayout): self.main_map.add_widget(hex_cell) # Add overlay conditionally. - if (row % 6 == 2 and col % 2 == 0) or (row % 6 == 5 and col % 2 == 1): + if (row % 6 == 1 and col % 2 == 1) or (row % 6 == 4 and col % 2 == 0): print('({}, {})'.format(row, col)) - self.add_widget(HexMapControlCell(hex_bind=hex_cell)) + #radius = math.sqrt(hex_cell.width**2 + hex_cell.height**2) + radius = 2*hex_cell.height + with hex_cell.canvas.after: + Color(1,0,1,1) + hex_cell.ell = Line(circle=(hex_cell.x, hex_cell.y,radius, 0, 360, 6), width=2) + hex_cell.bind(pos=hex_cell.update_pos, size=hex_cell.update_pos) + @staticmethod def pick_hex_cell(row, col): @@ -53,11 +61,19 @@ class StrategyGame(FloatLayout): return L() + class HexMapCell(label.Label): def __init__(self, row=0, col=0, **kwargs): super(HexMapCell, self).__init__(**kwargs) self.coords = MapCoords(row, col) + def update_pos(self, instance, value): + Logger.info("StratGame: {}".format(instance)) + #radius = math.sqrt(self.width**2 + self.height**2) + radius = 2*self.height + self.ell.circle = (self.x, self.y, radius, 0, 360, 6) + + class BU(HexMapCell): pass @@ -75,6 +91,7 @@ class R(HexMapCell): pass + class HexMapControlCell(button.Button): def __init__(self, hex_bind=None, **kwargs): super(HexMapControlCell, self).__init__(**kwargs) diff --git a/strategygame.kv b/strategygame.kv index 7efe1d1..37efb25 100644 --- a/strategygame.kv +++ b/strategygame.kv @@ -1,4 +1,5 @@ #:import math math +#:include debug.kv : id: _game @@ -30,36 +31,16 @@ size_hint: 1, .33 background_color: .75, .71, .99, 1 - -: - canvas: +: + pos_hint: {'center_x':.5, 'center_y':.5} + canvas.after: Color: - rgba: (1,1,1,1) - Line: - points: (self.x, self.y, self.right, self.top) - width: 2 -: - canvas: - Color: - rgba: (1,1,1,1) - Line: - points: (self.x, self.top, self.right, self.y) - width: 2 -: - canvas: - Color: - rgba: (1,1,1,1) - Line: - points: (self.x, self.y, self.x, self.top) - width: 2 -: - canvas: - Color: - rgba: (1,1,1,1) - Line: - points: (self.right, self.y, self.right, self.top) - width: 2 + rgba: 1,1,1,1 + Ellipse: + segments: 6 + pos: self.pos + size: min(self.width, self.height), min(self.width, self.height) : size_hint: 1, None - height: self.width / math.sqrt(3) + height: self.width / math.sqrt(3) \ No newline at end of file