How to display dynamic data in modal?

I’m using Foundation 5 as frontend framework. It works as supposed to. But I’m having trouble loading dynamic data in a modal.

The code displayed only has the necessary elements to support my question.

I have a collection of products. In my home template I have a loop that iterates over the products:

{{#each products}}
{{> product}}
{{/each}}

This works the products are displayed.

At the bottom of the home template I have a modal waiting to be called (I don’t know if this is the right place to put the modal?)

<div id="product-modal" class="reveal-modal" data-reveal aria-labelledby="modalTitle" aria-hidden="true" role="dialog">
{{> productPage}}
<a class="close-reveal-modal" aria-label="Close">&#215;</a>
</div>

The modal works. It opens and it closes. I displays all the static content but none of the dynamic.
When I use the router to route to the productPage template the dynamic data ‘does’ get loaded.

<template name="productPage">
	<div class="row">
		<div class="small-12 medium-9 columns">
			<div class="row">
				<div class="small-12 columns">
					<h1>{{title}}</h1>
				</div>
			</div>
			<div class="row">
				<div class="small-12 columns">
					{{#with image}}
						<img src="{{this.url}}" alt="">
					{{/with}}
				</div>
			</div>
		</div>
	</div>	
</template>

I don’t know if I have to look in the iron router for the answer or to use a template helper somehow.

Template.productPage.helpers({
	products: function () {
		return Products.findOne({});
	},
	image:function(){  
		return productImages.findOne({'metadata.productId':this._id})
	}
});

I hope someone can help me. Thank you.

It looks like the productPage isn’t getting the data context. If you use a template helper on the parent template you can query the data and pass it in with the with helper like this:

<template name='home'>
  <div id="product-modal" class="reveal-modal" data-reveal
    aria-labelledby="modalTitle" aria-hidden="true" role="dialog">

    {{#with productData}}
      {{> productPage}}
    {{/with}}
    <a class="close-reveal-modal" aria-label="Close">&#215;</a>
  </div>
</template>

and then in the home template create a helper like this:

Template.home.helpers({
  // returns a product document
  productData: function() {
    return db.products.findOne('some query here');
  }
});



However, when i’m using modal’s with Bootstrap I tend to use Iron Router’s named yield feature to switch out the template to render. This will pass the data from Iron Router into the template as well (assuming you can subscribe and fetch the data at this point).
The modal markup can go in the main template since it might be used on any page.

<template name='mainLayout'>

  {{> header}}

  <div class="main-content" id="content" role="main">
    {{> yield}}
  </div>

  <div id='modal'>
    {{> yield 'modalContent'}}
  </div

</template>    

and then in the controller you can tell IR to render a specific template into the named yield region:

PostsController.show = AppController.extend({
  template: 'postsShow',

  action: function() {
    this.render('postsShow');
    this.render('someTemplate', {to: 'modalContents'});
  }
});  

(note, I have an AppController that inherits from the base RouteController so it may look a bit different)

3 Likes

thanks to you it worked. I’ve been trying to get this to work for a week…

You pointed me in the right direction. I didn’t fully understand your code but I went to Eventedmind and watched some videos about iron router again and worked everything out.

This is the product which links to the productPage

<div class="product-title"> 
    {{#linkTo route='product.show' data-reveal-id="product-modal"}} 
          {{title}} 
    {{/linkTo}} 
</div>

This some of the router code

Router.route('product/:_id', function() {
	this.render('productPage',
	{
		data: function() {
			return Products.findOne(this.params._id);
		},
		to: 'modalContent'
	});
},{
	name: 'product.show'
});

Thanks again

No prob! Glad I could help :beers:

hi there it would be really good if you could expand on your notes some more here, to show your working solution. I am trying to follow this thread to get a similar scenario working for me, but I just can’t stitch a working solution together based on all the comments. All that happens for me at the moment is when I click the link to reveal the modal, the page navigates away to a new (blank) page and I get a blaze error in the console window. many thanks

Hi guys, I have got this working by specifying the second parameter for the modal although on another model on the same page the data context is not set.

What can i do for multiple modals in the same template? Why is the data not available when passed as a second argument?