Skip to content

Commit

Permalink
Fix draw control editing bug
Browse files Browse the repository at this point in the history
  • Loading branch information
giswqs committed Jun 15, 2024
1 parent 535649d commit 4e19eeb
Showing 1 changed file with 62 additions and 30 deletions.
92 changes: 62 additions & 30 deletions geemap/core.py
Original file line number Diff line number Diff line change
Expand Up @@ -178,30 +178,59 @@ def _sync_geometries(self):
return
# The current geometries from the draw_control.
test_geojsons = self._get_synced_geojson_from_draw_control()
i = 0
while i < self.count and i < len(test_geojsons):
local_geometry = None
test_geometry = None
while i < self.count and i < len(test_geojsons):
local_geometry = self.geometries[i]
test_geometry = common.geojson_to_ee(test_geojsons[i], geodesic=False)
if test_geometry == local_geometry:
i += 1
else:
break
if i < self.count and test_geometry is not None:
self.geometries[i] = test_geometry
if self.layer is not None:
self._redraw_layer()
self.geometries = [
common.geojson_to_ee(geo_json, geodesic=False) for geo_json in test_geojsons
]
# i = 0
# while i < self.count and i < len(test_geojsons):
# self.geometries = []

# local_geometry = None
# test_geometry = None
# while i < self.count and i < len(test_geojsons):
# local_geometry = self.geometries[i]
# test_geometry = common.geojson_to_ee(test_geojsons[i], geodesic=False)
# if test_geometry == local_geometry:
# i += 1
# else:
# break
# if i < self.count and test_geometry is not None:
# self.geometries[i] = test_geometry
# if self.layer is not None:
# self._redraw_layer()

def _redraw_layer(self):
if self.host_map:
self.host_map.add_layer(
self.collection, {"color": "blue"}, _DRAWN_FEATURES_LAYER, False, 0.5
)
self.layer = self.host_map.ee_layers.get(_DRAWN_FEATURES_LAYER, {}).get(
"ee_layer", None
)
# If the layer already exists, substitute it. This can avoid flickering.
if _DRAWN_FEATURES_LAYER in self.host_map.ee_layers:
old_layer = self.host_map.ee_layers.get(_DRAWN_FEATURES_LAYER, {})[
"ee_layer"
]
new_layer = ee_tile_layers.EELeafletTileLayer(
self.collection,
{"color": "blue"},
_DRAWN_FEATURES_LAYER,
old_layer.visible,
0.5,
)
self.host_map.substitute_layer(old_layer, new_layer)
self.layer = self.host_map.ee_layers.get(_DRAWN_FEATURES_LAYER, {}).get(
"ee_layer", None
)
self.host_map.ee_layers.get(_DRAWN_FEATURES_LAYER, {})[
"ee_layer"
] = new_layer
else: # Otherwise, add the layer.
self.host_map.add_layer(
self.collection,
{"color": "blue"},
_DRAWN_FEATURES_LAYER,
False,
0.5,
)
self.layer = self.host_map.ee_layers.get(_DRAWN_FEATURES_LAYER, {}).get(
"ee_layer", None
)

def _handle_geometry_created(self, geo_json):
geometry = common.geojson_to_ee(geo_json, geodesic=False)
Expand All @@ -217,7 +246,7 @@ def _handle_geometry_edited(self, geo_json):
self.last_geometry = geometry
self.last_draw_action = DrawActions.EDITED
self._sync_geometries()
self._redraw_layer()
# self._redraw_layer()
self._geometry_edit_dispatcher(self, geometry=geometry)

def _handle_geometry_deleted(self, geo_json):
Expand Down Expand Up @@ -254,8 +283,8 @@ def __init__(self, host_map, **kwargs):
# added to the layer instead of modified in place. Remove when
# https://github.com/jupyter-widgets/ipyleaflet/issues/1119 is fixed to
# allow geometry edits to be reflected on the tile layer.
def _handle_geometry_edited(self, geo_json):
return self._handle_geometry_created(geo_json)
# def _handle_geometry_edited(self, geo_json):
# return self._handle_geometry_created(geo_json)

def _get_synced_geojson_from_draw_control(self):
return [data.copy() for data in self.data]
Expand All @@ -276,20 +305,23 @@ def handle_draw(_, action, geo_json):
raise Exception(e)

self.on_draw(handle_draw)

# NOTE: Uncomment the following code once
# https://github.com/jupyter-widgets/ipyleaflet/issues/1119 is fixed
# to allow edited geometries to be reflected instead of added.
# def handle_data_update(_):
# self._sync_geometries()
# self.observe(handle_data_update, 'data')
def handle_data_update(_):
self._sync_geometries()
if self.last_draw_action == DrawActions.EDITED:
self._redraw_layer()

self.observe(handle_data_update, "data")

def _remove_geometry_at_index_on_draw_control(self, index):
# NOTE: Uncomment the following code once
# https://github.com/jupyter-widgets/ipyleaflet/issues/1119 is fixed to
# remove drawn geometries with `remove_last_drawn()`.
# del self.data[index]
# self.send_state(key='data')
pass
del self.data[index]
self.send_state(key="data")

def _clear_draw_control(self):
self.data = [] # Remove all drawn features from the map.
Expand Down

0 comments on commit 4e19eeb

Please sign in to comment.