ember.js - ember-cli how to instantiate a view from within a controller -
i building map single page app. able add or remove objects map retrieved geojson data.
some of these objects presented <div>
these objects therefore not generated form template need instantiated somewhere else. i've been thinking of controller in charge of parsing geojson data.
what have done far?
view
//app/views/map-popup.js import ember 'ember'; export default ember.view.extend({ templatename: "mappopup", classnames: ["map-popup"] });
template
// app/templates/map-popup.js <a class="popup-closer" {{action 'closepopup'}}></a> <div class="popup-header">{{header}}</div> <div class="popup-content">{{body}}</div>
controller
//app/controllers/map-popup.js /** * created alex on 13/04/2015. */ import ember 'ember'; export default ember.objectcontroller.extend({ needs: ['map'], feature: null, header: null, body: null, overlay: null, /** * create overlay anchor popup map. */ createoverlay: function() { return new ol.overlay(/** @type {olx.overlayoptions} */ ({ autopan: true, autopananimation: { duration: 250 } })); }, hide: function() { this.overlay.setposition(undefined); }, addtomap: function() { var map = this.get('controllers.map.map'); this.overlay = this.createoverlay(); map.addoverlay(this.overlay); }, actions: { closepopup: function() { this.hide(); } } });
i thinking in controller:
//app/controllers/map-draw.js //... code ...// var popup = this.get('mappopup').create({feature: this.sketch}); this.get('popups').pushobject(popup); popup.addtomap(); //... more code ...//
i've read lot dependency injection, lookup etc.
- "how dynamically load ember components name in template?"
- programmatically rendering ember components
- dependency injection & service lookup
- how dependency injection in ember ember cli?
the later 1 promising, find bit overkill create initializer inject view in single controller. think it?
edit: trying 4th solution
i added initializer:
//app/initializers/map-popup-service.js export function initialize(container, application ) { application.inject( 'controller:map-draw', 'mappopup', 'view:map-popup' ); } export default { name: 'map-popup-service', initialize: initialize };
when put break point in map-draw controller:
//app/controllers/map-draw.js var popup = this.get('mappopup').create({feature: this.sketch});
i can popup (debugger):
i can create element:
but if try view controller, has not been injected:
i tried call get('mappopup') several time in ma-draw controller same view instance (same id)
i'll try see in render helper how controller injection works...
edit: input reading source code of ember.js
in file ember.js/packages/ember-application/lib/system/application.js
```javascript app.inject(<full_name or type>, <property name>, <full_name>) app.inject('route', 'source', 'source:main') app.inject('route:application', 'email', 'model:email') ``` important note injections can performed on classes instantiated ember itself. instantiating class directly (via `create` or `new`) bypasses dependency injection system. **note:** ember-data instantiates models in unique manner, , consequently injections onto models (or models) not work expected. injections on models can enabled setting `ember.model_factory_injections` `true`. @method inject @param factorynameortype {string} @param property {string} @param injectionname {string} **/ inject() { this.registry.injection(...arguments); },
that line particularly gave me big hint:
instantiating class directly (via
create
ornew
) bypasses dependency injection system.
i tried import view in controller: import mappopup '../views/map-popup';
and instantiated popup that:
var popup = mappopup.create({feature: this.sketch});
now, new instance of view everytime call create still don't have controller though...
edit: after reading render helper managed set map-popup controller this:
//app/controller/map-draw.js var popup = mappopup.create({feature: this.sketch}); var controller = this.container.lookup('controller:map-popup'); controller.setproperties({ target: this, parentcontroller: }); popup.set('controller', controller);
now, can call function popup controller, kind of don't @ all. love if knowledge of ember.js direct me on before call controller factory different instances of controller...
edit: best solution can come with
after reading this:
if creating views outside context of parentview (this may not recommended, happening) want make sure instantiate view via container itself.
this.container.lookup('view:apple') // provide instance of apple view.
stefanpenner / default_container_deprecation.md
i went in source code , read that:
/** given fullname return corresponding instance. default behaviour lookup return singleton instance. singleton scoped container, allowing multiple containers have own locally scoped singletons. ```javascript var container = new container(); container.register('api:twitter', twitter); var twitter = container.lookup('api:twitter'); twitter instanceof twitter; // => true // default container return singletons var twitter2 = container.lookup('api:twitter'); twitter2 instanceof twitter; // => true twitter === twitter2; //=> true ``` if singletons not wanted optional flag can provided @ lookup. ```javascript var container = new container(); container.register('api:twitter', twitter); var twitter = container.lookup('api:twitter', { singleton: false }); var twitter2 = container.lookup('api:twitter', { singleton: false }); twitter === twitter2; //=> false ``` @method lookup @param {string} fullname @param {object} options @return {any} */ lookup: function(fullname, options)
i ended doing in controller:
//app/contorllers/map-draw.js var popup = _this.container.lookup('view:map-popup', { singleton: false }); var ctrl = _this.container.lookup('controller:map-popup', { singleton: false }); popup.set('controller', ctrl); popup.createelement(); // create div element
the singleton: false important, without popups render same content (the last added)
edit discovered child views , might give today
Comments
Post a Comment