How should component state be manageable by both the component and a controller?

We have a component that has a state of “open” or “closed”, determined by a boolean property open. This state should be changeable by both the internal actions of the component (a button), as well as the controller whose template is using this component.

With the push for data down, actions up, what is the proper pattern for allowing this functionality?

Having the Controller possibly managing this, as illustrated in the example below, seems like the leakage of internal logic of the component to the application, and if this is an addon it places a burden on the consuming app to be aware of such scenarios.

const dummyComponent = Ember.Component.extend({
	open: false,
	layout: '<button {{action "openButtonClicked"}}>Open</button>',

	actions: {
		openButtonClicked() {
			// What happens here?
			// this.set( 'open', true ); ?
			// this.sendAction( 'onOpenClick' ); ?
		}
	}
});

const pageController = Ember.Controller.extend({
	dummyComponentOpen: false,

	actions: {
		dummyComponentOpenClick() {
			this.set( 'dummyComponentOpen', true ); // Is this right?
		}
	}
});

const pageTemplate = '{{dummy-component onOpenClick=dummyComponentOpenClick open=dummyComponentOpen}}';
1 Like