Skip to content

Instantly share code, notes, and snippets.

@Logiraptor
Last active March 8, 2016 13:28
Show Gist options
  • Save Logiraptor/1c8526db6018c7786897 to your computer and use it in GitHub Desktop.
Save Logiraptor/1c8526db6018c7786897 to your computer and use it in GitHub Desktop.
// Ignore these imports
import React from 'react';
import ReactDOM from 'react-dom';
// Usage:
// 1. render a Popup anywhere in the app.
// 2. pass trigger and content props
// - trigger is the clickable element which shows/hides the content
// 3. register a global onClick listener **once** that calls Popup.hidePopups.
// - Navbar.js.jsx is a reasonable place for this.
// To test this, we'll need to do a few things:
//
// render Popup, call toggleContent
// expect props.content to be rendered inside props.trigger only when appropriate
//
// click on the rendered trigger element and expect toggleContent to have been called
//
// call Popup.hidePopups and expect component.hideContent to have been called.
var Popup = React.createClass({
// Here, we keep track of all rendered popups in a static array
// This is so we can hide them all when an outside click occurs.
statics: {
popups: [],
hidePopups: function(event) {
_.map(Popup.popups, function(popup) {
popup.hideContent(event);
});
}
},
propTypes: {
trigger: React.PropTypes.element.isRequired,
content: React.PropTypes.node.isRequired
},
getInitialState: function() {
return {
status: false
}
},
componentDidMount: function() {
Popup.popups.push(this);
},
componentWillUnmount: function() {
Popup.popups = _.without(Popup.popups, this);
},
hideContent: function(event) {
this.setState({
status: false
});
},
toggleContent: function(event) {
event.stopPropagation();
this.setState({
status: !this.state.status
})
},
render: function() {
var triggerChildren = [this.props.trigger.props.children];
if (this.state.status) {
triggerChildren = triggerChildren.concat([this.props.content]);
}
return React.cloneElement(
this.props.trigger,
{
onClick: this.toggleContent
},
triggerChildren
);
}
})
var App = React.createClass({
render: function() {
var trigger = (<span>Click Me</span>);
var content = (<div>Popup!</div>);
return (
<span onClick={Popup.hidePopups}>
Hello, World!
<Popup trigger={trigger} content={content}/>
</span>
);
}
});
ReactDOM.render(<App/>, document.getElementById('app'));
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment