2014-12-02 15:57:18 +01:00
|
|
|
/*eslint-env browser*/
|
2014-12-30 10:05:27 +01:00
|
|
|
define(['react', 'jquery', 'lodash', './playground-fiddle.rt', './playground.rt'], function (React, $, _, pgFiddleTemplate, playgroundTemplate) {
|
2014-12-10 13:14:22 +01:00
|
|
|
'use strict';
|
2014-12-07 14:12:50 +01:00
|
|
|
function emptyFunc() {
|
|
|
|
return null;
|
2014-12-02 15:57:18 +01:00
|
|
|
}
|
|
|
|
|
2014-12-30 09:42:31 +01:00
|
|
|
/**
|
|
|
|
* @param {string} html
|
|
|
|
* @param editor
|
|
|
|
* @param {string} name
|
|
|
|
* @return {string}
|
|
|
|
*/
|
|
|
|
function generateTemplateSource(html, editor, name) {
|
2014-12-07 14:12:50 +01:00
|
|
|
var code = null;
|
2014-12-02 15:57:18 +01:00
|
|
|
try {
|
2014-12-30 09:42:31 +01:00
|
|
|
code = window.reactTemplates.convertTemplateToReact(html.trim().replace(/\r/g, ''), {modules: 'none', name: name});
|
2014-12-25 11:13:07 +01:00
|
|
|
clearMessage(editor);
|
2014-12-02 15:57:18 +01:00
|
|
|
} catch (e) {
|
2014-12-10 13:14:22 +01:00
|
|
|
var msg;
|
2014-12-09 14:31:25 +01:00
|
|
|
if (e.name === 'RTCodeError') {
|
|
|
|
//index: -1 line: -1 message: "Document should have a root element" name: "RTCodeError"
|
2014-12-10 13:14:22 +01:00
|
|
|
msg = e.message + ', line: ' + e.line;
|
2014-12-30 09:42:31 +01:00
|
|
|
editor.annotate({line: e.line, message: e.message, index: e.index});
|
2014-12-10 13:14:22 +01:00
|
|
|
} else {
|
|
|
|
msg = e.message;
|
2014-12-30 09:42:31 +01:00
|
|
|
editor.annotate({line: 1, message: e.message});
|
2014-12-10 13:14:22 +01:00
|
|
|
}
|
2014-12-30 09:42:31 +01:00
|
|
|
//showMessage(editor, msg);
|
2014-12-10 13:14:22 +01:00
|
|
|
console.log(e);
|
2014-12-02 15:57:18 +01:00
|
|
|
}
|
2014-12-07 14:12:50 +01:00
|
|
|
return code;
|
|
|
|
}
|
2014-12-02 15:57:18 +01:00
|
|
|
|
2014-12-25 11:13:07 +01:00
|
|
|
function showMessage(editor, msg) {
|
|
|
|
if (editor && editor.showMessage) {
|
2014-12-30 09:42:31 +01:00
|
|
|
//editor.showMessage(msg);
|
|
|
|
editor.annotate({line: 1, message: msg});
|
|
|
|
//calcSize();
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
function calcSize() {
|
|
|
|
if (window.calcSize) {
|
|
|
|
window.calcSize();
|
2014-12-25 11:13:07 +01:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
function clearMessage(editor) {
|
|
|
|
if (editor && editor.clearMessage) {
|
2014-12-30 09:42:31 +01:00
|
|
|
//editor.clearMessage();
|
|
|
|
editor.clearAnnotations();
|
|
|
|
//calcSize();
|
2014-12-25 11:13:07 +01:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2014-12-07 14:12:50 +01:00
|
|
|
function generateTemplateFunction(code) {
|
2014-12-02 15:57:18 +01:00
|
|
|
try {
|
2014-12-07 14:12:50 +01:00
|
|
|
var defineMap = {'react/addons': React, lodash: _};
|
|
|
|
var define = function (requirementsNames, content) {
|
|
|
|
var requirements = _.map(requirementsNames, function (reqName) {
|
|
|
|
return defineMap[reqName];
|
|
|
|
});
|
|
|
|
return content.apply(this, requirements);
|
|
|
|
};
|
|
|
|
/*eslint no-eval:0*/
|
|
|
|
var res = eval(code);
|
|
|
|
return res;
|
2014-12-02 15:57:18 +01:00
|
|
|
} catch (e) {
|
2014-12-10 13:14:22 +01:00
|
|
|
console.log(e);
|
2014-12-07 14:12:50 +01:00
|
|
|
return emptyFunc;
|
2014-12-02 15:57:18 +01:00
|
|
|
}
|
2014-12-07 14:12:50 +01:00
|
|
|
}
|
|
|
|
|
|
|
|
function generateRenderFunc(renderFunc) {
|
|
|
|
return function () {
|
|
|
|
var res = null;
|
|
|
|
try {
|
|
|
|
res = renderFunc.apply(this);
|
|
|
|
} catch (e) {
|
|
|
|
res = React.DOM.div.apply(this, [{style: {color: 'red'}}, 'Exception:' + e.message]);
|
|
|
|
}
|
|
|
|
return React.DOM.div.apply(this, _.flatten([
|
|
|
|
{key: 'result'},
|
|
|
|
res
|
|
|
|
]));
|
2014-12-02 15:57:18 +01:00
|
|
|
};
|
2014-12-07 14:12:50 +01:00
|
|
|
}
|
|
|
|
|
2014-12-08 11:45:32 +01:00
|
|
|
var templateHTML = '<div></div>';
|
2014-12-30 09:42:31 +01:00
|
|
|
var templateProps = 'var template = React.createClass({\n' +
|
|
|
|
' render: function () {\n' +
|
|
|
|
' return templateRT.apply(this);\n' +
|
|
|
|
' }\n' +
|
|
|
|
'});';
|
2014-12-07 14:12:50 +01:00
|
|
|
|
2014-12-30 09:42:31 +01:00
|
|
|
var selfCleaningTimeout = {
|
|
|
|
componentDidUpdate: function() {
|
|
|
|
clearTimeout(this.timeoutID);
|
|
|
|
},
|
|
|
|
setTimeout: function() {
|
|
|
|
console.log('setTimeout');
|
|
|
|
clearTimeout(this.timeoutID);
|
|
|
|
this.timeoutID = setTimeout.apply(null, arguments);
|
|
|
|
}
|
|
|
|
};
|
2014-12-07 14:12:50 +01:00
|
|
|
|
2014-12-30 09:42:31 +01:00
|
|
|
var Playground = React.createClass({
|
2014-12-07 14:12:50 +01:00
|
|
|
displayName: 'Playground',
|
|
|
|
mixins: [React.addons.LinkedStateMixin],
|
|
|
|
propTypes: {
|
2014-12-25 11:13:07 +01:00
|
|
|
direction: React.PropTypes.oneOf(['horizontal', 'vertical']),
|
2014-12-07 14:12:50 +01:00
|
|
|
codeVisible: React.PropTypes.bool,
|
|
|
|
fiddle: React.PropTypes.bool
|
|
|
|
},
|
2014-12-30 09:42:31 +01:00
|
|
|
templateSource: '',
|
|
|
|
validHTML: true,
|
|
|
|
validProps: true,
|
|
|
|
setTimeout: function() {
|
|
|
|
console.log('setTimeout');
|
|
|
|
clearTimeout(this.timeoutID);
|
|
|
|
this.timeoutID = setTimeout.apply(null, arguments);
|
|
|
|
},
|
2014-12-07 14:12:50 +01:00
|
|
|
getDefaultProps: function () {
|
|
|
|
return {
|
|
|
|
direction: 'horizontal', //vertical
|
|
|
|
codeVisible: true,
|
|
|
|
fiddle: false
|
|
|
|
};
|
|
|
|
},
|
2014-12-30 09:42:31 +01:00
|
|
|
getLayoutClass: function () {
|
|
|
|
return (this.props.direction === 'horizontal' && 'horizontal') || 'vertical';
|
|
|
|
},
|
|
|
|
//executeCode: function() {
|
|
|
|
// var mountNode = this.refs.mount.getDOMNode();
|
|
|
|
//
|
|
|
|
// try {
|
|
|
|
// React.unmountComponentAtNode(mountNode);
|
|
|
|
// } catch (e) { }
|
|
|
|
//
|
|
|
|
// try {
|
|
|
|
// var compiledCode = this.compileCode();
|
|
|
|
// if (this.props.renderCode) {
|
|
|
|
// React.render(
|
|
|
|
// React.createElement(CodeMirrorEditor, {codeText: compiledCode, readOnly: true}),
|
|
|
|
// mountNode
|
|
|
|
// );
|
|
|
|
// } else {
|
|
|
|
// eval(compiledCode);
|
|
|
|
// }
|
|
|
|
// } catch (err) {
|
|
|
|
// this.setTimeout(function() {
|
|
|
|
// React.render(
|
|
|
|
// React.createElement('div', {className: 'playgroundError'}, err.toString()),
|
|
|
|
// mountNode
|
|
|
|
// );
|
|
|
|
// }, 500);
|
|
|
|
// }
|
|
|
|
//},
|
2014-12-28 16:36:39 +01:00
|
|
|
getTabs: function () {
|
|
|
|
if (this.props.codeVisible) {
|
2014-12-30 09:42:31 +01:00
|
|
|
return [['templateHTML', 'Template'], ['templateProps', 'Class'], ['templateSource', 'Generated code']];
|
2014-12-28 16:36:39 +01:00
|
|
|
} else {
|
2014-12-30 09:42:31 +01:00
|
|
|
return [['templateHTML', 'Template'], ['templateSource', 'Generated code']];
|
2014-12-28 16:36:39 +01:00
|
|
|
}
|
|
|
|
},
|
2014-12-07 14:12:50 +01:00
|
|
|
updateSample: function (state) {
|
2014-12-30 09:42:31 +01:00
|
|
|
var mountNode = this.refs.mount.getDOMNode();
|
|
|
|
|
|
|
|
//try {
|
|
|
|
// React.unmountComponentAtNode(mountNode);
|
|
|
|
//} catch (e) { }
|
|
|
|
|
|
|
|
this.generateCode();
|
|
|
|
//this.sampleFunc = generateTemplateFunction(this.templateSource);
|
|
|
|
//this.validHTML = this.sampleFunc !== emptyFunc;
|
|
|
|
this.validHTML = true;
|
2014-12-07 14:12:50 +01:00
|
|
|
this.sampleRender = generateRenderFunc(this.sampleFunc);
|
2014-12-30 09:42:31 +01:00
|
|
|
//var classBase = {};
|
2014-12-07 14:12:50 +01:00
|
|
|
try {
|
|
|
|
this.validProps = true;
|
|
|
|
console.log(state.templateProps);
|
2014-12-30 09:42:31 +01:00
|
|
|
//classBase = eval(this.templateSource + '\n' + state.templateProps);
|
|
|
|
//if (!_.isObject(classBase)) {
|
|
|
|
// throw 'failed to eval';
|
|
|
|
//}
|
|
|
|
this.sample = eval('(function () {' + this.templateSource + '\n' + state.templateProps + '\n return React.createElement(' + state.name + ');})()');
|
|
|
|
if (this.sample) {
|
|
|
|
React.render(this.sample, mountNode);
|
2014-12-07 14:12:50 +01:00
|
|
|
}
|
2014-12-25 11:13:07 +01:00
|
|
|
clearMessage(this.refs.editorCode);
|
2014-12-07 14:12:50 +01:00
|
|
|
} catch (e) {
|
2014-12-30 09:42:31 +01:00
|
|
|
//classBase = {};
|
|
|
|
this.rtMessage = e.toString();
|
2014-12-07 14:12:50 +01:00
|
|
|
this.validProps = false;
|
2014-12-30 09:42:31 +01:00
|
|
|
var editor = this.refs.editorCode;
|
|
|
|
this.setTimeout(function() {
|
|
|
|
showMessage(editor, e.message);
|
|
|
|
console.log('setTimeout playgroundError');
|
|
|
|
React.render(
|
|
|
|
React.createElement('div', {className: 'playground-error'}, e.toString()),
|
|
|
|
mountNode
|
|
|
|
);
|
|
|
|
}, 500);
|
2014-12-07 14:12:50 +01:00
|
|
|
}
|
2014-12-30 09:42:31 +01:00
|
|
|
//classBase.render = this.sampleRender;
|
|
|
|
//this.sample = React.createFactory(React.createClass(classBase));
|
2014-12-07 14:12:50 +01:00
|
|
|
},
|
2014-12-08 13:48:12 +01:00
|
|
|
clear: function () {
|
|
|
|
//console.log('clear');
|
|
|
|
var currentState = {
|
|
|
|
templateHTML: templateHTML,
|
|
|
|
templateProps: templateProps
|
|
|
|
};
|
|
|
|
//this.updateSample(currentState);
|
|
|
|
this.setState(currentState);
|
|
|
|
},
|
2014-12-07 14:12:50 +01:00
|
|
|
getInitialState: function () {
|
|
|
|
var currentState = {
|
|
|
|
templateHTML: this.props.templateHTML || templateHTML,
|
2014-12-28 16:36:39 +01:00
|
|
|
templateProps: this.props.templateProps || templateProps,
|
2014-12-30 09:42:31 +01:00
|
|
|
name: this.props.name || 'template',
|
2014-12-28 16:36:39 +01:00
|
|
|
currentTab: 'templateHTML'
|
2014-12-07 14:12:50 +01:00
|
|
|
};
|
2014-12-30 09:42:31 +01:00
|
|
|
//this.updateSample(currentState);
|
2014-12-07 14:12:50 +01:00
|
|
|
return currentState;
|
|
|
|
},
|
2014-12-30 09:42:31 +01:00
|
|
|
componentDidMount: function() {
|
|
|
|
if (this.props.fiddle) {
|
|
|
|
window.addEventListener('resize', this.calcSize);
|
|
|
|
this.calcSize();
|
|
|
|
}
|
|
|
|
this.updateSample(this.state);
|
|
|
|
},
|
|
|
|
|
|
|
|
componentWillUnmount: function(){
|
|
|
|
window.removeEventListener('resize', this.calcSize);
|
|
|
|
},
|
|
|
|
|
|
|
|
calcSize: function() {
|
|
|
|
var contentHeight = $(window).height() - $('#header').height();
|
|
|
|
var height = contentHeight / 2 - 10;
|
|
|
|
|
|
|
|
$('.code-area').each(function (i, k) {
|
|
|
|
$(this).height(height);
|
|
|
|
console.log($(this).height());
|
|
|
|
});
|
|
|
|
this.refs.editorCode.editor.refresh();
|
|
|
|
this.refs.editorRT.editor.refresh();
|
|
|
|
this.refs.editorGenerated.editor.refresh();
|
|
|
|
},
|
2014-12-07 14:12:50 +01:00
|
|
|
componentWillUpdate: function (nextProps, nextState) {
|
|
|
|
if (nextState.templateHTML !== this.state.templateHTML || nextState.templateProps !== this.state.templateProps) {
|
|
|
|
this.updateSample(nextState);
|
|
|
|
}
|
|
|
|
},
|
|
|
|
render: function () {
|
2014-12-30 09:42:31 +01:00
|
|
|
this.generateCode();
|
2014-12-07 14:12:50 +01:00
|
|
|
var template = this.props.fiddle ? pgFiddleTemplate : playgroundTemplate;
|
|
|
|
return template.apply(this);
|
2014-12-30 09:42:31 +01:00
|
|
|
},
|
|
|
|
generateCode: function () {
|
|
|
|
this.templateSource = generateTemplateSource(this.state.templateHTML, this.refs.editorRT, window.reactTemplates.normalizeName(this.state.name) + 'RT');
|
2014-12-02 15:57:18 +01:00
|
|
|
}
|
2014-12-07 14:12:50 +01:00
|
|
|
});
|
2014-12-02 15:57:18 +01:00
|
|
|
|
2014-12-07 14:12:50 +01:00
|
|
|
return Playground;
|
2014-12-02 15:57:18 +01:00
|
|
|
});
|