diff --git a/flatland/utils/editor.py b/flatland/utils/editor.py index 9dac8ca448e6b6270aaf82db85801f2d71cfaf82..c62ad0e7320e3f3fa78e9eeaa3f07291cef84681 100644 --- a/flatland/utils/editor.py +++ b/flatland/utils/editor.py @@ -3,6 +3,9 @@ from numpy import array import time from collections import deque from matplotlib import pyplot as plt +from contextlib import redirect_stdout +import os + # import io # from PIL import Image # from ipywidgets import IntSlider, link, VBox @@ -19,8 +22,8 @@ class JupEditor(object): self.qEvents = deque() # TODO: These are currently estimated values - self.yxBase = array([20, 20]) - self.nPixCell = 70 + self.yxBase = array([6, 21]) # pixel offset + self.nPixCell = 35 self.rcHistory = [] self.iTransLast = -1 @@ -62,6 +65,7 @@ class JupEditor(object): if len(rcHistory) > 1: rcLast = rcHistory[-1] if not np.array_equal(rcLast, rcCell): # only save at transition + # print(y, x, rcCell) rcHistory.append(rcCell) else: rcHistory.append(rcCell) @@ -98,10 +102,14 @@ class JupEditor(object): # Write the cell transition value back into the grid env.rail.grid[tuple(rcMiddle)] = iValCell - plt.figure(figsize=(10, 10)) - self.oRT.renderEnv(spacing=False, arrows=False, sRailColor="gray", show=False) - img = self.oRT.getImage() - plt.clf() + # TODO: bit of a hack - can we suppress the console messages from MPL at source? + with redirect_stdout(os.devnull): + plt.figure(figsize=(10, 10)) + self.oRT.renderEnv(spacing=False, arrows=False, sRailColor="gray", show=False) + img = self.oRT.getImage() + plt.clf() + plt.close() + # This updates the image in the browser with the new rendered image wid.data = img bRedrawn = True diff --git a/notebooks/CanvasEditor.ipynb b/notebooks/CanvasEditor.ipynb index 8888f536db2e2aa0020b7165bdb4c0ae1a86ea33..6013c92842b1c6a8f6863d309d9cebdcf4fa19f9 100644 --- a/notebooks/CanvasEditor.ipynb +++ b/notebooks/CanvasEditor.ipynb @@ -52,7 +52,7 @@ "metadata": {}, "outputs": [], "source": [ - "from ipywidgets import IntSlider, link, VBox" + "from ipywidgets import IntSlider, link, VBox, RadioButtons, HBox" ] }, { @@ -98,8 +98,8 @@ "metadata": {}, "outputs": [], "source": [ - "oEnv = RailEnv(width=10,\n", - " height=10,\n", + "oEnv = RailEnv(width=20,\n", + " height=20,\n", " rail_generator=random_rail_generator(cell_type_relative_proportion=[1,1] + [0.5] * 6),\n", " number_of_agents=0,\n", " obs_builder_object=TreeObsForRailEnv(max_depth=2))\n", @@ -115,7 +115,8 @@ "outputs": [], "source": [ "sfEnv = \"../flatland/env-data/tests/test1.npy\"\n", - "oEnv.rail.load_transition_map(sfEnv)" + "if False:\n", + " oEnv.rail.load_transition_map(sfEnv)" ] }, { @@ -209,7 +210,8 @@ "cell_type": "markdown", "metadata": {}, "source": [ - "### Edit the map below here by dragging the mouse to create transitions" + "### Edit the map below here by dragging the mouse to create transitions\n", + "You can create a dead-end by dragging foward and backward, ie Cell A -> Adjacent Cell B -> back to Cell A" ] }, { @@ -222,7 +224,7 @@ { "data": { "application/vnd.jupyter.widget-view+json": { - "model_id": "3216678923e047dd871b8b10cc87336c", + "model_id": "e36f66779f454856882018ee3fa8e8b3", "version_major": 2, "version_minor": 0 }, @@ -236,6 +238,7 @@ ], "source": [ "#wid_box\n", + "#HBox([wid_img, wid_buttons])\n", "wid_img" ] }, @@ -248,12 +251,104 @@ }, { "cell_type": "code", - "execution_count": 14, + "execution_count": 12, "metadata": {}, "outputs": [], "source": [ "oEnv.rail.save_transition_map(\"../flatland/env-data/tests/test-editor.npy\")" ] + }, + { + "cell_type": "markdown", + "metadata": {}, + "source": [ + "## Junk below here" + ] + }, + { + "cell_type": "code", + "execution_count": 13, + "metadata": {}, + "outputs": [ + { + "data": { + "application/vnd.jupyter.widget-view+json": { + "model_id": "52bb87bcae69447fb1ecbf06fff971bc", + "version_major": 2, + "version_minor": 0 + }, + "text/plain": [ + "RadioButtons(options=('Draw', 'Erase'), value='Draw')" + ] + }, + "metadata": {}, + "output_type": "display_data" + } + ], + "source": [ + "wid_buttons = ipywidgets.RadioButtons(options=[\"Draw\", \"Erase\"])\n", + "wid_buttons" + ] + }, + { + "cell_type": "code", + "execution_count": 14, + "metadata": {}, + "outputs": [ + { + "data": { + "text/plain": [ + "'Draw'" + ] + }, + "execution_count": 14, + "metadata": {}, + "output_type": "execute_result" + } + ], + "source": [ + "wid_buttons.get_interact_value()" + ] + }, + { + "cell_type": "code", + "execution_count": 15, + "metadata": {}, + "outputs": [], + "source": [ + "def evListen(wid, ev):\n", + " x = ev[\"canvasX\"]\n", + " y=ev[\"canvasY\"]\n", + " yxBase = array([6, 21])\n", + " nPixCell = 35\n", + " rcCell = ((array([y, x]) - yxBase) / nPixCell).astype(int)\n", + " print(x, y, (x-21) / 35, (y-6) / 35, rcCell)" + ] + }, + { + "cell_type": "code", + "execution_count": 16, + "metadata": {}, + "outputs": [], + "source": [ + "#wid_img.register_click(evListen)" + ] + }, + { + "cell_type": "code", + "execution_count": 17, + "metadata": {}, + "outputs": [], + "source": [ + "#wid_img.unregister_all()" + ] + }, + { + "cell_type": "code", + "execution_count": null, + "metadata": {}, + "outputs": [], + "source": [] } ], "metadata": {