I am a big fan of Jade… err Pug… wtf, but I stopped wishing for react-jade after a while because my render code fits on one page. I went scouring for my largest compoent and found this:
export const CharCreation = ({
player,
onCompleted,
onCancelled,
onChangeName,
onChangeGender,
onSetDifficulty,
onChangeAttribute
}) => (
<div className="ui middle aligned center aligned grid">
<div className="ui one column">
<div className="ui stacked vertical segment">
<div className="ui vertical segment">
<div className="ui labeled fluid input">
<div className="ui label">Character name:</div>
<input
type="text" name="name" placeholder="What word did your mother utter as you came kicking and screaming into this world?"
onChange={(e) => onChangeName(e.target.value)}
value={player.name}
/>
</div>
</div>
<Attributes attributes={player.attributes} onChangeAttribute={onChangeAttribute}/>
<div className="ui vertical segments">
<div className="ui vertical segment">Character Gender</div>
<div className="ui vertical segment">
<Gender gender={player.gender} onChangeGender={onChangeGender}/>
</div>
</div>
<GameDifficulty difficulty={player.difficulty} setDifficulty={onSetDifficulty}/>
<div className="ui button primary" onClick={() => onCompleted(player)}>Ok</div>
<div className="ui button" onClick={onCancelled}>Cancel</div>
<div className="ui button">View Icon</div>
<div className="ui button">Help</div>
</div>
</div>
</div>
);
That’s my biggest component and it’s 37 lines. Whilst I agree that Jade… f**k, Pug, would make it much prettier to the eye, cognitively, it almost makes no difference.
When I was doing blaze pages, the typical html -> jade transformation would be something like 400 lines to 200 lines and that takes alot of the cognitive load off traversing the nested elements, but with react, it’s not a big difference.
Here’s the Attributes component (27 lines):
const Attributes = ({attributes, onChangeAttribute}) => (
<div>
{
_.map(attributes, function (attribute, i) {
let attrName = attribute.name;
return (
<div className="ui segments" key={i}>
<div className="ui segment left aligned">
<h4 className="ui header">{attrName}:</h4>
<div className="ui indicating progress" data-percent={attribute.value}>
<div className={`bar test-${attrName}-bar`} style={{width:attribute.value+'%', minWidth:0}}></div>
<div className={`label test-${attrName}-description`}>{getAttributeDescription(attrName, attribute.value)}</div>
</div>
{attrName !== "Available" ?
buttons(onChangeAttribute, attrName) : ''}
</div>
</div>
)
})
}
</div>
);
Game difficulty (19 lines):
const GameDifficulty = ({
difficulty,
setDifficulty
}) => {
return (
<div className="four ui buttons">
{difficultyLevels.map(function (level, i) {
return (
<div
className={classNames('ui icon button', {active:difficulty === level.level}) }
onClick={() => setDifficulty(level.level)}
key={i}>
<div><i className={level.icon} /></div>
<label>{DifficultyLevel[level.level]}</label>
</div>
);
}, this)}
</div>
)
};
Gender (19 lines):
const Gender = ({
gender,
onChangeGender
}) => (
<div className="equal width column">
<div className="ui large buttons">
<div className={classNames("ui labeled icon button", {active:gender === 'male'})}
onClick={() => {onChangeGender('male');}}>
<i className="large male icon"/>
Male
</div>
<div className="or"></div>
<div className={classNames("ui labeled icon button", {active:gender === 'female'})}
onClick={() => {onChangeGender('female')}}>
<i className="large female icon"/>
Female
</div>
</div>
</div>
);
All together it renders this page:
http://cotwmtor.meteorapp.com/new
Not the prettiest but a fair amount of interactions for 65 lines of render code that I can look at/debug separately.
So I think people haven’t been focused on this because Jade solves a problem of templates and React doesn’t have templates.