re-frame

liebs 2023-10-24T20:29:11.712599Z

I've got this series of events and effects to interact with the Google Maps API:

(reg-event-db
 :config/save-map
 (fn [db [_ map]]
   (assoc db :config.geo/map map)))

(reg-event-db
 :map/update-map
 (fn [db [_ canvas lat-lng]]
   (let [Map (get db :config.geo/map)]
     (assoc db :map/current-view (Map. canvas (clj->js lat-lng))))))

(reg-event-fx
 :maps/set-current-center
 (fn [{:keys [db]} [_ new-center]]
   (let [new-coords (get-in db [:config.maps/coords new-center])]
     {:fx [[:dispatch [:map/update-map (gdom/getElement "map-canvas")
                       {:center new-coords
                        :zoom 13}]]]})))

(reg-event-fx
 :config/load-google-maps
 (fn [_ _]
   {:google-maps nil}))

(reg-fx
 :google-maps
 (fn [_]
   (js-await [_ (try (.load (Loader. #js {:apiKey api-key
                                          :version "weekly"}))
                     (catch js/Error e
                       (throw (ex-info "failed to load JS Maps API" {:cause e}))))]
             (js-await [lib (js/google.maps.importLibrary "maps")]
                       (dispatch [:config/save-map (gobj/get lib "Map")])))))
On various screens throughout my app, I am constructing a new map and rendering it. But if I want to see the change I expect, I have to click twice on a route before the change to the map takes. I'm guessing there's a bug in my code but I'd appreciate some insight. Should I perhaps instead just use the mutability provided by the Map class and update its state that way?

p-himik 2023-10-24T20:56:51.230889Z

One potential issue is that, it seems, (Map. canvas ...) actually mutates that canvas. And event handlers should be pure. Another potential issue might be in the way :map/current-view is used, if it is used. Yet another potential issue is re-using the same canvas for different maps. Finally, mutating an existing map object is always better than creating a completely new one each time you need to do something since that's how it was designed. Unrelated comments: • With React, you seldom need to access DOM elements by ID. That (gdom/getElement "map-canvas") should probably become a ref • (gobj/get lib "Map") can be (.-Map lib)

liebs 2023-10-24T21:04:26.149029Z

yeah, I am a little suspect about the :map/current-view myself. It doesn't do anything, yet, except hold that map state. I did attempt to use Map.setCenter to update the existing map but it didn't change anything about that double-click scenario. I'm gonna explore the ref solution.