notebook.py import%20marimo%0A%0A__generated_with%20%3D%20%220.17.7%22%0Aapp%20%3D%20marimo.App(%0A%20%20%20%20width%3D%22full%22%2C%0A%20%20%20%20app_title%3D%22MapWeaver%22%2C%0A%20%20%20%20layout_file%3D%22data%3Aapplication%2Fjson%3Bbase64%2CewogICJ0eXBlIjogImdyaWQiLAogICJkYXRhIjogewogICAgImNvbHVtbnMiOiAyOCwKICAgICJyb3dIZWlnaHQiOiAyMCwKICAgICJtYXhXaWR0aCI6IDE2MDAsCiAgICAiYm9yZGVyZWQiOiBmYWxzZSwKICAgICJjZWxscyI6IFsKICAgICAgewogICAgICAgICJwb3NpdGlvbiI6IFsKICAgICAgICAgIDIzLAogICAgICAgICAgMCwKICAgICAgICAgIDUsCiAgICAgICAgICAzCiAgICAgICAgXQogICAgICB9LAogICAgICB7CiAgICAgICAgInBvc2l0aW9uIjogbnVsbAogICAgICB9LAogICAgICB7CiAgICAgICAgInBvc2l0aW9uIjogWwogICAgICAgICAgMjMsCiAgICAgICAgICA2LAogICAgICAgICAgMywKICAgICAgICAgIDMKICAgICAgICBdCiAgICAgIH0sCiAgICAgIHsKICAgICAgICAicG9zaXRpb24iOiBbCiAgICAgICAgICAyMywKICAgICAgICAgIDMsCiAgICAgICAgICAzLAogICAgICAgICAgMwogICAgICAgIF0KICAgICAgfSwKICAgICAgewogICAgICAgICJwb3NpdGlvbiI6IG51bGwKICAgICAgfSwKICAgICAgewogICAgICAgICJwb3NpdGlvbiI6IFsKICAgICAgICAgIDIsCiAgICAgICAgICAwLAogICAgICAgICAgMTUsCiAgICAgICAgICAzMgogICAgICAgIF0sCiAgICAgICAgInNjcm9sbGFibGUiOiB0cnVlCiAgICAgIH0sCiAgICAgIHsKICAgICAgICAicG9zaXRpb24iOiBbCiAgICAgICAgICAxNywKICAgICAgICAgIDAsCiAgICAgICAgICA2LAogICAgICAgICAgNQogICAgICAgIF0KICAgICAgfSwKICAgICAgewogICAgICAgICJwb3NpdGlvbiI6IFsKICAgICAgICAgIDIsCiAgICAgICAgICAzMiwKICAgICAgICAgIDQsCiAgICAgICAgICAyCiAgICAgICAgXSwKICAgICAgICAic2lkZSI6ICJyaWdodCIKICAgICAgfSwKICAgICAgewogICAgICAgICJwb3NpdGlvbiI6IFsKICAgICAgICAgIDYsCiAgICAgICAgICAzMiwKICAgICAgICAgIDExLAogICAgICAgICAgMgogICAgICAgIF0KICAgICAgfSwKICAgICAgewogICAgICAgICJwb3NpdGlvbiI6IG51bGwKICAgICAgfSwKICAgICAgewogICAgICAgICJwb3NpdGlvbiI6IFsKICAgICAgICAgIDIsCiAgICAgICAgICAzNCwKICAgICAgICAgIDE1LAogICAgICAgICAgMTcKICAgICAgICBdLAogICAgICAgICJzY3JvbGxhYmxlIjogdHJ1ZQogICAgICB9LAogICAgICB7CiAgICAgICAgInBvc2l0aW9uIjogbnVsbAogICAgICB9LAogICAgICB7CiAgICAgICAgInBvc2l0aW9uIjogWwogICAgICAgICAgMTcsCiAgICAgICAgICAzNCwKICAgICAgICAgIDYsCiAgICAgICAgICAyCiAgICAgICAgXQogICAgICB9LAogICAgICB7CiAgICAgICAgInBvc2l0aW9uIjogbnVsbAogICAgICB9LAogICAgICB7CiAgICAgICAgInBvc2l0aW9uIjogWwogICAgICAgICAgMTcsCiAgICAgICAgICAzNiwKICAgICAgICAgIDYsCiAgICAgICAgICAxMwogICAgICAgIF0KICAgICAgfSwKICAgICAgewogICAgICAgICJwb3NpdGlvbiI6IG51bGwKICAgICAgfSwKICAgICAgewogICAgICAgICJwb3NpdGlvbiI6IFsKICAgICAgICAgIDIzLAogICAgICAgICAgMzYsCiAgICAgICAgICA1LAogICAgICAgICAgMTEKICAgICAgICBdCiAgICAgIH0sCiAgICAgIHsKICAgICAgICAicG9zaXRpb24iOiBbCiAgICAgICAgICAxNywKICAgICAgICAgIDUsCiAgICAgICAgICA2LAogICAgICAgICAgMgogICAgICAgIF0KICAgICAgfSwKICAgICAgewogICAgICAgICJwb3NpdGlvbiI6IFsKICAgICAgICAgIDE3LAogICAgICAgICAgNywKICAgICAgICAgIDYsCiAgICAgICAgICAyCiAgICAgICAgXQogICAgICB9LAogICAgICB7CiAgICAgICAgInBvc2l0aW9uIjogbnVsbAogICAgICB9LAogICAgICB7CiAgICAgICAgInBvc2l0aW9uIjogWwogICAgICAgICAgMTcsCiAgICAgICAgICA5LAogICAgICAgICAgNiwKICAgICAgICAgIDYKICAgICAgICBdCiAgICAgIH0sCiAgICAgIHsKICAgICAgICAicG9zaXRpb24iOiBbCiAgICAgICAgICAxNywKICAgICAgICAgIDE1LAogICAgICAgICAgNiwKICAgICAgICAgIDE5CiAgICAgICAgXSwKICAgICAgICAic2Nyb2xsYWJsZSI6IHRydWUKICAgICAgfSwKICAgICAgewogICAgICAgICJwb3NpdGlvbiI6IG51bGwKICAgICAgfSwKICAgICAgewogICAgICAgICJwb3NpdGlvbiI6IFsKICAgICAgICAgIDIzLAogICAgICAgICAgMTUsCiAgICAgICAgICA1LAogICAgICAgICAgMTUKICAgICAgICBdCiAgICAgIH0sCiAgICAgIHsKICAgICAgICAicG9zaXRpb24iOiBudWxsCiAgICAgIH0sCiAgICAgIHsKICAgICAgICAicG9zaXRpb24iOiBudWxsCiAgICAgIH0sCiAgICAgIHsKICAgICAgICAicG9zaXRpb24iOiBudWxsCiAgICAgIH0sCiAgICAgIHsKICAgICAgICAicG9zaXRpb24iOiBudWxsCiAgICAgIH0sCiAgICAgIHsKICAgICAgICAicG9zaXRpb24iOiBudWxsCiAgICAgIH0sCiAgICAgIHsKICAgICAgICAicG9zaXRpb24iOiBudWxsCiAgICAgIH0sCiAgICAgIHsKICAgICAgICAicG9zaXRpb24iOiBudWxsCiAgICAgIH0sCiAgICAgIHsKICAgICAgICAicG9zaXRpb24iOiBudWxsCiAgICAgIH0sCiAgICAgIHsKICAgICAgICAicG9zaXRpb24iOiBudWxsCiAgICAgIH0sCiAgICAgIHsKICAgICAgICAicG9zaXRpb24iOiBudWxsCiAgICAgIH0sCiAgICAgIHsKICAgICAgICAicG9zaXRpb24iOiBudWxsCiAgICAgIH0sCiAgICAgIHsKICAgICAgICAicG9zaXRpb24iOiBudWxsCiAgICAgIH0sCiAgICAgIHsKICAgICAgICAicG9zaXRpb24iOiBudWxsCiAgICAgIH0sCiAgICAgIHsKICAgICAgICAicG9zaXRpb24iOiBudWxsCiAgICAgIH0sCiAgICAgIHsKICAgICAgICAicG9zaXRpb24iOiBudWxsCiAgICAgIH0sCiAgICAgIHsKICAgICAgICAicG9zaXRpb24iOiBudWxsCiAgICAgIH0sCiAgICAgIHsKICAgICAgICAicG9zaXRpb24iOiBudWxsCiAgICAgIH0sCiAgICAgIHsKICAgICAgICAicG9zaXRpb24iOiBudWxsCiAgICAgIH0sCiAgICAgIHsKICAgICAgICAicG9zaXRpb24iOiBudWxsCiAgICAgIH0sCiAgICAgIHsKICAgICAgICAicG9zaXRpb24iOiBudWxsCiAgICAgIH0sCiAgICAgIHsKICAgICAgICAicG9zaXRpb24iOiBudWxsCiAgICAgIH0sCiAgICAgIHsKICAgICAgICAicG9zaXRpb24iOiBudWxsCiAgICAgIH0sCiAgICAgIHsKICAgICAgICAicG9zaXRpb24iOiBudWxsCiAgICAgIH0sCiAgICAgIHsKICAgICAgICAicG9zaXRpb24iOiBudWxsCiAgICAgIH0sCiAgICAgIHsKICAgICAgICAicG9zaXRpb24iOiBudWxsCiAgICAgIH0sCiAgICAgIHsKICAgICAgICAicG9zaXRpb24iOiBudWxsCiAgICAgIH0sCiAgICAgIHsKICAgICAgICAicG9zaXRpb24iOiBudWxsCiAgICAgIH0sCiAgICAgIHsKICAgICAgICAicG9zaXRpb24iOiBudWxsCiAgICAgIH0sCiAgICAgIHsKICAgICAgICAicG9zaXRpb24iOiBbCiAgICAgICAgICAwLAogICAgICAgICAgMCwKICAgICAgICAgIDIsCiAgICAgICAgICAzMgogICAgICAgIF0KICAgICAgfSwKICAgICAgewogICAgICAgICJwb3NpdGlvbiI6IG51bGwKICAgICAgfSwKICAgICAgewogICAgICAgICJwb3NpdGlvbiI6IG51bGwKICAgICAgfQogICAgXQogIH0KfQ%3D%3D%22%2C%0A%20%20%20%20css_file%3D%22%22%2C%0A%20%20%20%20html_head_file%3D%22splash.html%22%2C%0A)%0A%0A%0A%40app.cell%0Adef%20upload_data(mo%2C%20set_input_data)%3A%0A%20%20%20%20_file_browser%20%3D%20mo.ui.file(filetypes%3D%5B%22.geojson%22%2C%20%22.json%22%5D%2C%20on_change%3Dset_input_data%2C%20label%3Df%22Upload%22)%0A%20%20%20%20mo.md(f%22%7Btool_tip(_file_browser%2C%20%22Your%20data%20should%20be%20polygons.%20Currently%20only%20GeoJSON%20formatted%20data%20is%20readable.%22)%7D%22)%0A%20%20%20%20return%0A%0A%0A%40app.cell%0Adef%20read_gdf(%0A%20%20%20%20builtin_gdf%2C%0A%20%20%20%20get_gdf%2C%0A%20%20%20%20get_input_data%2C%0A%20%20%20%20get_numeric_variables%2C%0A%20%20%20%20gpd%2C%0A%20%20%20%20io%2C%0A%20%20%20%20is_valid%2C%0A%20%20%20%20ok_message%2C%0A%20%20%20%20set_crs%2C%0A%20%20%20%20set_gdf%2C%0A%20%20%20%20set_status_message%2C%0A%20%20%20%20set_variables%2C%0A%20%20%20%20wsp%2C%0A)%3A%0A%20%20%20%20%23%20flags%20to%20control%20recovery%20if%20load%20fails%20for%20some%20reason%0A%20%20%20%20_done%20%3D%20False%0A%20%20%20%20_did_repairs%20%3D%20False%0A%20%20%20%20%23%20if%20input%20data%20is%20a%20string%20then%20it's%20the%20initial%20setting%0A%20%20%20%20%23%20otherwise%20it's%20the%20upload%20button%20result%20unless%20that%20is%20length%200%0A%20%20%20%20if%20isinstance(get_input_data()%2C%20str)%20or%20len(get_input_data())%20%3D%3D%200%3A%0A%20%20%20%20%20%20%20%20set_gdf(builtin_gdf)%0A%20%20%20%20%20%20%20%20set_crs(builtin_gdf.crs)%0A%20%20%20%20else%3A%0A%20%20%20%20%20%20%20%20%23%20store%20current%20GDF%20in%20case%20we%20need%20to%20restore%20it%0A%20%20%20%20%20%20%20%20_old_gdf%20%3D%20get_gdf()%0A%20%20%20%20%20%20%20%20try%3A%0A%20%20%20%20%20%20%20%20%20%20%20%20%23%20after%20much%20experimentation%20this%20seems%20to%20be%20the%20most%20reliable%20%0A%20%20%20%20%20%20%20%20%20%20%20%20%23%20way%20to%20load%20JSON%20from%20bytes%20contents%20of%20the%20upload%20button%0A%20%20%20%20%20%20%20%20%20%20%20%20_new_gdf%20%3D%20gpd.read_file(io.BytesIO(get_input_data()%5B0%5D.contents).read().decode())%0A%20%20%20%20%20%20%20%20except%20Exception%20as%20e%3A%0A%20%20%20%20%20%20%20%20%20%20%20%20%23%20would%20be%20better%20to%20figure%20out%20what%20exceptions%20can%20happen%20and%20trap%0A%20%20%20%20%20%20%20%20%20%20%20%20%23%20the%20exact%20type%2C%20but%20we'll%20keep%20an%20eye%20on%20that%20and%20update%0A%20%20%20%20%20%20%20%20%20%20%20%20%23%20meanwhile...%20reset%20to%20the%20current%20GDF%20and%20flag%20error%0A%20%20%20%20%20%20%20%20%20%20%20%20set_gdf(_old_gdf)%0A%20%20%20%20%20%20%20%20%20%20%20%20set_crs(_old_gdf.crs)%0A%20%20%20%20%20%20%20%20%20%20%20%20set_status_message(%22ERROR!%20Exception%20in%20uploading%20data%22)%0A%20%20%20%20%20%20%20%20%20%20%20%20print(e.args)%0A%20%20%20%20%20%20%20%20%20%20%20%20raise%20e%0A%20%20%20%20%20%20%20%20else%3A%0A%20%20%20%20%20%20%20%20%20%20%20%20%23%20if%20not%20enough%20variables%20for%20tiling%20then%20flag%20and%20reset%20to%20current%20GDF%0A%20%20%20%20%20%20%20%20%20%20%20%20_n%20%3D%20len(get_numeric_variables(_new_gdf))%0A%20%20%20%20%20%20%20%20%20%20%20%20if%20_n%20%3C%202%3A%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20set_status_message(%22WARNING!%20One%20or%20fewer%20variables%2C%20data%20not%20loaded%22)%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20set_gdf(_old_gdf)%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20set_crs(_old_gdf.crs)%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20_done%20%3D%20True%20%23%20we're%20done%0A%20%20%20%20%20%20%20%20%20%20%20%20if%20not%20_done%3A%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%23%20check%20no%20topology%20issues%20and%20attempt%20repair%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20if%20not%20all(is_valid(_new_gdf.geometry))%3A%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20_new_gdf.geometry%20%3D%20wsp.tiling_utils.repair_polygon(_new_gdf.geometry)%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%23%20recheck%20and%20if%20repair%20failed%20report%20error%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20if%20not%20all(is_valid(_new_gdf.geometry))%3A%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20set_status_message(%22ERROR!%20Geometries%20not%20valid%2C%20try%20another%20dataset%22)%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20set_gdf(_old_gdf)%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20_done%20%3D%20True%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20else%3A%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20_did_repairs%20%3D%20True%0A%20%20%20%20%20%20%20%20%20%20%20%20if%20not%20_done%3A%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%23%20check%20data%20are%20projected%20and%20reproject%20if%20not%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20if%20not%20_new_gdf.crs.is_projected%3A%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20_new_gdf%20%3D%20_new_gdf.to_crs(3857)%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20set_crs(3857)%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20set_variables(get_numeric_variables(_new_gdf))%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20if%20_did_repairs%3A%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20set_status_message(%22WARNING!%20Repaired%20geometry%20errors%20in%20your%20data%22)%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20else%3A%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20set_status_message(ok_message)%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20set_gdf(_new_gdf)%0A%20%20%20%20return%0A%0A%0A%40app.cell%0Adef%20set_download_type(mo)%3A%0A%20%20%20%20download_type%20%3D%20mo.ui.dropdown(options%3D%5B%22GeoJSON%22%2C%20%22GeoPackage%22%2C%20%22SVG%22%2C%20%22PNG%22%5D%2C%20value%3D%22GeoJSON%22)%0A%20%20%20%20mo.md(f%22%7Btool_tip(download_type%2C%20'Set%20the%20file%20format%20for%20downloaded%20map%20data')%7D%22)%0A%20%20%20%20return%20(download_type%2C)%0A%0A%0A%40app.cell%0Adef%20download_result(%0A%20%20%20%20Path%2C%0A%20%20%20%20download_type%2C%0A%20%20%20%20get_input_data%2C%0A%20%20%20%20io%2C%0A%20%20%20%20mo%2C%0A%20%20%20%20result%2C%0A%20%20%20%20tiled_map%2C%0A%20%20%20%20tiling_map%2C%0A)%3A%0A%20%20%20%20mo.stop(tiling_map)%0A%20%20%20%20if%20isinstance(get_input_data()%2C%20str)%20or%20len(get_input_data())%20%3D%3D%200%3A%0A%20%20%20%20%20%20%20%20_fname%20%3D%20f%22%7BPath(get_input_data()).with_suffix('').stem%7D-map-weaver-map%22%0A%20%20%20%20else%3A%0A%20%20%20%20%20%20%20%20_fname%20%3D%20f%22%7BPath(get_input_data()%5B0%5D.name).stem%7D-map-weaver-map%22%0A%0A%20%20%20%20if%20download_type.value%20%3D%3D%20%22GeoJSON%22%3A%0A%20%20%20%20%20%20%20%20_download_button%20%3D%20mo.download(%0A%20%20%20%20%20%20%20%20%20%20%20%20data%3Dtiled_map.map.to_json().encode('utf-8')%2C%20filename%3Df'%7B_fname%7D.geojson'%2C%20mimetype%3D'text%2Fplain'%2C%20label%3D'Download')%0A%20%20%20%20elif%20download_type.value%20%3D%3D%20%22GeoPackage%22%3A%0A%20%20%20%20%20%20%20%20%23%20here%20we%20have%20to%20use%20a%20BytesIO%20stream%20to%20write%20to%0A%20%20%20%20%20%20%20%20with%20io.BytesIO()%20as%20_f%3A%0A%20%20%20%20%20%20%20%20%20%20%20%20tiled_map.map.to_file(_f%2C%20driver%3D%22GPKG%22%2C%20engine%3D%22fiona%22)%0A%20%20%20%20%20%20%20%20%20%20%20%20_download_button%20%3D%20mo.download(%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20data%3D_f%2C%20filename%3Df'%7B_fname%7D.gpkg'%2C%20mimetype%3D%22application%2Fgeopackage%2Bsqlite3%22%2C%20label%3D'Download')%0A%20%20%20%20elif%20download_type.value%20%3D%3D%20%22SVG%22%3A%0A%20%20%20%20%20%20%20%20with%20io.BytesIO()%20as%20_f%3A%0A%20%20%20%20%20%20%20%20%20%20%20%20result.savefig(_f%2C%20format%3D%22svg%22)%0A%20%20%20%20%20%20%20%20%20%20%20%20_download_button%20%3D%20mo.download(%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20data%3D_f%2C%20filename%3Df'%7B_fname%7D.svg'%2C%20mimetype%3D%22image%2Fsvg%2Bxml%22%2C%20label%3D%22Download%22)%0A%20%20%20%20else%3A%0A%20%20%20%20%20%20%20%20with%20io.BytesIO()%20as%20_f%3A%0A%20%20%20%20%20%20%20%20%20%20%20%20result.savefig(_f%2C%20format%3D%22png%22%2C%20dpi%3D300)%0A%20%20%20%20%20%20%20%20%20%20%20%20_download_button%20%3D%20mo.download(%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20data%3D_f%2C%20filename%3Df'%7B_fname%7D.png'%2C%20mimetype%3D%22image%2Fpng%22%2C%20label%3D%22Download%22)%0A%0A%20%20%20%20mo.md(f'%7Btool_tip(_download_button%2C%20%22Download%20the%20tiled%20map%22)%7D')%0A%20%20%20%20return%0A%0A%0A%40app.cell%0Adef%20get_tiled_map(%0A%20%20%20%20clip_by_areas%2C%0A%20%20%20%20get_gdf%2C%0A%20%20%20%20get_modded_tile_unit%2C%0A%20%20%20%20join_on_prototile%2C%0A%20%20%20%20keep_tileables%2C%0A%20%20%20%20map_as_icons%2C%0A%20%20%20%20wsp%2C%0A)%3A%0A%20%20%20%20tiling_map%20%3D%20True%20%23%20flag%20to%20block%20some%20other%20cells%20(potentially...)%0A%20%20%20%20tiled_map%20%3D%20wsp.Tiling(get_modded_tile_unit()%2C%20get_gdf()%2C%20as_icons%3Dmap_as_icons.value).get_tiled_map(%0A%20%20%20%20%20%20%20%20retain_tileables%3Dkeep_tileables.value%2C%0A%20%20%20%20%20%20%20%20ragged_edges%3Dnot(clip_by_areas.value)%2C%0A%20%20%20%20%20%20%20%20join_on_prototiles%3Djoin_on_prototile.value)%0A%20%20%20%20tiling_map%20%3D%20False%20%23%20stop%20blocking%20other%20cells%0A%20%20%20%20return%20tiled_map%2C%20tiling_map%0A%0A%0A%40app.cell%0Adef%20render_tiled_map(%0A%20%20%20%20get_gdf%2C%0A%20%20%20%20get_selected_colour_palettes%2C%0A%20%20%20%20get_tile_ids%2C%0A%20%20%20%20get_variables%2C%0A%20%20%20%20show_map%2C%0A%20%20%20%20tiled_map%2C%0A)%3A%0A%20%20%20%20tiled_map.ids_to_map%20%3D%20%5Bid%20for%20id%2C%20v%20in%20zip(get_tile_ids()%2C%20get_variables())%20if%20v%20!%3D%20%22---%22%5D%0A%20%20%20%20tiled_map.vars_to_map%20%3D%20%5Bv%20for%20v%20in%20get_variables()%20if%20v%20!%3D%20%22---%22%5D%0A%20%20%20%20tiled_map.colors_to_use%20%3D%20%5Bc%20for%20c%2C%20v%20in%20zip(get_selected_colour_palettes()%2C%20get_variables())%20if%20v%20!%3D%20%22---%22%5D%0A%20%20%20%20result%20%3D%20tiled_map.render(legend%3DFalse)%0A%20%20%20%20if%20show_map.value%3A%0A%20%20%20%20%20%20%20%20get_gdf().plot(ax%3Dresult.axes%5B0%5D%2C%20fc%3D%22%2300000000%22%2C%20edgecolor%3D%22w%22%2C%20linewidth%3D2.5)%0A%20%20%20%20%20%20%20%20get_gdf().plot(ax%3Dresult.axes%5B0%5D%2C%20fc%3D%22%2300000000%22%2C%20edgecolor%3D%22k%22%2C%20linewidth%3D1.5)%0A%20%20%20%20result%0A%20%20%20%20return%20(result%2C)%0A%0A%0A%40app.cell%0Adef%20set_number_of_variables(mo)%3A%0A%20%20%20%20num_tiles%20%3D%20mo.ui.slider(steps%3D%5Bx%20for%20x%20in%20range(2%2C%2021)%20if%20x%20!%3D%2017%5D%2C%20value%3D4%2C%20debounce%3DTrue%2C%20show_value%3DTrue)%0A%20%20%20%20mo.md(f%22%22%22%0A%20%20%20%20%23%23%23%20General%20settings%0A%20%20%20%20%23%23%23%23%20Set%20number%20of%20tiling%20elements%20%7Btool_tip(num_tiles%2C%20'Choose%20the%20number%20of%20distinct%20tiles%20you%20want%20to%20use%20to%20symbolise%20data.')%7D%0A%20%20%20%20%22%22%22)%0A%20%20%20%20return%20(num_tiles%2C)%0A%0A%0A%40app.cell%0Adef%20variable_palette_map_header(mo)%3A%0A%20%20%20%20mo.md(f%22%22%22%0A%20%20%20%20%23%23%23%20Variables%20%26lrarr%3B%20palettes%0A%20%20%20%20%22%22%22)%0A%20%20%20%20return%0A%0A%0A%40app.cell%0Adef%20status_panel(%0A%20%20%20%20get_gdf%2C%0A%20%20%20%20get_numeric_variables%2C%0A%20%20%20%20get_status_message%2C%0A%20%20%20%20mo%2C%0A%20%20%20%20num_tiles%2C%0A%20%20%20%20set_status_message%2C%0A)%3A%0A%20%20%20%20set_status_message(%22STATUS%20All%20good!%22)%0A%20%20%20%20if%20len(get_numeric_variables(get_gdf()))%20%3C%20num_tiles.value%3A%0A%20%20%20%20%20%20%20%20set_status_message(f%22WARNING!%20More%20tiles%20(%7Bnum_tiles.value%7D)%20than%20variables%20(%7Blen(get_numeric_variables(get_gdf()))%7D)%22)%0A%0A%20%20%20%20if%20%22ERROR%22%20in%20get_status_message()%3A%0A%20%20%20%20%20%20%20%20_bkgd%2C%20_col%20%3D%20%22red%22%2C%20%22white%22%0A%20%20%20%20elif%20%22WARNING%22%20in%20get_status_message()%3A%0A%20%20%20%20%20%20%20%20_bkgd%2C%20_col%20%3D%20%22pink%22%2C%20%22black%22%0A%20%20%20%20else%3A%20%23%20OK%0A%20%20%20%20%20%20%20%20_bkgd%2C%20_col%20%3D%20%22lightgreen%22%2C%20%22black%22%0A%0A%20%20%20%20mo.md(f%22%3Cspan%20style%3D'background-color%3A%7B_bkgd%7D%3Bcolor%3A%7B_col%7D%3Bfont-face%3Asans-serif%3Bpadding%3A2px%3B'%3E%7Bget_status_message()%7D%3C%2Fspan%3E%22).center()%0A%20%20%20%20return%0A%0A%0A%40app.cell%0Adef%20build_variable_and_palette_dropdowns(%0A%20%20%20%20available_palettes%2C%0A%20%20%20%20get_gdf%2C%0A%20%20%20%20get_numeric_variables%2C%0A%20%20%20%20get_palettes%2C%0A%20%20%20%20get_reversed%2C%0A%20%20%20%20get_variables%2C%0A%20%20%20%20mo%2C%0A%20%20%20%20num_tiles%2C%0A%20%20%20%20set_palettes%2C%0A%20%20%20%20set_reversed%2C%0A%20%20%20%20set_variables%2C%0A%20%20%20%20tiling_map%2C%0A)%3A%0A%20%20%20%20mo.stop(tiling_map)%0A%20%20%20%20_n%20%3D%20num_tiles.value%0A%20%20%20%20_vars%20%3D%20get_variables()%0A%20%20%20%20_pals%20%3D%20get_palettes()%0A%20%20%20%20_revs%20%3D%20get_reversed()%0A%20%20%20%20if%20_n%20%3C%20len(_vars)%3A%0A%20%20%20%20%20%20%20%20set_variables(_vars%5B%3A_n%5D)%0A%20%20%20%20%20%20%20%20set_palettes(_pals%5B%3A_n%5D)%0A%20%20%20%20%20%20%20%20set_reversed(_revs%5B%3A_n%5D)%0A%20%20%20%20elif%20_n%20%3E%3D%20len(_vars)%3A%0A%20%20%20%20%20%20%20%20_numeric_vars%20%3D%20get_numeric_variables(get_gdf())%0A%20%20%20%20%20%20%20%20%23%20add%20as%20many%20additional%20variables%20as%20we%20have%20to%20work%20with%0A%20%20%20%20%20%20%20%20_n_to_add%20%3D%20min(_n%2C%20len(_numeric_vars))%20-%20len(_vars)%0A%20%20%20%20%20%20%20%20_to_add%20%3D%20%5Bv%20for%20v%20in%20_numeric_vars%20if%20v%20not%20in%20_vars%5D%5B%3A_n_to_add%5D%0A%20%20%20%20%20%20%20%20set_variables(_vars%20%2B%20_to_add)%0A%20%20%20%20%20%20%20%20set_palettes(_pals%20%2B%20%5Bp%20for%20p%20in%20available_palettes%20if%20not%20p%20in%20_pals%5D%5B%3A_n_to_add%5D)%0A%20%20%20%20%20%20%20%20set_reversed(_revs%20%2B%20%5BFalse%5D%20*%20_n_to_add)%0A%0A%20%20%20%20variables%20%3D%20mo.ui.array(%0A%20%20%20%20%20%20%20%20%5Bmo.ui.dropdown(options%3Dget_numeric_variables(get_gdf())%20%2B%20%5B%22---%22%5D%2C%20value%3Dv)%20%0A%20%20%20%20%20%20%20%20%20for%20v%20in%20get_variables()%5D%2C%20on_change%3Dset_variables)%20%0A%20%20%20%20pals%20%3D%20mo.ui.array(%0A%20%20%20%20%20%20%20%20%5Bmo.ui.dropdown(options%3Davailable_palettes%2C%20value%3Dp)%20%0A%20%20%20%20%20%20%20%20%20for%20p%20in%20get_palettes()%5D%2C%20on_change%3Dset_palettes)%0A%20%20%20%20rev_pals%20%3D%20mo.ui.array(%0A%20%20%20%20%20%20%20%20%5Bmo.ui.switch(r)%0A%20%20%20%20%20%20%20%20%20for%20r%20in%20get_reversed()%5D%2C%20on_change%3Dset_reversed)%0A%20%20%20%20return%20pals%2C%20rev_pals%2C%20variables%0A%0A%0A%40app.cell%0Adef%20build_var_palette_mapping(%0A%20%20%20%20color_ramps%2C%0A%20%20%20%20get_tile_ids%2C%0A%20%20%20%20mo%2C%0A%20%20%20%20pals%2C%0A%20%20%20%20rev_pals%2C%0A%20%20%20%20variables%2C%0A)%3A%0A%20%20%20%20_cols%20%3D%20%5Bpal.value%20%2B%20(%22_r%22%20if%20rev.value%20else%20%22%22)%20for%20pal%2C%20rev%20in%20zip(pals%2C%20rev_pals)%5D%0A%20%20%20%20mo.md(%22%5Cn%22.join(%5B%0A%20%20%20%20%20%20%20%20%22%26nbsp%3B%26nbsp%3B%22.join(%0A%20%20%20%20%20%20%20%20%20%20%20%20%5Bf%22%23%23%23%23%20Tiles%20%60%7Btile_id%7D%60%22%2C%0A%20%20%20%20%20%20%20%20%20%20%20%20%20f%22%7Btool_tip(var%2C%20f%22Variable%20for%20tiles%20with%20id%20%7Btile_id%7D%22)%7D%20%26rarr%3B%22%2C%0A%20%20%20%20%20%20%20%20%20%20%20%20%20f%22%7Btool_tip(pal%2C%20f%22Palette%20for%20variable%20%7Bvar.value%7D%22)%7D%22%2C%0A%20%20%20%20%20%20%20%20%20%20%20%20%20f%22%3Cspan%20style%3D'position%3Arelative%3Btop%3A5px%3B'%3E%7Btool_tip(rev%2C%20'Reverse%20ramp')%7D%3C%2Fspan%3E%22%2C%0A%20%20%20%20%20%20%20%20%20%20%20%20%20f%22%3Cspan%20style%3D'display%3Ainline-block%3Bobject-fit%3Acover%3Bheight%3A24px%3Bposition%3Arelative%3Bbottom%3A22px%3B'%3E%7Bcolor_ramps%5Bcol%5D%7D%3C%2Fspan%3E%22%5D)%20%0A%20%20%20%20%20%20%20%20for%20tile_id%2C%20var%2C%20pal%2C%20rev%2C%20col%20in%20zip(get_tile_ids()%2C%20variables%2C%20pals%2C%20rev_pals%2C%20_cols)%5D))%0A%20%20%20%20return%0A%0A%0A%40app.cell%0Adef%20set_spacing_limits(get_spacings%2C%20mo)%3A%0A%20%20%20%20_spacing_steps%2C%20_spacing_value%20%3D%20get_spacings()%0A%20%20%20%20spacing%20%3D%20mo.ui.slider(steps%3D_spacing_steps%2C%20value%3D_spacing_value%2C%20show_value%3DTrue%2C%20debounce%3DTrue)%0A%20%20%20%20return%20(spacing%2C)%0A%0A%0A%40app.cell%0Adef%20_(mo%2C%20tile_or_weave)%3A%0A%20%20%20%20mo.md(f%22%22%22%0A%20%20%20%20%23%23%23%20%7Btile_or_weave.value.capitalize()%7D%20modifiers%0A%20%20%20%20%22%22%22)%0A%20%20%20%20return%0A%0A%0A%40app.cell%0Adef%20tiling_modifier_ui_elements(mo)%3A%0A%20%20%20%20tile_rotate%20%3D%20mo.ui.slider(steps%3Drange(-90%2C%2091%2C%201)%2C%20value%3D0%2C%20show_value%3DTrue%2C%20debounce%3DTrue)%0A%20%20%20%20tile_scale_x%20%3D%20mo.ui.slider(steps%20%3D%20%5B_%2F50%20for%20_%20in%20range(25%2C%2050)%5D%20%2B%20%5B_%2F10%20for%20_%20in%20range(10%2C%2041)%5D%2C%20value%3D1%2C%20show_value%3DTrue%2C%20debounce%3DTrue)%0A%20%20%20%20tile_scale_y%20%3D%20mo.ui.slider(steps%20%3D%20%5B_%2F50%20for%20_%20in%20range(25%2C%2050)%5D%20%2B%20%5B_%2F10%20for%20_%20in%20range(10%2C%2041)%5D%2C%20value%3D1%2C%20show_value%3DTrue%2C%20debounce%3DTrue)%0A%20%20%20%20tile_skew_x%20%3D%20mo.ui.slider(steps%3Drange(-45%2C%2046%2C%201)%2C%20value%3D0%2C%20show_value%3DTrue%2C%20debounce%3DTrue)%0A%20%20%20%20tile_skew_y%20%3D%20mo.ui.slider(steps%3Drange(-45%2C%2046%2C%201)%2C%20value%3D0%2C%20show_value%3DTrue%2C%20debounce%3DTrue)%0A%20%20%20%20p_inset%20%3D%20mo.ui.slider(start%3D0%2C%20stop%3D10%2C%20step%3D0.1%2C%20value%3D0%2C%20show_value%3DTrue%2C%20debounce%3DTrue)%0A%20%20%20%20t_inset%20%3D%20mo.ui.slider(start%3D0%2C%20stop%3D5%2C%20step%20%3D%200.1%2C%20value%3D0%2C%20show_value%3DTrue%2C%20debounce%3DTrue)%0A%20%20%20%20return%20(%0A%20%20%20%20%20%20%20%20p_inset%2C%0A%20%20%20%20%20%20%20%20t_inset%2C%0A%20%20%20%20%20%20%20%20tile_rotate%2C%0A%20%20%20%20%20%20%20%20tile_scale_x%2C%0A%20%20%20%20%20%20%20%20tile_scale_y%2C%0A%20%20%20%20%20%20%20%20tile_skew_x%2C%0A%20%20%20%20%20%20%20%20tile_skew_y%2C%0A%20%20%20%20)%0A%0A%0A%40app.cell%0Adef%20setup_tiling_modifiers(%0A%20%20%20%20mo%2C%0A%20%20%20%20p_inset%2C%0A%20%20%20%20spacing%2C%0A%20%20%20%20t_inset%2C%0A%20%20%20%20tile_or_weave%2C%0A%20%20%20%20tile_rotate%2C%0A%20%20%20%20tile_scale_x%2C%0A%20%20%20%20tile_scale_y%2C%0A%20%20%20%20tile_skew_x%2C%0A%20%20%20%20tile_skew_y%2C%0A%20%20%20%20tiling_map%2C%0A)%3A%0A%20%20%20%20mo.stop(tiling_map)%0A%20%20%20%20if%20tile_or_weave.value%20%3D%3D%20%22tiling%22%3A%0A%20%20%20%20%20%20%20%20_str%20%3D%20f%22%22%22%0A%20%20%20%20%20%20%20%20%20%20%20%20%23%23%23%23%20Spacing%20%7Btool_tip(spacing%2C%20'In%20units%20of%20the%20map%20CRS%2C%20the%20approximate%20dimension%20of%20the%20repeating%20group.')%7D%0A%20%20%20%20%20%20%20%20%20%20%20%20%23%23%23%23%20Rotate%20by%20%7Btool_tip(tile_rotate%2C%20'Rotate%20tiling%20(degrees).%20The%20tile%20group%20is%20rotated%20before%20any%20scaling%20or%20skew%20transforms%20are%20applied.')%7D%0A%20%20%20%20%20%20%20%20%20%20%20%20%23%23%23%23%20Group%20inset%20%7Btool_tip(p_inset%2C%20'Inset%20the%20tile%20group%20(%25%20spacing).')%7D%0A%20%20%20%20%20%20%20%20%20%20%20%20%23%23%23%23%20Tiles%20inset%20%7Btool_tip(t_inset%2C%20'Inset%20individual%20tiles%20(%25%20spacing).')%7D%0A%20%20%20%20%20%20%20%20%20%20%20%20%23%23%23%23%20Scale%20EW%20%7Btool_tip(tile_scale_x%2C%20'Scale%20in%20the%20x%20direction.')%7D%0A%20%20%20%20%20%20%20%20%20%20%20%20%23%23%23%23%20Scale%20NS%20%7Btool_tip(tile_scale_y%2C%20'Scale%20in%20the%20y%20direction.')%7D%0A%20%20%20%20%20%20%20%20%20%20%20%20%23%23%23%23%20Skew%20EW%20%7Btool_tip(tile_skew_x%2C%20'Skew%20in%20the%20x%20direction%20(degrees).')%7D%0A%20%20%20%20%20%20%20%20%20%20%20%20%23%23%23%23%20Skew%20NS%20%7Btool_tip(tile_skew_y%2C%20'Skew%20in%20the%20y%20direction%20(degrees).')%7D%0A%20%20%20%20%20%20%20%20%20%20%20%20%22%22%22%0A%20%20%20%20else%3A%0A%20%20%20%20%20%20%20%20_str%20%3D%20f%22%22%22%0A%20%20%20%20%20%20%20%20%20%20%20%20%23%23%23%23%20Spacing%20%7Btool_tip(spacing%2C%20'In%20units%20of%20the%20map%20CRS%2C%20the%20distance%20between%20strand%20centre%20lines.')%7D%0A%20%20%20%20%20%20%20%20%20%20%20%20%23%23%23%23%20Rotate%20by%20%7Btool_tip(tile_rotate%2C%20%22'Rotate%20weave%20(degrees).%20The%20weave%20is%20rotated%20before%20any%20scaling%20or%20skew%20transforms%20are%20applied.'%22)%7D%0A%20%20%20%20%20%20%20%20%20%20%20%20%23%23%23%23%20Strands%20inset%20%7Btool_tip(t_inset%2C%20%22'Inset%20strands%20(%25%20width).'%22)%7D%0A%20%20%20%20%20%20%20%20%20%20%20%20%23%23%23%23%20Scale%20EW%20%7Btool_tip(tile_scale_x%2C%20%22'Scale%20in%20the%20x%20direction.'%22)%7D%0A%20%20%20%20%20%20%20%20%20%20%20%20%23%23%23%23%20Scale%20NS%20%7Btool_tip(tile_scale_y%2C%20%22'Scale%20in%20the%20y%20direction.'%22)%7D%0A%20%20%20%20%20%20%20%20%20%20%20%20%23%23%23%23%20Skew%20EW%20%7Btool_tip(tile_skew_x%2C%20%22'Skew%20in%20the%20x%20direction%20(degrees).'%22)%7D%0A%20%20%20%20%20%20%20%20%20%20%20%20%23%23%23%23%20Skew%20NS%20%7Btool_tip(tile_skew_y%2C%20%22'Skew%20in%20the%20y%20direction%20(degrees).'%22)%7D%0A%20%20%20%20%20%20%20%20%20%20%20%20%22%22%22%0A%20%20%20%20mo.md(_str)%0A%20%20%20%20return%0A%0A%0A%40app.cell%0Adef%20_(mo)%3A%0A%20%20%20%20show_map%20%3D%20mo.ui.switch(value%3DFalse)%0A%20%20%20%20join_on_prototile%20%3D%20mo.ui.switch(value%3DFalse)%0A%20%20%20%20keep_tileables%20%3D%20mo.ui.switch(value%3DFalse)%0A%20%20%20%20clip_by_areas%20%3D%20mo.ui.switch(value%3DFalse)%0A%20%20%20%20spacing_mode%20%3D%20mo.ui.switch(value%3DFalse)%0A%20%20%20%20map_as_icons%20%3D%20mo.ui.switch(value%3DFalse)%0A%20%20%20%20return%20(%0A%20%20%20%20%20%20%20%20clip_by_areas%2C%0A%20%20%20%20%20%20%20%20join_on_prototile%2C%0A%20%20%20%20%20%20%20%20keep_tileables%2C%0A%20%20%20%20%20%20%20%20map_as_icons%2C%0A%20%20%20%20%20%20%20%20show_map%2C%0A%20%20%20%20%20%20%20%20spacing_mode%2C%0A%20%20%20%20)%0A%0A%0A%40app.cell%0Adef%20_(%0A%20%20%20%20clip_by_areas%2C%0A%20%20%20%20join_on_prototile%2C%0A%20%20%20%20keep_tileables%2C%0A%20%20%20%20map_as_icons%2C%0A%20%20%20%20mo%2C%0A%20%20%20%20show_map%2C%0A%20%20%20%20spacing_mode%2C%0A)%3A%0A%20%20%20%20mo.md(f%22%22%22%0A%20%20%20%20%23%23%23%23%20%7Btool_tip(show_map%2C%20%22Show%20map%20units%20as%20a%20transparent%20overlay.%22)%7D%20Show%20map%20units%0A%20%20%20%20%23%23%23%23%20%7Btool_tip(join_on_prototile%2C%20%22Base%20joining%20data%20on%20the%20tileable%20unit%2C%20not%20the%20tiles.%22)%7D%20Join%20using%20tileable%0A%20%20%20%20%23%23%23%23%20%7Btool_tip(keep_tileables%2C%20%22Retain%20the%20tileable%20units%20even%20where%20a%20tile%20element%20does%20not%20intersect%20a%20map%20area.%20Only%20makes%20sense%20if%20'Join%20using%20tileable'%20is%20set%20on.%22)%7D%20Retain%20tileables%0A%20%20%20%20%23%23%23%23%20%7Btool_tip(clip_by_areas%2C%20%22Show%20tiles%20at%20map%20edges%2C%20not%20map%20areas.%22)%7D%20Clip%20by%20map%20units%0A%20%20%20%20%23%23%23%23%20%7Btool_tip(spacing_mode%2C%20'Apply%20spacing%20of%20repeat%20pattern%20regardless%20of%20any%20scaling.')%7D%20Scale%20as%20glyph%0A%20%20%20%20%23%23%23%23%20%7Btool_tip(map_as_icons%2C%20'Place%20one%20tile%20glyph%20per%20map%20area.')%7D%20Use%20tile%20unit%20as%20icon%0A%20%20%20%20%22%22%22)%0A%20%20%20%20return%0A%0A%0A%40app.cell%0Adef%20tiling_or_weave_chooser(mo%2C%20num_tiles%2C%20tilings_by_n)%3A%0A%20%20%20%20_options%20%3D%20list(set(%5Bv%5B%22type%22%5D%20for%20v%20in%20tilings_by_n%5Bnum_tiles.value%5D.values()%5D))%0A%20%20%20%20tile_or_weave%20%3D%20mo.ui.dropdown(options%3D_options%2C%20value%3D%22tiling%22)%0A%20%20%20%20mo.md(f%22%23%23%23%23%20Pick%20tiling%20or%20weave%20%7Btool_tip(tile_or_weave%2C%20'Choose%20tiling%20or%20a%20weave%20tiling')%7D%22)%0A%20%20%20%20return%20(tile_or_weave%2C)%0A%0A%0A%40app.cell%0Adef%20tiling_type_chooser(mo%2C%20num_tiles%2C%20tile_or_weave%2C%20tilings_by_n)%3A%0A%20%20%20%20_options%20%3D%20%5Bk%20for%20k%2C%20v%20in%20tilings_by_n%5Bnum_tiles.value%5D.items()%20if%20v%5B%22type%22%5D%20%3D%3D%20tile_or_weave.value%5D%0A%20%20%20%20family%20%3D%20mo.ui.dropdown(options%3D_options%2C%20value%3D_options%5B0%5D)%0A%20%20%20%20mo.md(f%22%23%23%23%23%20%7Btile_or_weave.value.capitalize()%7D%20type%20%7Btool_tip(family%2C%20%22Choose%20tiling%20family%22)%7D%22)%0A%20%20%20%20return%20(family%2C)%0A%0A%0A%40app.cell%0Adef%20setup_chosen_tiling_options(%0A%20%20%20%20family%2C%0A%20%20%20%20mo%2C%0A%20%20%20%20num_tiles%2C%0A%20%20%20%20tile_or_weave%2C%0A%20%20%20%20tilings_by_n%2C%0A)%3A%0A%20%20%20%20if%20%22slice%22%20in%20family.value%3A%0A%20%20%20%20%20%20%20%20_offset%20%3D%20mo.ui.slider(steps%3D%5Bx%20%2F%20100%20for%20x%20in%20range(-100%2C%20101)%5D%2C%20value%3D0%2C%20label%3D%22%23%23%23%23%20Offset%22%2C%20show_value%3DTrue%2C%20debounce%3DTrue)%20%0A%20%20%20%20elif%20%22dissect%22%20in%20family.value%3A%0A%20%20%20%20%20%20%20%20_offset%20%3D%20mo.ui.number(start%3D0%2C%20stop%3D1%2C%20value%3D0%2C%20label%3D%22%23%23%23%23%20Offset%22%2C%20debounce%3DTrue)%0A%20%20%20%20%20%20%20%20if%20%22hex%22%20in%20family.value%3A%0A%20%20%20%20%20%20%20%20%20%20%20%20_offset_angle%20%3D%20mo.ui.slider(steps%3D%5Bx%20for%20x%20in%20range(-50%2C%2086)%5D%2C%20value%3D0%2C%20label%3D%22%23%23%23%23%20Inner%20angle%22%2C%20show_value%3DTrue%2C%20debounce%3DTrue)%0A%20%20%20%20%20%20%20%20else%3A%0A%20%20%20%20%20%20%20%20%20%20%20%20_offset_angle%20%3D%20mo.ui.slider(steps%3D%5Bx%20for%20x%20in%20range(-30%2C%2071)%5D%2C%20value%3D0%2C%20label%3D%22%23%23%23%23%20Inner%20angle%22%2C%20show_value%3DTrue%2C%20debounce%3DTrue)%0A%20%20%20%20elif%20%22star1%22%20in%20family.value%3A%0A%20%20%20%20%20%20%20%20_point_angle%20%3D%20mo.ui.slider(steps%3D%5Bx%20for%20x%20in%20range(10%2C%20121)%5D%2C%20value%3D30%2C%20label%3D%22%23%23%23%23%20Point%20angle%22%2C%20show_value%3DTrue%2C%20debounce%3DTrue)%0A%20%20%20%20elif%20%22weave%22%20in%20family.value%3A%0A%20%20%20%20%20%20%20%20_aspect%20%3D%20mo.ui.slider(steps%3D%5Bround(_%2F12%2C%203)%20for%20_%20in%20range(1%2C%2013)%5D%2C%20value%3D0.75%2C%20label%3D%22%23%23%23%23%20Strand%20width%22%2C%20show_value%3DTrue%2C%20debounce%3DTrue)%0A%20%20%20%20%20%20%20%20if%20not%20%22cube%22%20in%20family.value%3A%0A%20%20%20%20%20%20%20%20%20%20%20%20_over_under%20%3D%20mo.ui.text(value%3Dtilings_by_n%5Bnum_tiles.value%5D%5Bfamily.value%5D%5B%22n%22%5D%2C%20label%3D%22%23%23%23%23%20Over-under%22)%0A%0A%20%20%20%20if%20tile_or_weave.value%20%3D%3D%20%22tiling%22%3A%0A%20%20%20%20%20%20%20%20if%20%22slice%22%20in%20family.value%3A%0A%20%20%20%20%20%20%20%20%20%20%20%20tile_spec%20%3D%20mo.ui.dictionary(%7B%22offset%22%3A%20_offset%2C%7D)%0A%20%20%20%20%20%20%20%20%20%20%20%20tooltips%20%3D%20%5B%220%20starts%20at%20the%20base%20tile%20corners%2C%201%20at%20the%20mid-point%20along%20segments%20equally%20dividing%20the%20base%20tile%20perimeter%20into%20the%20requested%20number%20of%20tiles.%22%5D%0A%20%20%20%20%20%20%20%20elif%20%22dissect%22%20in%20family.value%3A%0A%20%20%20%20%20%20%20%20%20%20%20%20tile_spec%20%3D%20mo.ui.dictionary(%7B%22offset%22%3A%20_offset%2C%20%22offset_angle%22%3A%20_offset_angle%2C%7D)%0A%20%20%20%20%20%20%20%20%20%20%20%20tooltips%20%3D%20%5B%220%20starts%20at%20the%20base%20tile%20corners%2C%201%20at%20the%20mid-point%20along%20segments%20equally%20dividing%20the%20base%20tile%20perimeter%20into%20the%20requested%20number%20of%20tiles.%22%2C%20%22Angle%20by%20which%20inner%20polygon%20is%20rotated%20relative%20to%20the%20outer.%20Reverse%20the%20angle%20for%20a%20different%20look.%22%5D%0A%20%20%20%20%20%20%20%20elif%20%22star1%22%20in%20family.value%3A%0A%20%20%20%20%20%20%20%20%20%20%20%20tile_spec%20%3D%20mo.ui.dictionary(%7B%22point_angle%22%3A%20_point_angle%7D)%0A%20%20%20%20%20%20%20%20%20%20%20%20tooltips%20%3D%20%5B%22Set%20the%20interior%20angle%20of%20the%20star%20points.%22%5D%0A%20%20%20%20%20%20%20%20else%3A%0A%20%20%20%20%20%20%20%20%20%20%20%20tile_spec%20%3D%20None%0A%20%20%20%20else%3A%0A%20%20%20%20%20%20%20%20if%20%22plain%22%20in%20family.value%20or%20%22cube%22%20in%20family.value%3A%0A%20%20%20%20%20%20%20%20%20%20%20%20tile_spec%20%3D%20mo.ui.dictionary(%7B%22aspect%22%3A%20_aspect%7D)%0A%20%20%20%20%20%20%20%20%20%20%20%20tooltips%20%3D%20%5B%22The%20width%20of%20the%20weave%20strands%20relative%20to%20strand%20spacing.%20A%20value%20of%201%20will%20fill%20the%20map%20with%20no%20gaps.%20Progressively%20smaller%20values%20will%20leave%20'holes'%20in%20the%20woven%20pattern%20and%20will%20eventually%20give%20the%20appearance%20of%20a%20cross%20hatch.%22%5D%0A%20%20%20%20%20%20%20%20else%3A%0A%20%20%20%20%20%20%20%20%20%20%20%20tile_spec%20%3D%20mo.ui.dictionary(%7B%22aspect%22%3A%20_aspect%2C%20%22over_under%22%3A%20_over_under%2C%7D)%0A%20%20%20%20%20%20%20%20%20%20%20%20tooltips%20%3D%20%5B%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%22The%20width%20of%20the%20weave%20strands%20relative%20to%20strand%20spacing.%22%2C%20%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%22Comma-separated%20sequence%20of%20how%20many%20strands%20in%20the%20other%20direction%20each%20ribbon%20should%20go%20over%2C%20then%20under.%20Use%20values%20that%20are%20factors%20of%20the%20numbers%20of%20strands%20in%20each%20direction%20to%20avoid%20very%20large%20and%20complex%20repeating%20units.%22%5D%0A%20%20%20%20return%20tile_spec%2C%20tooltips%0A%0A%0A%40app.cell%0Adef%20additional_tiling_options(mo%2C%20tile_or_weave%2C%20tile_spec%2C%20tooltips)%3A%0A%20%20%20%20%23%20mo.stop(tiling_map)%0A%20%20%20%20if%20tile_spec%20is%20None%3A%0A%20%20%20%20%20%20%20%20_show_options%20%3D%20mo.md(f%22%23%23%23%23%20No%20%7Btile_or_weave.value%7D%20options%20to%20set%22)%0A%20%20%20%20else%3A%0A%20%20%20%20%20%20%20%20_show_options%20%3D%20mo.md(%22%5Cn%22.join(%0A%20%20%20%20%20%20%20%20%20%20%20%20%5Bf%22%23%23%23%20Set%20%7Btile_or_weave.value%7D%20options%22%5D%20%2B%20%0A%20%20%20%20%20%20%20%20%20%20%20%20%5Bf%22%23%23%23%23%20%7Btool_tip(v%2C%20tt)%7D%22%20for%20(k%2C%20v)%2C%20tt%20in%20zip(tile_spec.items()%2C%20tooltips)%5D%0A%20%20%20%20%20%20%20%20))%0A%20%20%20%20_show_options%0A%20%20%20%20return%0A%0A%0A%40app.cell%0Adef%20tiling_design_plot(get_modded_tile_unit%2C%20plot_tiles)%3A%0A%20%20%20%20plot_tiles(get_modded_tile_unit())%0A%20%20%20%20return%0A%0A%0A%40app.cell%0Adef%20design_view_settings(mo)%3A%0A%20%20%20%20_radius%20%20%20%20%20%20%20%20%20%20%20%20%20%3D%20mo.ui.slider(steps%3Drange(5)%2C%20value%3D0%2C%20show_value%3DTrue)%0A%20%20%20%20_show_prototile%20%20%20%20%20%3D%20mo.ui.switch(value%3DFalse)%0A%20%20%20%20_show_reg_prototile%20%3D%20mo.ui.switch(value%3DFalse)%0A%20%20%20%20_show_vectors%20%20%20%20%20%20%20%3D%20mo.ui.switch(value%3DFalse)%0A%20%20%20%20_show_ids%20%20%20%20%20%20%20%20%20%20%20%3D%20mo.ui.switch(value%3DTrue)%0A%20%20%20%20_show_scale%20%20%20%20%20%20%20%20%20%3D%20mo.ui.switch(value%3DFalse)%0A%0A%20%20%20%20view_settings%20%3D%20mo.ui.dictionary(%7B%0A%20%20%20%20%20%20%20%20%22radius%22%3A%20_radius%2C%0A%20%20%20%20%20%20%20%20%22show_ids%22%3A%20_show_ids%2C%0A%20%20%20%20%20%20%20%20%22show_prototile%22%3A%20_show_prototile%2C%0A%20%20%20%20%20%20%20%20%22show_reg_prototile%22%3A%20_show_reg_prototile%2C%0A%20%20%20%20%20%20%20%20%22show_vectors%22%3A%20_show_vectors%2C%0A%20%20%20%20%20%20%20%20%22show_scale%22%3A%20_show_scale%2C%0A%20%20%20%20%7D)%0A%20%20%20%20return%20(view_settings%2C)%0A%0A%0A%40app.cell%0Adef%20design_view_ui_elements(mo%2C%20view_settings)%3A%0A%20%20%20%20mo.md(f%22%22%22%0A%20%20%20%20%23%23%23%20Design%20view%20options%0A%20%20%20%20%23%23%23%23%20%7Btool_tip(view_settings%5B'show_ids'%5D%2C%20'Show%20the%20tiling%20element%20labels%20used%20to%20match%20tiles%20to%20variables%20in%20the%20map%20data.')%7D%20Show%20tile%20IDs%0A%20%20%20%20%23%23%23%23%20%7Btool_tip(view_settings%5B'show_prototile'%5D%2C%20'Show%20in%20fine%20black%20outline%20the%20simple%20tile%20(usually%20a%20square%20or%20hexagon)%20which%20forms%20the%20basis%20of%20the%20pattern.')%7D%20Show%20base%20tile%0A%20%20%20%20%23%23%23%23%20%7Btool_tip(view_settings%5B'show_vectors'%5D%2C%20'Show%20the%20translations%20that%20map%20repeating%20tiles%20in%20the%20pattern%20onto%20one%20another.')%7D%20Show%20vectors%0A%20%20%20%20%23%23%23%23%20%7Btool_tip(view_settings%5B'show_reg_prototile'%5D%2C%20'Show%20in%20a%20red%20outline%20the%20repeating%20set%20tile%20group%20that%20pieces%20together%20jigsaw-like%20to%20form%20the%20pattern.')%7D%20Show%20%26lsquo%3Bjigsaw%20piece%26rsquo%3B%0A%20%20%20%20%23%23%23%23%20%7Btool_tip(view_settings%5B'show_scale'%5D%2C%20'Give%20an%20indication%20of%20scale%20in%20map%20units.')%7D%20Show%20scale%0A%20%20%20%20%23%23%23%23%20Tile%20unit%20'shells'%20to%20show%20%7Btool_tip(view_settings%5B'radius'%5D%2C%20'The%20number%20of%20%26lsquo%3Bshells%26rsquo%3B%20of%20the%20tiling%20to%20show%20around%20the%20base%20tile%20group.')%7D%0A%20%20%20%20%22%22%22)%0A%20%20%20%20return%0A%0A%0A%40app.cell%0Adef%20_(%0A%20%20%20%20family%2C%0A%20%20%20%20get_crs%2C%0A%20%20%20%20num_tiles%2C%0A%20%20%20%20spacing%2C%0A%20%20%20%20tile_or_weave%2C%0A%20%20%20%20tile_spec%2C%0A%20%20%20%20tilings_by_n%2C%0A%20%20%20%20wsp%2C%0A)%3A%0A%20%20%20%20def%20get_base_tile_unit()%20-%3E%20wsp.Tileable%3A%0A%20%20%20%20%20%20%20%20%22%22%22%0A%20%20%20%20%20%20%20%20Returns%20a%20Tileable%20object%20based%20on%20the%20current%20configuration%20of%20the%20app%20UI%0A%20%20%20%20%20%20%20%20%22%22%22%0A%20%20%20%20%20%20%20%20%23%20call%20TileUnit%20or%20WeaveUnit%20with%20appropriate%20settings%0A%20%20%20%20%20%20%20%20spec%20%3D%20tilings_by_n%5Bnum_tiles.value%5D%5Bfamily.value%5D%0A%20%20%20%20%20%20%20%20if%20tile_or_weave.value%20%3D%3D%20%22tiling%22%3A%0A%20%20%20%20%20%20%20%20%20%20%20%20result%20%3D%20wsp.TileUnit(%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20tiling_type%3Dspec%5B%22tiling_type%22%5D%2C%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20spacing%3Dspacing.value%2C%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20n%3Dspec%5B%22n%22%5D%20if%20%22n%22%20in%20spec%20else%20None%2C%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20code%3Dspec%5B%22code%22%5D%20if%20%22code%22%20in%20spec%20else%20None%2C%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20offset%3Dtile_spec%5B%22offset%22%5D.value%20if%20%22offset%22%20in%20spec%20else%20None%2C%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20offset_angle%3Dtile_spec%5B%22offset_angle%22%5D.value%20if%20%22offset_angle%22%20in%20spec%20else%20None%2C%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20point_angle%3Dtile_spec%5B%22point_angle%22%5D.value%20if%20%22point_angle%22%20in%20spec%20else%20None%2C%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20crs%3Dget_crs())%0A%20%20%20%20%20%20%20%20else%3A%0A%20%20%20%20%20%20%20%20%20%20%20%20result%20%3D%20wsp.WeaveUnit(%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20weave_type%3Dspec%5B%22weave_type%22%5D%2C%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20spacing%3Dspacing.value%2C%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20strands%3Dspec%5B%22strands%22%5D%2C%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20n%3Dget_over_under(tile_spec%5B%22over_under%22%5D.value)%20%5C%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20if%20spec%5B%22weave_type%22%5D%20in%20%5B%22twill%22%2C%20%22basket%22%5D%20else%201%2C%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20aspect%3Dtile_spec%5B%22aspect%22%5D.value%2C%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20crs%3Dget_crs())%0A%20%20%20%20%20%20%20%20return%20result%0A%20%20%20%20return%20(get_base_tile_unit%2C)%0A%0A%0A%40app.cell%0Adef%20_(%0A%20%20%20%20get_base_tile_unit%2C%0A%20%20%20%20p_inset%2C%0A%20%20%20%20spacing%2C%0A%20%20%20%20spacing_mode%2C%0A%20%20%20%20t_inset%2C%0A%20%20%20%20tile_or_weave%2C%0A%20%20%20%20tile_rotate%2C%0A%20%20%20%20tile_scale_x%2C%0A%20%20%20%20tile_scale_y%2C%0A%20%20%20%20tile_skew_x%2C%0A%20%20%20%20tile_skew_y%2C%0A%20%20%20%20tile_spec%2C%0A)%3A%0A%20%20%20%20def%20get_modded_tile_unit()%3A%0A%20%20%20%20%20%20%20%20%22%22%22%0A%20%20%20%20%20%20%20%20Returns%20a%20Tileable%20object%20based%20on%20the%20current%20configuration%20of%20the%20app%20UI%0A%20%20%20%20%20%20%20%20including%20any%20modifications%20(rotations%2C%20skews%2C%20scaling%20etc.)%0A%20%20%20%20%20%20%20%20%22%22%22%0A%20%20%20%20%20%20%20%20%23%20make%20any%20requested%20modifications%20to%20the%20tile%20or%20weave%20unit%0A%20%20%20%20%20%20%20%20if%20tile_or_weave.value%20%3D%3D%20%22tiling%22%3A%0A%20%20%20%20%20%20%20%20%20%20%20%20return%20get_base_tile_unit()%20%5C%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20.transform_rotate(tile_rotate.value)%20%5C%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20.transform_scale(tile_scale_x.value%2C%20tile_scale_y.value%2C%20spacing_mode.value)%20%5C%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20.transform_skew(tile_skew_x.value%2C%20tile_skew_y.value)%20%5C%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20.inset_tiles(t_inset.value%20*%20spacing.value%20%2F%20100)%20%5C%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20.inset_prototile(p_inset.value%20*%20spacing.value%20%2F%20100)%0A%20%20%20%20%20%20%20%20else%3A%0A%20%20%20%20%20%20%20%20%20%20%20%20return%20get_base_tile_unit()%20%5C%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20.transform_rotate(tile_rotate.value)%20%5C%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20.transform_scale(tile_scale_x.value%2C%20tile_scale_y.value%2C%20spacing_mode.value)%20%5C%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20.transform_skew(tile_skew_x.value%2C%20tile_skew_y.value)%20%5C%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20.inset_tiles(t_inset.value%20*%20tile_spec%5B%22aspect%22%5D.value%20*%20spacing.value%20%2F%20100)%0A%20%20%20%20return%20(get_modded_tile_unit%2C)%0A%0A%0A%40app.function%0Adef%20get_over_under(pattern%3Astr)%20-%3E%20int%7Ctuple%5Bint%5D%3A%0A%20%20%20%20%22%22%22%0A%20%20%20%20Returns%20either%20an%20integer%20or%20tuple%20of%20integers%20of%20even%20length%20%0A%20%20%20%20based%20on%20the%20supplied%20comma-separated%20string%20of%20integer%20values%0A%20%20%20%20%22%22%22%0A%20%20%20%20%23%20convert%20string%20over%20under%20pattern%20to%20tuple%5Bint%5D%0A%20%20%20%20%23%20if%20any%20invalid%20characters%20in%20string%20return%20a%20useful%20default%0A%20%20%20%20if%20any(%5Bnot%20c%20in%20%220123456789%2C%22%20for%20c%20in%20pattern%5D)%3A%20return%20(2%2C%202)%0A%20%20%20%20numbers%20%3D%20%5Bint(s)%20for%20s%20in%20pattern.split(%22%2C%22)%5D%0A%20%20%20%20%23%20has%20to%20be%20an%20even%20number%20of%20elements%20so%20trim%20if%20needed%0A%20%20%20%20length%20%3D%202%20*%20len(numbers)%20%2F%2F%202%0A%20%20%20%20if%20length%20%3D%3D%200%3A%0A%20%20%20%20%20%20%20%20return%20(2%2C%202)%0A%20%20%20%20else%3A%0A%20%20%20%20%20%20%20%20return%20tuple(numbers%5B%3Alength%5D)%0A%0A%0A%40app.cell%0Adef%20_(get_selected_colour_palettes%2C%20mpl%2C%20num_tiles%2C%20view_settings%2C%20wsp)%3A%0A%20%20%20%20def%20plot_tiles(tiles%3Awsp.Tileable)%20-%3E%20mpl.axis%3A%0A%20%20%20%20%20%20%20%20%22%22%22%0A%20%20%20%20%20%20%20%20Returns%20a%20matplotlib%20axis%20with%20the%20Tileable%20supplied%20plotted%20on%20it%0A%20%20%20%20%20%20%20%20%22%22%22%0A%20%20%20%20%20%20%20%20fig%2C%20ax%20%3D%20mpl.pyplot.subplots(1%2C%201%2C%20figsize%3D(4.5%2C%204))%0A%20%20%20%20%20%20%20%20cols%20%3D%20%5Bmpl.colormaps.get(p)(2%2F3)%20for%20p%20in%20get_selected_colour_palettes()%5D%0A%20%20%20%20%20%20%20%20blanks%20%3D%20%5B%5D%0A%20%20%20%20%20%20%20%20while%20len(cols)%20%3C%20num_tiles.value%3A%0A%20%20%20%20%20%20%20%20%20%20%20%20cols%20%3D%20cols%20%2B%20%5B%22%23ffffff00%22%5D%0A%20%20%20%20%20%20%20%20%20%20%20%20blanks.append(%22abcdefghijklmnopqrstuvwxyz%22%5Blen(cols)%20-%201%5D)%0A%20%20%20%20%20%20%20%20cm%20%3D%20mpl.colors.ListedColormap(cols)%0A%20%20%20%20%20%20%20%20tiles.plot(ax%20%3D%20ax%2C%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20r%3Dview_settings%5B%22radius%22%5D.value%2C%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20show_vectors%3Dview_settings%5B%22show_vectors%22%5D.value%2C%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20show_prototile%3Dview_settings%5B%22show_prototile%22%5D.value%2C%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20show_reg_prototile%3Dview_settings%5B%22show_reg_prototile%22%5D.value%2C%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20show_ids%3Dview_settings%5B%22show_ids%22%5D.value%2C%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20cmap%3Dcm%2C%20%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20r_alpha%3D0.5)%0A%20%20%20%20%20%20%20%20if%20view_settings%5B%22show_scale%22%5D.value%3A%0A%20%20%20%20%20%20%20%20%20%20%20%20ax.xaxis.set_visible(True)%0A%20%20%20%20%20%20%20%20%20%20%20%20ax.yaxis.set_visible(False)%0A%20%20%20%20%20%20%20%20%20%20%20%20ax.set_frame_on(False)%0A%20%20%20%20%20%20%20%20else%3A%0A%20%20%20%20%20%20%20%20%20%20%20%20ax.set_axis_off()%0A%20%20%20%20%20%20%20%20if%20len(blanks)%20%3E%200%3A%0A%20%20%20%20%20%20%20%20%20%20%20%20tiles.tiles.loc%5Btiles.tiles%5B%22tile_id%22%5D.isin(blanks)%5D.plot(ax%20%3D%20ax%2C%20fc%3D%22%2300000000%22%2C%20hatch%3D%22%2F%2F%2F%2F%22%2C%20ec%3D%22lightgrey%22)%0A%20%20%20%20%20%20%20%20return%20ax%0A%20%20%20%20return%20(plot_tiles%2C)%0A%0A%0A%40app.cell%0Adef%20_(get_gdf%2C%20get_numeric_variables)%3A%0A%20%20%20%20def%20get_tile_ids()%20-%3E%20list%5Bstr%5D%3A%0A%20%20%20%20%20%20%20%20%22%22%22%0A%20%20%20%20%20%20%20%20Returns%20a%20list%20of%20lower%20case%20letters%20starting%20%5B'a'%2C%20'b'%2C%20...%5D%20length%20limited%0A%20%20%20%20%20%20%20%20by%20the%20number%20of%20available%20numeric%20variables%20in%20the%20data%0A%20%20%20%20%20%20%20%20%22%22%22%0A%20%20%20%20%20%20%20%20return%20list(%22abcdefghijklmnopqrstuvwxyz%22)%5B%3Alen(get_numeric_variables(get_gdf()))%5D%0A%20%20%20%20return%20(get_tile_ids%2C)%0A%0A%0A%40app.cell%0Adef%20_(num_tiles%2C%20pals%2C%20rev_pals)%3A%0A%20%20%20%20def%20get_selected_colour_palettes()%20-%3E%20list%5Bstr%5D%3A%0A%20%20%20%20%20%20%20%20%22%22%22%0A%20%20%20%20%20%20%20%20Returns%20a%20list%20of%20the%20currently%20selected%20colourmap%20names%2C%20including%0A%20%20%20%20%20%20%20%20_r%20suffix%20where%20the%20reverse%20switch%20has%20been%20set%0A%20%20%20%20%20%20%20%20%22%22%22%0A%20%20%20%20%20%20%20%20return%20%5B(p%20if%20not%20r%20else%20p%20%2B%20%22_r%22)%20%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20for%20p%2C%20r%20in%20zip(pals.value%5B%3Anum_tiles.value%5D%2C%20rev_pals.value%5B%3Anum_tiles.value%5D)%5D%0A%20%20%20%20return%20(get_selected_colour_palettes%2C)%0A%0A%0A%40app.cell%0Adef%20_(io%2C%20mo%2C%20mpl)%3A%0A%20%20%20%20def%20get_colour_ramp(pal_name%3Astr%3D%22Reds%22%2C%20rev%3Abool%3DFalse)%20-%3E%20mo.image%3A%0A%20%20%20%20%20%20%20%20%22%22%22%0A%20%20%20%20%20%20%20%20Returns%20a%20marimo%20image%20to%20represent%20the%20colour%20ramp%20specified%20by%20the%20supplied%0A%20%20%20%20%20%20%20%20base%20name%20(%60pal%60)%20and%20whether%20or%20not%20it%20is%20reversed%20(the%20%60rev%60)%20setting%20when%0A%20%20%20%20%20%20%20%20_r%20will%20be%20appended%20to%20the%20base%20name%0A%20%20%20%20%20%20%20%20%22%22%22%0A%20%20%20%20%20%20%20%20%23%20returns%20an%20image%20representing%20the%20colour%20ramp%20for%20the%20supplied%20palette%20name%0A%20%20%20%20%20%20%20%20fig%2C%20ax%20%3D%20mpl.pyplot.subplots()%0A%20%20%20%20%20%20%20%20%23%20this%20code%20based%20on%20code%20in%20matplotlib%20docs%20at%0A%20%20%20%20%20%20%20%20%23%20https%3A%2F%2Fmatplotlib.org%2Fstable%2Fusers%2Fexplain%2Fcolors%2Fcolormaps.html%0A%20%20%20%20%20%20%20%20xy%20%3D%20%5B%5Bx%20%2F%20256%20for%20x%20in%20range(257)%5D%20for%20i%20in%20range(2)%5D%0A%20%20%20%20%20%20%20%20ax.imshow(xy%2C%20aspect%3D30%2C%20cmap%3Dmpl.colormaps.get(pal_name%20%2B%20(%22_r%22%20if%20rev%20else%20%22%22)))%0A%20%20%20%20%20%20%20%20ax.set_axis_off()%0A%20%20%20%20%20%20%20%20%23%20write%20to%20memory%20and%20embed%20in%20a%20marimo%20image%20object%0A%20%20%20%20%20%20%20%20with%20io.BytesIO()%20as%20buf%3A%0A%20%20%20%20%20%20%20%20%20%20%20%20mpl.pyplot.savefig(buf%2C%20dpi%3D24%2C%20pad_inches%3D0%2C%20bbox_inches%3D%22tight%22)%0A%20%20%20%20%20%20%20%20%20%20%20%20mpl.pyplot.close(fig)%0A%20%20%20%20%20%20%20%20%20%20%20%20img%20%3D%20mo.image(buf)%0A%20%20%20%20%20%20%20%20return%20img%0A%20%20%20%20return%20(get_colour_ramp%2C)%0A%0A%0A%40app.cell%0Adef%20_(gpd%2C%20pd)%3A%0A%20%20%20%20def%20get_numeric_variables(_gdf%3Agpd.GeoDataFrame)%20-%3E%20list%5Bstr%5D%3A%0A%20%20%20%20%20%20%20%20%22%22%22%0A%20%20%20%20%20%20%20%20Returns%20a%20list%20of%20the%20column%20names%20in%20the%20supplied%20GeoDataFrame%20which%0A%20%20%20%20%20%20%20%20are%20numeric%0A%20%20%20%20%20%20%20%20%22%22%22%0A%20%20%20%20%20%20%20%20return%20%5Bcol%20for%20col%20in%20_gdf.columns%20if%20not%20%22geom%22%20in%20col%20%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20and%20pd.api.types.is_numeric_dtype(_gdf%5Bcol%5D.dtype)%5D%0A%20%20%20%20return%20(get_numeric_variables%2C)%0A%0A%0A%40app.cell%0Adef%20_(get_gdf%2C%20math)%3A%0A%20%20%20%20def%20get_spacings()%20-%3E%20tuple%5Blist%5Bint%5D%2Cint%5D%3A%0A%20%20%20%20%20%20%20%20%22%22%22%0A%20%20%20%20%20%20%20%20Returns%20a%20list%20of%20int%20values%20and%20a%20midpoint%20as%20settings%20for%20the%20spacing%20UI%20element%0A%20%20%20%20%20%20%20%20%22%22%22%0A%20%20%20%20%20%20%20%20%23%20returns%20reasonable%20rounded%20set%20of%20spacing%20options%20given%20the%20bounds%20of%20the%20data%0A%20%20%20%20%20%20%20%20bb%20%3D%20get_gdf().total_bounds%0A%20%20%20%20%20%20%20%20width%2C%20height%20%3D%20bb%5B2%5D%20-%20bb%5B0%5D%2C%20bb%5B3%5D%20-%20bb%5B1%5D%0A%20%20%20%20%20%20%20%20max_s%20%3D%2010%20**%20math.floor(math.log10(max(width%2C%20height)))%20%2F%2F%205%0A%20%20%20%20%20%20%20%20mid_s%20%3D%20max_s%20%2F%2F%202%0A%20%20%20%20%20%20%20%20min_s%20%3D%20max_s%20%2F%2F%2020%0A%20%20%20%20%20%20%20%20stepsize1%20%3D%20min_s%20%2F%2F%2010%0A%20%20%20%20%20%20%20%20stepsize2%20%3D%20min_s%20%2F%2F%202%0A%20%20%20%20%20%20%20%20steps%20%3D%20%5Bx%20for%20x%20in%20range(min_s%2C%20mid_s%2C%20stepsize1)%5D%20%2B%20%5C%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%5Bx%20for%20x%20in%20range(mid_s%2C%20max_s%20%2B%201%2C%20stepsize2)%5D%0A%20%20%20%20%20%20%20%20return%20steps%2C%203%20*%20mid_s%20%2F%2F%204%0A%20%20%20%20return%20(get_spacings%2C)%0A%0A%0A%40app.function%0Adef%20tool_tip(ele%3Astr%2C%20tip%3Astr)%20-%3E%20str%3A%0A%20%20%20%20%22%22%22%0A%20%20%20%20Returns%20a%20HTML%20%3Cspan%3E%20string%20putting%20a%20tooltip%20around%20the%20supplied%20element%20%0A%20%20%20%20%22%22%22%0A%20%20%20%20%23%20convenience%20function%20to%20add%20a%20tooltip%20to%20supplied%20string%0A%20%20%20%20return%20f'%3Cspan%20title%3D%22%7Btip%7D%22%3E%7Bele%7D%3C%2Fspan%3E'%0A%0A%0A%40app.cell%0Adef%20constants(CMAPS_DIVERGING%2C%20CMAPS_SEQUENTIAL%2C%20get_colour_ramp%2C%20gpd)%3A%0A%20%20%20%20ok_message%20%3D%20%22STATUS%20All%20good!%22%0A%20%20%20%20dummy_data_file%20%3D%20%22https%3A%2F%2Fraw.githubusercontent.com%2FDOSull%2Fweaving-space%2Frefs%2Fheads%2Fmain%2Fexamples%2Fdata%2Fdummy-data-2.json%22%0A%20%20%20%20builtin_gdf%20%3D%20gpd.read_file(dummy_data_file%2C%20engine%3D%22fiona%22)%0A%20%20%20%20available_palettes%20%3D%20%5Bpal%20for%20pal%20in%20CMAPS_SEQUENTIAL%20%2B%20CMAPS_DIVERGING%20if%20pal%5B-2%3A%5D%20!%3D%20%22_r%22%20and%20%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20pal%20not%20in%20%5B%22berlin%22%2C%20%22managua%22%2C%20%22vanimo%22%5D%5D%20%23%20these%20don't%20seem%20to%20be%20in%20MPL3.8.4%0A%20%20%20%20%23%20make%20a%20bunch%20of%20colour%20ramps%20and%20save%20them%20in%20a%20dictionary%20so%20we%20only%0A%20%20%20%20%23%20have%20to%20make%20them%20at%20notebook%20initialisation%0A%20%20%20%20color_ramps%20%3D%20%7Bk%3A%20get_colour_ramp(k)%20for%20k%20in%20available_palettes%20%2B%20%5Bp%20%2B%20%22_r%22%20for%20p%20in%20available_palettes%5D%7D%0A%20%20%20%20return%20(%0A%20%20%20%20%20%20%20%20available_palettes%2C%0A%20%20%20%20%20%20%20%20builtin_gdf%2C%0A%20%20%20%20%20%20%20%20color_ramps%2C%0A%20%20%20%20%20%20%20%20dummy_data_file%2C%0A%20%20%20%20%20%20%20%20ok_message%2C%0A%20%20%20%20)%0A%0A%0A%40app.cell%0Adef%20_(dummy_data_file%2C%20mo)%3A%0A%20%20%20%20%23%20the%20input%20data%20source%0A%20%20%20%20get_input_data%2C%20set_input_data%20%3D%20mo.state(dummy_data_file)%0A%20%20%20%20return%20get_input_data%2C%20set_input_data%0A%0A%0A%40app.cell%0Adef%20_(builtin_gdf%2C%20mo)%3A%0A%20%20%20%20%23%20the%20GeoDataframe%20we%20are%20tiling%20-%20using%20state%20means%20we%20can%20restore%0A%20%20%20%20%23%20current%20GDF%20if%20a%20new%20one%20has%20issues%20%0A%20%20%20%20get_gdf%2C%20set_gdf%20%3D%20mo.state(builtin_gdf)%0A%20%20%20%20return%20get_gdf%2C%20set_gdf%0A%0A%0A%40app.cell%0Adef%20_(mo)%3A%0A%20%20%20%20%23%20variables%20currently%20selected%20by%20the%20user%0A%20%20%20%20get_variables%2C%20set_variables%20%3D%20mo.state(%5B%5D)%0A%20%20%20%20return%20get_variables%2C%20set_variables%0A%0A%0A%40app.cell%0Adef%20_(available_palettes%2C%20mo)%3A%0A%20%20%20%20%23%20palettes%20currently%20selected%20by%20the%20user%0A%20%20%20%20get_palettes%2C%20set_palettes%20%3D%20mo.state(available_palettes)%0A%20%20%20%20%23%20palette%20reverse%20settings%0A%20%20%20%20return%20get_palettes%2C%20set_palettes%0A%0A%0A%40app.cell%0Adef%20_(mo)%3A%0A%20%20%20%20get_reversed%2C%20set_reversed%20%3D%20mo.state(%5B%5D)%0A%20%20%20%20%23%20app%20status%20message%0A%20%20%20%20return%20get_reversed%2C%20set_reversed%0A%0A%0A%40app.cell%0Adef%20_(mo%2C%20ok_message)%3A%0A%20%20%20%20get_status_message%2C%20set_status_message%20%3D%20mo.state(ok_message)%0A%20%20%20%20return%20get_status_message%2C%20set_status_message%0A%0A%0A%40app.cell%0Adef%20_(mo)%3A%0A%20%20%20%20get_crs%2C%20set_crs%20%3D%20mo.state(3857)%0A%20%20%20%20return%20get_crs%2C%20set_crs%0A%0A%0A%40app.cell%0Adef%20module_imports()%3A%0A%20%20%20%20import%20io%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20%23%20for%20in-memory%20loading%20of%20inputs%20and%20outputs%0A%20%20%20%20return%20(io%2C)%0A%0A%0A%40app.cell%0Adef%20_()%3A%0A%20%20%20%20from%20pathlib%20import%20Path%0A%20%20%20%20return%20(Path%2C)%0A%0A%0A%40app.cell%0Adef%20_()%3A%0A%20%20%20%20import%20matplotlib%20as%20mpl%0A%20%20%20%20return%20(mpl%2C)%0A%0A%0A%40app.cell%0Adef%20_()%3A%0A%20%20%20%20import%20math%0A%20%20%20%20return%20(math%2C)%0A%0A%0A%40app.cell%0Adef%20_()%3A%0A%20%20%20%20import%20pandas%20as%20pd%0A%20%20%20%20return%20(pd%2C)%0A%0A%0A%40app.cell%0Adef%20_()%3A%0A%20%20%20%20import%20geopandas%20as%20gpd%0A%20%20%20%20return%20(gpd%2C)%0A%0A%0A%40app.cell%0Adef%20_()%3A%0A%20%20%20%20from%20shapely%20import%20is_valid%0A%20%20%20%20return%20(is_valid%2C)%0A%0A%0A%40app.cell%0Adef%20_()%3A%0A%20%20%20%20import%20weavingspace%20as%20wsp%0A%20%20%20%20return%20(wsp%2C)%0A%0A%0A%40app.cell%0Adef%20_()%3A%0A%20%20%20%20from%20weavingspace%20import%20CMAPS_SEQUENTIAL%0A%20%20%20%20from%20weavingspace%20import%20CMAPS_DIVERGING%0A%20%20%20%20return%20CMAPS_DIVERGING%2C%20CMAPS_SEQUENTIAL%0A%0A%0A%40app.cell(hide_code%3DTrue)%0Adef%20setup_tilings_dictionary()%3A%0A%20%20%20%20tilings_by_n%20%3D%20%7B%0A%20%20%20%20%20%202%3A%20%7B%0A%20%20%20%20%20%20%20%20%22plain%20weave%20a%7Cb%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22plain%22%2C%20strands%3D%22a%7Cb%22%2C%20n%3D%221%22)%2C%0A%20%20%20%20%20%20%20%20%22twill%20weave%20a%7Cb%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22twill%22%2C%20strands%3D%22a%7Cb%22%2C%20n%3D%222%22)%2C%0A%20%20%20%20%20%20%20%20%22twill%20weave%20a%7Cb-%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22twill%22%2C%20strands%3D%22a%7Cb-%22%2C%20n%3D%222%22)%2C%0A%20%20%20%20%20%20%20%20%22twill%20weave%20a%7Cb%203%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22twill%22%2C%20strands%3D%22a%7Cb%22%2C%20n%3D%223%22)%2C%0A%20%20%20%20%20%20%20%20%22twill%20weave%20a%7Cb-%203%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22twill%22%2C%20strands%3D%22a%7Cb-%22%2C%20n%3D%223%22)%2C%0A%20%20%20%20%20%20%20%20%22twill%20weave%20a%7Cb%204%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22twill%22%2C%20strands%3D%22a%7Cb%22%2C%20n%3D%224%22)%2C%0A%20%20%20%20%20%20%20%20%22twill%20weave%20a%7Cb%201%2C2%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22twill%22%2C%20strands%3D%22a%7Cb%22%2C%20n%3D%221%2C2%22)%2C%0A%20%20%20%20%20%20%20%20%22twill%20weave%20a%7Cb-%201%2C2%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22twill%22%2C%20strands%3D%22a%7Cb-%22%2C%20n%3D%221%2C2%22)%2C%0A%20%20%20%20%20%20%20%20%22twill%20weave%20a%7Cb%201%2C2%2C2%2C1%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22twill%22%2C%20strands%3D%22a%7Cb%22%2C%20n%3D%221%2C2%2C2%2C1%22)%2C%0A%20%20%20%20%20%20%20%20%22twill%20weave%20a%7Cb%202%2C3%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22twill%22%2C%20strands%3D%22a%7Cb%22%2C%20n%3D%222%2C3%22)%2C%0A%20%20%20%20%20%20%20%20%22twill%20weave%20a%7Cb%202%2C3%2C3%2C2%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22twill%22%2C%20strands%3D%22a%7Cb%22%2C%20n%3D%222%2C3%2C3%2C2%22)%2C%0A%20%20%20%20%20%20%20%20%22archimedean%204.8.8%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22archi%22%2C%20code%3D%224.8.8%22)%2C%0A%20%20%20%20%20%20%20%20%22square-slice%202%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22square-slice%22%2C%20n%3D2%2C%20offset%3D0)%2C%0A%20%20%20%20%20%20%20%20%22crosses%202%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22cross%22%2C%20n%3D2)%2C%0A%20%20%20%20%20%20%20%20%22star1%2044%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22star1%22%2C%20code%3D%2244%22%2C%20point_angle%3D30)%2C%0A%20%20%20%20%20%20%20%20%22hex-colouring%202%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22hex-col%22%2C%20n%3D2)%2C%0A%20%20%20%20%20%20%20%20%22square-colouring%202%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22square-col%22%2C%20n%3D2)%2C%0A%20%20%20%20%20%20%20%20%22hex-slice%202%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22hex-slice%22%2C%20n%3D2%2C%20offset%3D0)%2C%0A%20%20%20%20%20%20%20%20%22laves%203.3.3.4.4%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22lave%22%2C%20code%3D%223.3.3.4.4%22)%2C%0A%20%20%20%20%20%20%7D%2C%0A%20%20%20%20%20%203%3A%20%7B%0A%20%20%20%20%20%20%20%20%22cube%20weave%20a--%7Cb--%7Cc--%22%3A%20dict(type%3D%20%22weave%22%2C%20weave_type%3D%22cube%22%2C%20strands%3D%22a--%7Cb--%7Cc--%22)%2C%0A%20%20%20%20%20%20%20%20%22plain%20weave%20ab%7Cc%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22plain%22%2C%20strands%3D%22ab%7Cc%22%2C%20n%3D%221%22)%2C%0A%20%20%20%20%20%20%20%20%22plain%20weave%20ab-%7Cc%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22plain%22%2C%20strands%3D%22ab-%7Cc%22%2C%20n%3D%221%22)%2C%0A%20%20%20%20%20%20%20%20%22twill%20weave%20ab%7Cc-%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22twill%22%2C%20strands%3D%22ab%7Cc-%22%2C%20n%3D%222%22)%2C%0A%20%20%20%20%20%20%20%20%22basket%20weave%20ab%7Cc-%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22basket%22%2C%20strands%3D%22ab%7Cc-%22%2C%20n%3D%222%22)%2C%0A%20%20%20%20%20%20%20%20%22hex-slice%203%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22hex-slice%22%2C%20n%3D3%2C%20offset%3D0)%2C%0A%20%20%20%20%20%20%20%20%22hex-colouring%203%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22hex-col%22%2C%20n%3D3)%2C%0A%20%20%20%20%20%20%20%20%22crosses%203%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22cross%22%2C%20n%3D3)%2C%0A%20%20%20%20%20%20%20%20%22square-colouring%203%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22square-col%22%2C%20n%3D3)%2C%0A%20%20%20%20%20%20%20%20%22archimedean%203.6.3.6%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22archi%22%2C%20code%3D%223.6.3.6%22)%2C%0A%20%20%20%20%20%20%20%20%22archimedean%203.12.12%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22archi%22%2C%20code%3D%223.12.12%22)%2C%0A%20%20%20%20%20%20%20%20%22square-slice%203%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22square-slice%22%2C%20n%3D3%2C%20offset%3D0)%2C%0A%20%20%20%20%20%20%20%20%22archimedean%203.3.3.4.4%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22archi%22%2C%20code%3D%223.3.3.4.4%22)%2C%0A%20%20%20%20%20%20%20%20%23%20%22hex-dissection%203%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22hex-dissect%22%2C%20n%3D3%2C%20offset%3D0%2C%20offset_angle%3D0)%2C%0A%20%20%20%20%20%20%20%20%23%20%22square-dissection%203%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22square-dissect%22%2C%20n%3D3%2C%20offset%3D0%2C%20offset_angle%3D0)%2C%0A%20%20%20%20%20%20%20%20%22star1%2033%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22star1%22%2C%20code%3D%2233%22%2C%20point_angle%3D30)%2C%0A%20%20%20%20%20%20%20%20%22star2%2066%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22star2%22%2C%20code%3D%2266%22)%2C%0A%20%20%20%20%20%20%20%20%22star1%2036%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22star1%22%2C%20code%3D%2236%22%2C%20point_angle%3D30)%2C%0A%20%20%20%20%20%20%20%20%22star1%2063%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22star1%22%2C%20code%3D%2263%22%2C%20point_angle%3D30)%2C%0A%20%20%20%20%20%20%7D%2C%0A%20%20%20%20%20%204%3A%20%7B%0A%20%20%20%20%20%20%20%20%22laves%203.3.4.3.4%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22laves%22%2C%20code%3D%223.3.4.3.4%22)%2C%0A%20%20%20%20%20%20%20%20%22plain%20weave%20ab%7Ccd%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22plain%22%2C%20strands%3D%22ab%7Ccd%22%2C%20n%3D%221%22)%2C%0A%20%20%20%20%20%20%20%20%22plain%20weave%20ab-%7Ccd%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22plain%22%2C%20strands%3D%22ab-%7Ccd%22%2C%20n%3D%221%22)%2C%0A%20%20%20%20%20%20%20%20%22plain%20weave%20ab-%7Ccd-%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22plain%22%2C%20strands%3D%22ab-%7Ccd-%22%2C%20n%3D%221%22)%2C%0A%20%20%20%20%20%20%20%20%22basket%20weave%20ab%7Ccd%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22basket%22%2C%20strands%3D%22ab%7Ccd%22%2C%20n%3D%222%22)%2C%0A%20%20%20%20%20%20%20%20%22basket%20weave%20ab%7Ccd%203%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22basket%22%2C%20strands%3D%22ab%7Ccd%22%2C%20n%3D%223%22)%2C%0A%20%20%20%20%20%20%20%20%22twill%20weave%20ab%7Ccd%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22twill%22%2C%20strands%3D%22ab%7Ccd%22%2C%20n%3D%222%22)%2C%0A%20%20%20%20%20%20%20%20%22twill%20weave%20ab%7Ccd%203%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22twill%22%2C%20strands%3D%22ab%7Ccd%22%2C%20n%3D%223%22)%2C%0A%20%20%20%20%20%20%20%20%22twill%20weave%20ab%7Ccd%201%2C2%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22twill%22%2C%20strands%3D%22ab%7Ccd%22%2C%20n%3D%221%2C2%22)%2C%0A%20%20%20%20%20%20%20%20%22twill%20weave%20ab%7Ccd%201%2C2%2C2%2C1%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22twill%22%2C%20strands%3D%22ab%7Ccd%22%2C%20n%3D%221%2C2%2C2%2C1%22)%2C%0A%20%20%20%20%20%20%20%20%22basket%20weave%20ab-%7Ccd%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22basket%22%2C%20strands%3D%22ab-%7Ccd%22%2C%20n%3D%223%22)%2C%0A%20%20%20%20%20%20%20%20%22twill%20weave%20ab-%7Ccd%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22twill%22%2C%20strands%3D%22ab-%7Ccd%22%2C%20n%3D%223%22)%2C%0A%20%20%20%20%20%20%20%20%22basket%20weave%20ab-%7Ccd-%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22basket%22%2C%20strands%3D%22ab-%7Ccd-%22%2C%20n%3D%223%22)%2C%0A%20%20%20%20%20%20%20%20%22twill%20weave%20ab-%7Ccd-%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22twill%22%2C%20strands%3D%22ab-%7Ccd-%22%2C%20n%3D%223%22)%2C%0A%20%20%20%20%20%20%20%20%22crosses%204%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22cross%22%2C%20n%3D4)%2C%0A%20%20%20%20%20%20%20%20%22square-slice%204%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22square-slice%22%2C%20n%3D4%2C%20offset%3D0)%2C%0A%20%20%20%20%20%20%20%20%22square-colouring%204%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22square-col%22%2C%20n%3D4)%2C%0A%20%20%20%20%20%20%20%20%22hex-colouring%204%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22hex-col%22%2C%20n%3D4)%2C%0A%20%20%20%20%20%20%20%20%22star2%2064%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22star2%22%2C%20code%3D%2264%22)%2C%0A%20%20%20%20%20%20%20%20%22star2%20464%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22star2%22%2C%20code%3D%22464%22)%2C%0A%20%20%20%20%20%20%20%20%22star2%20844%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22star2%22%2C%20code%3D%22844%22)%2C%0A%20%20%20%20%20%20%20%20%22hex-slice%204%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22hex-slice%22%2C%20n%3D4%2C%20offset%3D0)%2C%0A%20%20%20%20%20%20%20%20%23%20%22hex-dissection%204%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22hex-dissect%22%2C%20n%3D4%2C%20offset%3D0%2C%20offset_angle%3D0)%2C%0A%20%20%20%20%20%20%7D%2C%0A%20%20%20%20%20%205%3A%20%7B%0A%20%20%20%20%20%20%20%20%22square-colouring%205%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22square-col%22%2C%20n%3D5)%2C%0A%20%20%20%20%20%20%20%20%22crosses%205%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22crosses%22%2C%20n%3D5)%2C%0A%20%20%20%20%20%20%20%20%22plain%20weave%20abc%7Cde%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22plain%22%2C%20strands%3D%22abc%7Cde%22%2C%20n%3D%221%22)%2C%0A%20%20%20%20%20%20%20%20%22plain%20weave%20abc-%7Cde%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22plain%22%2C%20strands%3D%22abc-%7Cde%22%2C%20n%3D%221%22)%2C%0A%20%20%20%20%20%20%20%20%22plain%20weave%20abc-%7Cde-%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22plain%22%2C%20strands%3D%22abc-%7Cde-%22%2C%20n%3D%221%22)%2C%0A%20%20%20%20%20%20%20%20%22twill%20weave%20abc%7Cde%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22twill%22%2C%20strands%3D%22abc%7Cde%22%2C%20n%3D%223%22)%2C%0A%20%20%20%20%20%20%20%20%22twill%20weave%20abc%7Cde-%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22twill%22%2C%20strands%3D%22abc%7Cde-%22%2C%20n%3D%223%22)%2C%0A%20%20%20%20%20%20%20%20%22twill%20weave%20abc-%7Cde-%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22twill%22%2C%20strands%3D%22abc-%7Cde-%22%2C%20n%3D%223%22)%2C%0A%20%20%20%20%20%20%20%20%22basket%20weave%20abc%7Cde%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22basket%22%2C%20strands%3D%22abc%7Cde%22%2C%20n%3D%223%22)%2C%0A%20%20%20%20%20%20%20%20%22basket%20weave%20abc%7Cde-%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22basket%22%2C%20strands%3D%22abc%7Cde-%22%2C%20n%3D%223%22)%2C%0A%20%20%20%20%20%20%20%20%22basket%20weave%20abc-%7Cde-%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22basket%22%2C%20strands%3D%22abc-%7Cde-%22%2C%20n%3D%223%22)%2C%0A%20%20%20%20%20%20%20%20%22hex-colouring%205%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22hex-col%22%2C%20n%3D5)%2C%0A%20%20%20%20%20%20%20%20%22hex-slice%205%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22hex-slice%22%2C%20n%3D5%2C%20offset%3D0)%2C%0A%20%20%20%20%20%20%20%20%22square-slice%205%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22square-slice%22%2C%20n%3D5%2C%20offset%3D0)%2C%0A%20%20%20%20%20%20%20%20%22square-dissection%205%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22square-dissect%22%2C%20n%3D5%2C%20offset%3D0%2C%20offset_angle%3D0)%2C%0A%20%20%20%20%20%20%7D%2C%0A%20%20%20%20%20%206%3A%20%7B%0A%20%20%20%20%20%20%20%20%22hex-slice%206%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22hex-slice%22%2C%20n%3D6%2C%20offset%3D0)%2C%0A%20%20%20%20%20%20%20%20%22square-slice%206%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22square-slice%22%2C%20n%3D6%2C%20offset%3D0)%2C%0A%20%20%20%20%20%20%20%20%22square-colouring%206%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22square-col%22%2C%20n%3D6)%2C%0A%20%20%20%20%20%20%20%20%22laves%203.3.3.3.6%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22lave%22%2C%20code%3D%223.3.3.3.6%22)%2C%0A%20%20%20%20%20%20%20%20%22laves%203.12.12%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22lave%22%2C%20code%3D%223.12.12%22)%2C%0A%20%20%20%20%20%20%20%20%22cube%20weave%20a-b%7Cc-d%7Ce-f%22%3A%20dict(type%3D%20%22weave%22%2C%20weave_type%3D%22cube%22%2C%20strands%3D%22a-b%7Cc-d%7Ce-f%22)%2C%0A%20%20%20%20%20%20%20%20%22plain%20weave%20abc%7Cdef%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22plain%22%2C%20strands%3D%22abc%7Cdef%22%2C%20n%3D%221%22)%2C%0A%20%20%20%20%20%20%20%20%22plain%20weave%20abc-%7Cdef%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22plain%22%2C%20strands%3D%22abc-%7Cdef%22%2C%20n%3D%221%22)%2C%0A%20%20%20%20%20%20%20%20%22plain%20weave%20abc-%7Cdef-%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22plain%22%2C%20strands%3D%22abc-%7Cdef-%22%2C%20n%3D%221%22)%2C%0A%20%20%20%20%20%20%20%20%22basket%20weave%20abc%7Cdef%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22basket%22%2C%20strands%3D%22abc%7Cdef%22%2C%20n%3D%223%22)%2C%0A%20%20%20%20%20%20%20%20%22twill%20weave%20abc%7Cdef%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22twill%22%2C%20strands%3D%22abc%7Cdef%22%2C%20n%3D%223%22)%2C%0A%20%20%20%20%20%20%20%20%22basket%20weave%20abc-%7Cdef%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22basket%22%2C%20strands%3D%22abc-%7Cdef%22%2C%20n%3D%223%22)%2C%0A%20%20%20%20%20%20%20%20%22twill%20weave%20abc-%7Cdef%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22twill%22%2C%20strands%3D%22abc-%7Cdef%22%2C%20n%3D%223%22)%2C%0A%20%20%20%20%20%20%20%20%22basket%20weave%20abc-%7Cdef-%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22basket%22%2C%20strands%3D%22abc-%7Cdef-%22%2C%20n%3D%224%22)%2C%0A%20%20%20%20%20%20%20%20%22twill%20weave%20abc-%7Cdef-%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22twill%22%2C%20strands%3D%22abc-%7Cdef-%22%2C%20n%3D%224%22)%2C%0A%20%20%20%20%20%20%20%20%22archimedean%203.3.4.3.4%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22archi%22%2C%20code%3D%223.3.4.3.4%22)%2C%0A%20%20%20%20%20%20%20%20%22archimedean%203.4.6.4%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22archi%22%2C%20code%3D%223.4.6.4%22)%2C%0A%20%20%20%20%20%20%20%20%22archimedean%204.6.12%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22archi%22%2C%20code%3D%224.6.12%22)%2C%0A%20%20%20%20%20%20%20%20%22crosses%206%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22cross%22%2C%20n%3D6)%2C%0A%20%20%20%20%20%20%20%20%22star2%2045%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22star2%22%2C%20code%3D%2245%22)%2C%0A%20%20%20%20%20%20%20%20%22star2%20663%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22star2%22%2C%20code%3D%22663%22)%2C%0A%20%20%20%20%20%20%20%20%22star2%20466%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22star2%22%2C%20code%3D%22466%22)%2C%0A%20%20%20%20%20%20%20%20%22hex-colouring%206%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22hex-col%22%2C%20n%3D6)%2C%0A%20%20%20%20%20%20%7D%2C%0A%20%20%20%20%20%207%3A%20%7B%0A%20%20%20%20%20%20%20%20%22hex-colouring%207%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22hex-col%22%2C%20n%3D7)%2C%0A%20%20%20%20%20%20%20%20%22crosses%207%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22cross%22%2C%20n%3D7)%2C%0A%20%20%20%20%20%20%20%20%22plain%20weave%20abcd%7Cefg%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22plain%22%2C%20strands%3D%22abcd%7Cefg%22%2C%20n%3D%221%22)%2C%0A%20%20%20%20%20%20%20%20%22plain%20weave%20abcd%7Cefg-%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22plain%22%2C%20strands%3D%22abcd%7Cefg-%22%2C%20n%3D%221%22)%2C%0A%20%20%20%20%20%20%20%20%22plain%20weave%20abcd-%7Cefg-%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22plain%22%2C%20strands%3D%22abcd-%7Cefg-%22%2C%20n%3D%221%22)%2C%0A%20%20%20%20%20%20%20%20%22basket%20weave%20abcd%7Cefg%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22basket%22%2C%20strands%3D%22abcd%7Cefg%22%2C%20n%3D%223%22)%2C%0A%20%20%20%20%20%20%20%20%22basket%20weave%20abcd%7Cefg-%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22basket%22%2C%20strands%3D%22abcd%7Cefg-%22%2C%20n%3D%224%22)%2C%0A%20%20%20%20%20%20%20%20%22basket%20weave%20abcd%7Cefg-%202%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22basket%22%2C%20strands%3D%22abcd%7Cefg-%22%2C%20n%3D%222%22)%2C%0A%20%20%20%20%20%20%20%20%22twill%20weave%20abcd%7Cefg%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22twill%22%2C%20strands%3D%22abcd%7Cefg%22%2C%20n%3D%223%22)%2C%0A%20%20%20%20%20%20%20%20%22twill%20weave%20abcd%7Cefg-%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22twill%22%2C%20strands%3D%22abcd%7Cefg-%22%2C%20n%3D%224%22)%2C%0A%20%20%20%20%20%20%20%20%22twill%20weave%20abcd%7Cefg-%202%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22twill%22%2C%20strands%3D%22abcd%7Cefg-%22%2C%20n%3D%222%22)%2C%0A%20%20%20%20%20%20%20%20%22square-colouring%207%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22square-col%22%2C%20n%3D7)%2C%0A%20%20%20%20%20%20%20%20%22hex-slice%207%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22hex-slice%22%2C%20n%3D7%2C%20offset%3D0)%2C%0A%20%20%20%20%20%20%20%20%22square-slice%207%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22square-slice%22%2C%20n%3D7%2C%20offset%3D0)%2C%0A%20%20%20%20%20%20%20%20%22hex-dissection%207%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22hex-dissect%22%2C%20n%3D7%2C%20offset%3D0%2C%20offset_angle%3D0)%2C%0A%20%20%20%20%20%20%7D%2C%0A%20%20%20%20%20%208%3A%20%7B%0A%20%20%20%20%20%20%20%20%22square-slice%208%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22square-slice%22%2C%20n%3D8%2C%20offset%3D0)%2C%0A%20%20%20%20%20%20%20%20%22plain%20weave%20abcd%7Cefgh%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22plain%22%2C%20strands%3D%22abcd%7Cefgh%22%2C%20n%3D%221%22)%2C%0A%20%20%20%20%20%20%20%20%22plain%20weave%20abcd-%7Cefgh%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22plain%22%2C%20strands%3D%22abcd-%7Cefgh%22%2C%20n%3D%221%22)%2C%0A%20%20%20%20%20%20%20%20%22plain%20weave%20abcd-%7Cefgh-%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22plain%22%2C%20strands%3D%22abcd-%7Cefgh-%22%2C%20n%3D%221%22)%2C%0A%20%20%20%20%20%20%20%20%22basket%20weave%20abcd%7Cefgh%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22basket%22%2C%20strands%3D%22abcd%7Cefgh%22%2C%20n%3D%224%22)%2C%0A%20%20%20%20%20%20%20%20%22basket%20weave%20abcd%7Cefgh%202%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22basket%22%2C%20strands%3D%22abcd%7Cefgh%22%2C%20n%3D%222%22)%2C%0A%20%20%20%20%20%20%20%20%22twill%20weave%20abcd%7Cefgh%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22twill%22%2C%20strands%3D%22abcd%7Cefgh%22%2C%20n%3D%224%22)%2C%0A%20%20%20%20%20%20%20%20%22twill%20weave%20abcd%7Cefgh%202%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22twill%22%2C%20strands%3D%22abcd%7Cefgh%22%2C%20n%3D%222%22)%2C%0A%20%20%20%20%20%20%20%20%22square-colouring%208%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22square-col%22%2C%20n%3D8)%2C%0A%20%20%20%20%20%20%20%20%22hex-slice%208%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22hex-slice%22%2C%20n%3D8%2C%20offset%3D0)%2C%0A%20%20%20%20%20%20%20%20%22hex-colouring%208%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22hex-col%22%2C%20n%3D8)%2C%0A%20%20%20%20%20%20%7D%2C%0A%20%20%20%20%20%209%3A%20%7B%0A%20%20%20%20%20%20%20%20%22cube%20weave%20abc%7Cdef%7Cghi%22%3A%20dict(type%3D%20%22weave%22%2C%20weave_type%3D%22cube%22%2C%20strands%3D%22abc%7Cdef%7Cghi%22)%2C%0A%20%20%20%20%20%20%20%20%22hex-slice%209%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22hex-slice%22%2C%20n%3D9%2C%20offset%3D0)%2C%0A%20%20%20%20%20%20%20%20%22square-colouring%209%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22square-col%22%2C%20n%3D9)%2C%0A%20%20%20%20%20%20%20%20%22hex-colouring%209%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22hex-col%22%2C%20n%3D9)%2C%0A%20%20%20%20%20%20%20%20%22square-slice%209%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22square-slice%22%2C%20n%3D9%2C%20offset%3D0)%2C%0A%20%20%20%20%20%20%20%20%22archimedean%203.3.3.3.6%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22archi%22%2C%20code%3D%223.3.3.3.6%22)%2C%0A%20%20%20%20%20%20%20%20%22plain%20weave%20abcde%7Cfghi%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22plain%22%2C%20strands%3D%22abcde%7Cfghi%22%2C%20n%3D%221%22)%2C%0A%20%20%20%20%20%20%20%20%22plain%20weave%20abcde-%7Cfghi%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22plain%22%2C%20strands%3D%22abcde-%7Cfghi%22%2C%20n%3D%221%22)%2C%0A%20%20%20%20%20%20%20%20%22plain%20weave%20abcde-%7Cfghi-%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22plain%22%2C%20strands%3D%22abcde-%7Cfghi-%22%2C%20n%3D%221%22)%2C%0A%20%20%20%20%20%20%20%20%22hex-dissection%209%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22hex-dissect%22%2C%20n%3D9%2C%20offset%3D0%2C%20offset_angle%3D0)%2C%0A%20%20%20%20%20%20%20%20%22square-dissection%209%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22square-dissect%22%2C%20n%3D9%2C%20offset%3D0%2C%20offset_angle%3D0)%2C%0A%20%20%20%20%20%20%7D%2C%0A%20%20%20%20%20%2010%3A%20%7B%0A%20%20%20%20%20%20%20%20%22hex-colouring%2010%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22hex-col%22%2C%20n%3D10)%2C%0A%20%20%20%20%20%20%20%20%22hex-slice%2010%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22hex-slice%22%2C%20n%3D10%2C%20offset%3D0)%2C%0A%20%20%20%20%20%20%20%20%22square-slice%2010%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22square-slice%22%2C%20n%3D10%2C%20offset%3D0)%2C%0A%20%20%20%20%20%20%20%20%22plain%20weave%20abcde%7Cfghij%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22plain%22%2C%20strands%3D%22abcde%7Cfghij%22%2C%20n%3D%221%22)%2C%0A%20%20%20%20%20%20%20%20%22plain%20weave%20abcde-%7Cfghij%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22plain%22%2C%20strands%3D%22abcde-%7Cfghij%22%2C%20n%3D%221%22)%2C%0A%20%20%20%20%20%20%20%20%22plain%20weave%20abcde-%7Cfghij-%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22plain%22%2C%20strands%3D%22abcde-%7Cfghij-%22%2C%20n%3D%221%22)%2C%0A%20%20%20%20%20%20%7D%2C%0A%20%20%20%20%20%2011%3A%20%7B%0A%20%20%20%20%20%20%20%20%22hex-colouring%2011%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22hex-col%22%2C%20n%3D11)%2C%0A%20%20%20%20%20%20%20%20%22hex-slice%2011%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22hex-slice%22%2C%20n%3D11%2C%20offset%3D0)%2C%0A%20%20%20%20%20%20%20%20%22square-slice%2011%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22square-slice%22%2C%20n%3D11%2C%20offset%3D0)%2C%0A%20%20%20%20%20%20%20%20%22chavey%20E%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22chavey%22%2C%20code%3D%22E%22)%2C%0A%20%20%20%20%20%20%20%20%22chavey%20F%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22chavey%22%2C%20code%3D%22F%22)%2C%0A%20%20%20%20%20%20%20%20%22plain%20weave%20abcdef%7Cghijk%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22plain%22%2C%20strands%3D%22abcdef%7Cghijk%22%2C%20n%3D%221%22)%2C%0A%20%20%20%20%20%20%20%20%22plain%20weave%20abcdef%7Cghijk-%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22plain%22%2C%20strands%3D%22abcdef%7Cghijk-%22%2C%20n%3D%221%22)%2C%0A%20%20%20%20%20%20%20%20%22plain%20weave%20abcdef-%7Cghijk-%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22plain%22%2C%20strands%3D%22abcdef-%7Cghijk-%22%2C%20n%3D%221%22)%2C%0A%20%20%20%20%20%20%7D%2C%0A%20%20%20%20%20%2012%3A%20%7B%0A%20%20%20%20%20%20%20%20%22hex-slice%2012%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22hex-slice%22%2C%20n%3D12%2C%20offset%3D0)%2C%0A%20%20%20%20%20%20%20%20%22square-slice%2012%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22square-slice%22%2C%20n%3D12%2C%20offset%3D0)%2C%0A%20%20%20%20%20%20%20%20%22plain%20weave%20abcdef%7Cghijkl%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22plain%22%2C%20strands%3D%22abcdef%7Cghijkl%22%2C%20n%3D%221%22)%2C%0A%20%20%20%20%20%20%20%20%22plain%20weave%20abcdef-%7Cghijkl%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22plain%22%2C%20strands%3D%22abcdef-%7Cghijkl%22%2C%20n%3D%221%22)%2C%0A%20%20%20%20%20%20%20%20%22plain%20weave%20abcdef-%7Cghijkl-%22%3A%20dict(type%3D%22weave%22%2C%20weave_type%3D%22plain%22%2C%20strands%3D%22abcdef-%7Cghijkl-%22%2C%20n%3D%221%22)%2C%0A%20%20%20%20%20%20%7D%2C%0A%20%20%20%20%20%2013%3A%20%7B%22chavey%20A%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22chavey%22%2C%20code%3D%22A%22)%2C%7D%2C%0A%20%20%20%20%20%2014%3A%20%7B%22chavey%20B%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22chavey%22%2C%20code%3D%22B%22)%2C%7D%2C%0A%20%20%20%20%20%2015%3A%20%7B%0A%20%20%20%20%20%20%20%20%22chavey%20H%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22chavey%22%2C%20code%3D%22H%22)%2C%0A%20%20%20%20%20%20%20%20%22chavey%20J%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22chavey%22%2C%20code%3D%22J%22)%2C%0A%20%20%20%20%20%20%7D%2C%0A%20%20%20%20%20%2016%3A%20%7B%0A%20%20%20%20%20%20%20%20%22square-colouring%2016%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22square-col%22%2C%20n%3D16)%2C%0A%20%20%20%20%20%20%20%20%22hex-colouring%2016%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22hex-col%22%2C%20n%3D16)%2C%0A%20%20%20%20%20%20%7D%2C%0A%20%20%20%20%20%2018%3A%20%7B%0A%20%20%20%20%20%20%20%20%22chavey%20C%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22chavey%22%2C%20code%3D%22C%22)%2C%0A%20%20%20%20%20%20%20%20%22chavey%20D%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22chavey%22%2C%20code%3D%22D%22)%2C%0A%20%20%20%20%20%20%7D%2C%0A%20%20%20%20%20%2019%3A%20%7B%22chavey%20G%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22chavey%22%2C%20code%3D%22G%22)%2C%7D%2C%0A%20%20%20%20%20%2020%3A%20%7B%0A%20%20%20%20%20%20%20%20%22chavey%20I%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22chavey%22%2C%20code%3D%22I%22)%2C%0A%20%20%20%20%20%20%20%20%22chavey%20K%22%3A%20dict(type%3D%22tiling%22%2C%20tiling_type%3D%22chavey%22%2C%20code%3D%22K%22)%2C%0A%20%20%20%20%20%20%7D%2C%0A%20%20%20%20%7D%0A%20%20%20%20return%20(tilings_by_n%2C)%0A%0A%0A%40app.cell%0Adef%20_(centred%2C%20mo)%3A%0A%20%20%20%20mo.vstack(%5Bmo.image(src%3D%22mw.png%22).style(centred)%2C%0A%20%20%20%20%20%20%20%20%20%20%20%20%20%20%20mo.md(f%22%3Cp%20style%3D'font-style%3Aitalic%3Btext-align%3Acenter%3Bline-height%3A1.2em%3B'%20title%3D'Weaving%20maps%20of%20complex%20data'%3E2026.01.31%20built%20with%20%3Ca%20href%3D'https%3A%2F%2Fgithub.com%2FDOSull%2Fweaving-space'%20target%3D'_blank'%3Eweavingspace%200.0.7.19%3C%2Fa%3E%20and%20%3Ca%20href%3D'https%3A%2F%2Fmarimo.io'%3Emarimo%200.17.7%3C%2Fa%3E%3C%2Fp%3E%22)%5D).center()%0A%20%20%20%20return%0A%0A%0A%40app.cell%0Adef%20_()%3A%0A%20%20%20%20centred%20%3D%20%7B%0A%20%20%20%20%20%20%20%20%22display%22%3A%20%22flex%22%2C%0A%20%20%20%20%20%20%20%20%22height%22%3A%20%22500px%22%2C%0A%20%20%20%20%20%20%20%20%22justify-content%22%3A%20%22center%22%2C%0A%20%20%20%20%20%20%20%20%22align-items%22%3A%20%22center%22%2C%0A%20%20%20%20%20%20%20%20%22text-align%22%3A%20%22center%22%2C%0A%20%20%20%20%7D%0A%20%20%20%20return%20(centred%2C)%0A%0A%0A%40app.cell%0Adef%20_()%3A%0A%20%20%20%20import%20marimo%20as%20mo%0A%20%20%20%20return%20(mo%2C)%0A%0A%0Aif%20__name__%20%3D%3D%20%22__main__%22%3A%0A%20%20%20%20app.run()%0A