Reputation: 13425
Is there a way to bind an event to occur after the render is finished in a backbone view?
I'm trying to attach a jQuery Date Range Picker to an input which is appended to the DOM after a link is clicked, but if I do it during the render, the range picker appears in the wrong place (because the input hasn't been given a DOM position yet). So, I need to wait until after the input has been rendered before I attach the date picker. Coffeescript is below.
@makeDateRangePicker
is a function that inits the date picker
class window.ClientDestinationPricingFieldsView extends ModelSaverView
template: (json) ->
_.template(jQuery("#special-pricing-timeframe-template").html()) json
render: ->
jQuery(@el).html @template(@model.toJSON())
@makeDateRangePicker jQuery(@el).find("input[name=date_range]")
this
Upvotes: 1
Views: 2620
Reputation: 6741
One way to do this is to trigger a custom event from the parent view after rendering is complete. $('body').trigger('my-rendering-is-done')
(a better way would be to trigger it on the view which is being rendered from the calling code). And have a listener in your view which uses the makeDateRangePicker
.
Upvotes: 0
Reputation: 2228
I would try this:
class window.ClientDestinationPricingFieldsView extends ModelSaverView
events:
'click input[name=date_range]': 'makeDateRangePicker'
template: (json) ->
_.template(jQuery("#special-pricing-timeframe-template").html()) json
render: ->
jQuery(@el).html @template(@model.toJSON())
this
You would have to modify @makeDateRangePicker
to take an event element instead.
Upvotes: 2
Reputation: 39223
Edit: So, my last stab at a solution was not.
What you're saying is that after your call to jQuery(@el).html
, the expected html is not there? That sounds very weird. I think it might be as simple as that you need to quote your attribute value:
jQuery(@el).find("input[name='date_range']")
Note the '
single-quote around date_range
.
Edit: Sorry, after verifying that it actually seems to work without quotes. I've been bitten by something similar before. Anyway, if the question is correct as it is now (after it's been updated with info about adding the input on a click event), then you should call makeDateRangePicker
right after you append the element, right?
Upvotes: 1
Reputation: 434665
You can usually use setTimeout
with a timeout of zero for this sort of thing. setTimeout(..., 0)
essentially queues up a function to be called once the browser has control again. Something like this:
render: ->
jQuery(@el).html @template(@model.toJSON())
setTimeout
=> @makeDateRangePicker jQuery(@el).find("input[name=date_range]")
0
@
I often use this trick with Google Maps to make it positioned and sized properly.
Upvotes: 1