mirror of
https://github.com/naturalcrit/homebrewery.git
synced 2026-01-09 00:42:47 +00:00
it works
This commit is contained in:
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
|
Before Width: | Height: | Size: 337 KiB |
Binary file not shown.
|
Before Width: | Height: | Size: 5.4 MiB |
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
|
Before Width: | Height: | Size: 9.4 KiB |
Binary file not shown.
|
Before Width: | Height: | Size: 14 KiB |
@@ -1,105 +0,0 @@
|
||||
var React = require('react');
|
||||
var _ = require('lodash');
|
||||
var cx = require('classnames');
|
||||
|
||||
var Snippets = require('./snippets.js');
|
||||
|
||||
|
||||
var Icons = [
|
||||
{
|
||||
icon : 'fa-book',
|
||||
snippet : Snippets.intro,
|
||||
tooltip : 'Intro'
|
||||
},
|
||||
{
|
||||
icon : 'fa-magic',
|
||||
snippet : Snippets.spell,
|
||||
tooltip : 'Spell'
|
||||
},
|
||||
{
|
||||
icon : 'fa-bookmark',
|
||||
snippet : Snippets.classFeatures,
|
||||
tooltip : 'Class Intro'
|
||||
},
|
||||
{
|
||||
icon : 'fa-trophy',
|
||||
snippet : Snippets.destroyUndead,
|
||||
tooltip : 'Class Feature'
|
||||
},
|
||||
{
|
||||
icon : 'fa-sticky-note',
|
||||
snippet : Snippets.note,
|
||||
tooltip : 'Note'
|
||||
},
|
||||
{
|
||||
icon : 'fa-bug',
|
||||
snippet : Snippets.statBlock,
|
||||
tooltip : 'Monster Stat Block'
|
||||
},
|
||||
{
|
||||
icon : 'fa-table',
|
||||
snippet : "",
|
||||
tooltip : "Class Table"
|
||||
},
|
||||
{
|
||||
icon : 'fa-columns',
|
||||
snippet : "```\n```\n\n",
|
||||
tooltip : "Column Break"
|
||||
},
|
||||
{
|
||||
icon : 'fa-file-text',
|
||||
snippet : "\\pagen\n\n",
|
||||
tooltip : "New Page"
|
||||
},
|
||||
|
||||
|
||||
]
|
||||
|
||||
var Editor = React.createClass({
|
||||
getDefaultProps: function() {
|
||||
return {
|
||||
text : "",
|
||||
onChange : function(){}
|
||||
};
|
||||
},
|
||||
|
||||
handleTextChange : function(e){
|
||||
this.props.onChange(e.target.value);
|
||||
},
|
||||
|
||||
iconClick : function(snippet){
|
||||
var curPos = this.refs.textarea.selectionStart;
|
||||
this.props.onChange(this.props.text.slice(0, curPos) +
|
||||
snippet +
|
||||
this.props.text.slice(curPos + 1));
|
||||
},
|
||||
|
||||
renderTemplateIcons : function(){
|
||||
return _.map(Icons, (t) => {
|
||||
return <div className='icon' key={t.icon}
|
||||
onClick={this.iconClick.bind(this, t.snippet)}
|
||||
data-tooltip={t.tooltip}>
|
||||
<i className={'fa ' + t.icon} />
|
||||
</div>;
|
||||
})
|
||||
},
|
||||
|
||||
render : function(){
|
||||
var self = this;
|
||||
return(
|
||||
<div className='editor'>
|
||||
<div className='textIcons'>
|
||||
{this.renderTemplateIcons()}
|
||||
|
||||
</div>
|
||||
<textarea
|
||||
ref='textarea'
|
||||
value={this.props.text}
|
||||
onChange={this.handleTextChange} />
|
||||
</div>
|
||||
);
|
||||
}
|
||||
});
|
||||
|
||||
module.exports = Editor;
|
||||
|
||||
@@ -1,32 +0,0 @@
|
||||
.editor{
|
||||
position : fixed;
|
||||
height : 100%;
|
||||
.textIcons{
|
||||
display: inline-block;
|
||||
vertical-align: top;
|
||||
.icon{
|
||||
cursor: pointer;
|
||||
width : 30px;
|
||||
height : 30px;
|
||||
text-align: center;
|
||||
line-height: 30px;
|
||||
font-size: 1.5em;
|
||||
|
||||
&:nth-child(8n + 1){ background-color: @blue; }
|
||||
&:nth-child(8n + 2){ background-color: @orange; }
|
||||
&:nth-child(8n + 3){ background-color: @teal; }
|
||||
&:nth-child(8n + 4){ background-color: @red; }
|
||||
&:nth-child(8n + 5){ background-color: @purple; }
|
||||
&:nth-child(8n + 6){ background-color: @silver; }
|
||||
&:nth-child(8n + 7){ background-color: @yellow; }
|
||||
&:nth-child(8n + 8){ background-color: @green; }
|
||||
|
||||
}
|
||||
}
|
||||
textarea{
|
||||
display: inline-block;
|
||||
height : 100%;
|
||||
overflow-y: scroll;
|
||||
width : 300px;
|
||||
}
|
||||
}
|
||||
@@ -1,110 +0,0 @@
|
||||
module.exports = {
|
||||
|
||||
intro : [
|
||||
'# Welcome to HomeBrew',
|
||||
'This tool you to effortless make and edit in real time D&D style ideas',
|
||||
'\nIt uses **markdown-syntax** anda well-designed style sheet to create stuff.',
|
||||
'As you edit text on the left it will live update on the right.',
|
||||
"Any changes you make will auto-saved to your browser as well.",
|
||||
"",
|
||||
"There's a few premade templates for common things in the PHB.",
|
||||
"Just hit the icons to inject the template wherever your cursor was in the text box. \n***Have fun.***"
|
||||
|
||||
].join('\n'),
|
||||
|
||||
|
||||
classFeatures : [
|
||||
"## Class Features",
|
||||
"As a paladin, you gain the following class features.",
|
||||
"",
|
||||
"#### Hit Points",
|
||||
"___",
|
||||
"- **Hit Dice:** 1d10 per paladin level",
|
||||
"- **Hit Points at 1st Level:** 10 + your Constitution modifier",
|
||||
"- **Hit Points at Higher Levels:** 1d10 (or 6) + your Constituion modifier per paladin level after 1st",
|
||||
"",
|
||||
"#### Proficiencies",
|
||||
"___",
|
||||
"- **Armor:** All armor, Shields",
|
||||
"- **Weapons:** Simple Weapons, martial weapons",
|
||||
"- **Tools:** None <br>",
|
||||
"___",
|
||||
"- **Saving Throws:** Wisdom, Charisma",
|
||||
"- **Skills:** Choose two from Athletics, Insight, Intimidation, Medicine, Persuasion, and Religion",
|
||||
"",
|
||||
"#### Equipment",
|
||||
"You start with the following equipment, in addition to the equipment granted by your background:",
|
||||
"",
|
||||
"- *(a)* a martial weapon and a shield or *(b)* two martial weapons",
|
||||
"- *(a)* five javelins or *(b)* any simple melee weapon",
|
||||
"- Chain mail and a holy symbol",
|
||||
].join('\n'),
|
||||
|
||||
spell : [
|
||||
"#### Continual Flame",
|
||||
"*2nd-level evocation*",
|
||||
"___",
|
||||
"- **Casting Time:** 1 action",
|
||||
"- **Range:** Touch",
|
||||
"- **Components:** V, S, M (ruby dust worth 50gp, which the spell consumes)",
|
||||
"- **Duration:** Until dispelled",
|
||||
"",
|
||||
"A flame, equivalent in brightness to a torch, springs from from an object that you touch. ",
|
||||
"The effect look like a regular flame, but it creates no heat and doesn't use oxygen. ",
|
||||
"A *continual flame* can be covered or hidden but not smothered or quenched."
|
||||
].join('\n'),
|
||||
|
||||
destroyUndead : [
|
||||
"### Destroy Undead",
|
||||
"Starting at 5th level, when an undead fails its saving throw against your Turn Undead feature,",
|
||||
"the creature is instantly destroyed if its challange rating is at or below a certain threshold,",
|
||||
"as shown in the Destroy Undead table.",
|
||||
"",
|
||||
"##### Destroy Undead",
|
||||
"| Cleric Level | Destroys Undead of CR... |",
|
||||
"|:----:|:-------------|",
|
||||
"| 5th | 1/2 or lower |",
|
||||
"| 8th | 1 or lower |",
|
||||
"| 11th | 2 or lower |",
|
||||
"| 14th | 3 or lower |",
|
||||
"| 17th | 4 or lower |\n\n",
|
||||
].join('\n'),
|
||||
|
||||
note : [
|
||||
"> ##### Variant: Playing on a Grid",
|
||||
"> If you play out a combat using a square grid and miniatures or other tokens, follow these rules",
|
||||
">",
|
||||
"> ***Squares.*** Each square on the grid represents 5 feet.",
|
||||
">",
|
||||
"> ***Speed.*** Rather than moving foot by foot, move square by square on the grid. This means you use your speed in 5-foot segments.",
|
||||
].join('\n'),
|
||||
|
||||
statBlock :[
|
||||
"___",
|
||||
"> ## Warhorse",
|
||||
">*Large beast, unaligned*",
|
||||
"> ___",
|
||||
"> - **Armor Class** 18 (natural armor)",
|
||||
"> - **Hit Points** 33 (6d8 + 6)",
|
||||
"> - **Speed** 25ft",
|
||||
">___",
|
||||
">|STR|DEX|CON|INT|WIS|CHA|",
|
||||
">|:---:|:---:|:---:|:---:|:---:|:---:|:---:|",
|
||||
">|18 (+4)|18 (+4)|18 (+4)|18 (+4)|18 (+4)|18 (+4)|",
|
||||
">___",
|
||||
"> - **Damage Immunities** poison, psychic",
|
||||
"> - **Condition Immunities** blinded, charmed, deafened, exhaustion, frightened, paralyzed, petrified, poisoned",
|
||||
"> - **Languages** None",
|
||||
"> - **Challenge** 1 (200 XP)",
|
||||
"> ___",
|
||||
"> ***Pack Tactics.*** These guys work together. Like super well, you don't even know.",
|
||||
">",
|
||||
"> ***False Appearance. *** While the armor reamin motionless, it is indistinguishable from a normal suit of armor.",
|
||||
"> ### Actions",
|
||||
"> ***Multiattack.*** The armor makes two two melee attacks.",
|
||||
">",
|
||||
"> ***Slam.*** *Melee Weapon Attack:* +4 to hit, reach 5ft., one target. *Hit* 5 (1d6 + 2) ",
|
||||
].join('\n')
|
||||
|
||||
|
||||
}
|
||||
@@ -1,53 +0,0 @@
|
||||
var React = require('react');
|
||||
var _ = require('lodash');
|
||||
var cx = require('classnames');
|
||||
|
||||
var PHB = require('./phb/phb.jsx');
|
||||
var Editor = require('./editor/editor.jsx');
|
||||
|
||||
|
||||
var Snippets = require('./editor/snippets');
|
||||
|
||||
var KEY = 'naturalCrit-homebrew';
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
var Homebrew = React.createClass({
|
||||
|
||||
getInitialState: function() {
|
||||
return {
|
||||
text : Snippets.intro
|
||||
};
|
||||
},
|
||||
|
||||
componentDidMount: function() {
|
||||
var storage = localStorage.getItem(KEY);
|
||||
if(storage){
|
||||
this.setState({
|
||||
text : storage
|
||||
})
|
||||
}
|
||||
},
|
||||
|
||||
handleTextChange : function(text){
|
||||
this.setState({
|
||||
text : text
|
||||
});
|
||||
|
||||
localStorage.setItem(KEY, text);
|
||||
},
|
||||
|
||||
render : function(){
|
||||
var self = this;
|
||||
return(
|
||||
<div className='homebrew'>
|
||||
<Editor text={this.state.text} onChange={this.handleTextChange} />
|
||||
<PHB text={this.state.text} />
|
||||
</div>
|
||||
);
|
||||
}
|
||||
});
|
||||
|
||||
module.exports = Homebrew;
|
||||
@@ -1,6 +0,0 @@
|
||||
|
||||
|
||||
.homebrew{
|
||||
background-color: @steel;
|
||||
height : 100%;
|
||||
}
|
||||
@@ -1,28 +0,0 @@
|
||||
var React = require('react');
|
||||
var _ = require('lodash');
|
||||
var cx = require('classnames');
|
||||
|
||||
var Markdown = require('marked');
|
||||
|
||||
var Phb = React.createClass({
|
||||
getDefaultProps: function() {
|
||||
return {
|
||||
text : ""
|
||||
};
|
||||
},
|
||||
|
||||
renderPages : function(){
|
||||
return _.map(this.props.text.split('\\page'), (pageText, index) => {
|
||||
return <div className='phb' dangerouslySetInnerHTML={{__html:Markdown(pageText)}} key={index} />
|
||||
})
|
||||
},
|
||||
|
||||
render : function(){
|
||||
var self = this;
|
||||
return <div className="pbhPages">
|
||||
{this.renderPages()}
|
||||
</div>;
|
||||
}
|
||||
});
|
||||
|
||||
module.exports = Phb;
|
||||
@@ -1,323 +0,0 @@
|
||||
|
||||
.pbhPages{
|
||||
&>.phb{
|
||||
margin-bottom : 40px;
|
||||
margin-left : 400px;
|
||||
}
|
||||
}
|
||||
@font-face {
|
||||
font-family : BookInsanity;
|
||||
src : url('/assets/naturalCrit/homebrew/assets/Bookinsanity.otf');
|
||||
}
|
||||
@font-face {
|
||||
font-family : BookInsanityBold;
|
||||
src : url('/assets/naturalCrit/homebrew/assets/Bookinsanity Bold.otf');
|
||||
}
|
||||
@font-face {
|
||||
font-family : BookInsanityItalic;
|
||||
src : url('/assets/naturalCrit/homebrew/assets/Bookinsanity Italic.otf');
|
||||
}
|
||||
@font-face {
|
||||
font-family : BookInsanityBoldItalic;
|
||||
src : url('/assets/naturalCrit/homebrew/assets/Bookinsanity Bold Italic.otf');
|
||||
}
|
||||
@font-face {
|
||||
font-family : ScalaSans;
|
||||
src : url('/assets/naturalCrit/homebrew/assets/Scaly Sans.otf');
|
||||
}
|
||||
/*
|
||||
@font-face {
|
||||
font-family : ScalaSansBold;
|
||||
src : url('/assets/naturalCrit/homebrew/assets/Scala Sans Bold.ttf');
|
||||
}
|
||||
*/
|
||||
@font-face {
|
||||
font-family : ScalaSansSmallCaps;
|
||||
src : url('/assets/naturalCrit/homebrew/assets/Scala Sans SmallCaps.ttf');
|
||||
}
|
||||
@font-face {
|
||||
font-family : Solbera;
|
||||
src : url('/assets/naturalCrit/homebrew/assets/Solbera Imitation.otf');
|
||||
}
|
||||
@font-face {
|
||||
font-family : MrEaves;
|
||||
src : url('/assets/naturalCrit/homebrew/assets/MrsEavesSmallCaps_Regular.ttf') format('truetype'),
|
||||
url('/assets/naturalCrit/homebrew/assets/Mr Eaves Small Caps.otf') format('otf');
|
||||
}
|
||||
.phb{
|
||||
@background : #f2ece4;
|
||||
@green : #e0e5c1;
|
||||
@headerUnderline : #c9ad6a;
|
||||
@horizontalRule : #9c2b1b;
|
||||
@header : #58180D;
|
||||
box-sizing : border-box;
|
||||
height : 27.5cm;
|
||||
width : 21cm;
|
||||
padding : 1.0cm 1.7cm;
|
||||
column-count : 2;
|
||||
column-fill : auto;
|
||||
column-gap : 1cm;
|
||||
column-width : 8cm;
|
||||
background-color: #EEE5CE;
|
||||
background-image : url('/assets/naturalCrit/homebrew/assets/PHB-background.png');
|
||||
-webkit-column-count : 2;
|
||||
-moz-column-count : 2;
|
||||
-webkit-column-width : 8cm;
|
||||
-moz-column-width : 8cm;
|
||||
-webkit-column-gap : 1cm;
|
||||
text-rendering : optimizeLegibility;
|
||||
|
||||
overflow: hidden;
|
||||
|
||||
|
||||
p,ul,blockquote{
|
||||
-webkit-column-break-inside : avoid;
|
||||
-moz-column-break-inside : avoid;
|
||||
-o-column-break-inside : avoid;
|
||||
-ms-column-break-inside : avoid;
|
||||
column-break-inside : avoid;
|
||||
}
|
||||
|
||||
p,ul{
|
||||
strong{
|
||||
font-family : BookInsanityBold;
|
||||
em{
|
||||
font-family : BookInsanityBoldItalic;
|
||||
}
|
||||
}
|
||||
em{
|
||||
font-family : BookInsanityItalic;
|
||||
}
|
||||
}
|
||||
p {
|
||||
padding-bottom : 1em;
|
||||
font-family : BookInsanity;
|
||||
font-size : 9pt;
|
||||
line-height : 1.3em;
|
||||
&+p{
|
||||
margin-top : -1em;
|
||||
text-indent : 1em;
|
||||
}
|
||||
}
|
||||
ul{
|
||||
margin-bottom : 1em;
|
||||
font-family : BookInsanity;
|
||||
font-size : 9pt;
|
||||
line-height : 1.3em;
|
||||
list-style-position : inside;
|
||||
list-style-type : disc;
|
||||
}
|
||||
|
||||
|
||||
//Full Spell casting table
|
||||
hr+table{
|
||||
-webkit-column-span : all;
|
||||
column-span : all;
|
||||
background-color: white;
|
||||
}
|
||||
table{
|
||||
width : 100%;
|
||||
margin-bottom : 1em;
|
||||
font-family : ScalaSans;
|
||||
font-size : 10pt;
|
||||
thead{
|
||||
font-weight : 800;
|
||||
th{
|
||||
padding-bottom : 0.3em;
|
||||
}
|
||||
}
|
||||
tr{
|
||||
td{
|
||||
padding : 0.2em 0em;
|
||||
}
|
||||
&:nth-child(even){
|
||||
background : @green;
|
||||
}
|
||||
}
|
||||
}
|
||||
hr{
|
||||
visibility: hidden;
|
||||
//border : none;
|
||||
margin: 0px;
|
||||
}
|
||||
|
||||
//Fancy List of things
|
||||
hr+ul{
|
||||
list-style-type: none;
|
||||
text-indent: -1em;
|
||||
padding-left: 1em;
|
||||
|
||||
//margin-top: -0.5em;
|
||||
margin-bottom: 0.5em;
|
||||
}
|
||||
|
||||
//Column Break
|
||||
pre{
|
||||
visibility: hidden;
|
||||
-webkit-column-break-after: always;
|
||||
}
|
||||
|
||||
//Monster Stat block
|
||||
hr+blockquote{
|
||||
position : relative;
|
||||
background-color: #FDF1DC;
|
||||
border : none;
|
||||
|
||||
h2{
|
||||
margin-bottom: 0px;
|
||||
&+p{
|
||||
padding-bottom: 0px;
|
||||
}
|
||||
}
|
||||
h3{
|
||||
font-family: ScalaSans;
|
||||
font-weight: 400;
|
||||
border-bottom: 1px solid @header;
|
||||
}
|
||||
|
||||
ul{
|
||||
list-style-type: none;
|
||||
font-family: ScalaSans;
|
||||
color : @header;
|
||||
font-size: 10pt;
|
||||
text-indent: -1em;
|
||||
padding-left: 1em;
|
||||
strong{
|
||||
font-family: ScalaSans;
|
||||
font-weight: 800;
|
||||
}
|
||||
}
|
||||
|
||||
hr+table{
|
||||
-webkit-column-span : 1;
|
||||
column-span : 1;
|
||||
background-color: transparent;
|
||||
}
|
||||
table{
|
||||
color : @header;
|
||||
}
|
||||
|
||||
p+p{
|
||||
margin-top : 0em;
|
||||
text-indent : 0em;
|
||||
padding-bottom: 0.5em;
|
||||
}
|
||||
|
||||
|
||||
|
||||
//Maybe move this to be built in
|
||||
hr{
|
||||
visibility: visible;
|
||||
margin: 8px 0px;
|
||||
|
||||
border-color : transparent;
|
||||
position: relative;
|
||||
@height : 3px;
|
||||
&:after, &:before{
|
||||
content : "";
|
||||
position: absolute;
|
||||
width: 100%;
|
||||
height: @height;
|
||||
left: 0px;
|
||||
}
|
||||
&:before{
|
||||
top : -@height;
|
||||
background: linear-gradient(to right top, @horizontalRule 40%, transparent 50%)
|
||||
}
|
||||
&:after{
|
||||
top: 0px;
|
||||
background: linear-gradient(to right bottom, @horizontalRule 40%, transparent 50%)
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
//Borders
|
||||
&:after, &:before{
|
||||
content : "";
|
||||
position: absolute;
|
||||
background-color : #E69A28;
|
||||
border: 1px solid black;
|
||||
height : 4px;
|
||||
width : 100%;
|
||||
padding : 0px 3px;
|
||||
}
|
||||
&:before{
|
||||
top : 0px;
|
||||
left : -3px;
|
||||
}
|
||||
&:after{
|
||||
bottom : 0px;
|
||||
left : -3px;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
//Note
|
||||
blockquote{
|
||||
box-sizing : border-box;
|
||||
margin-bottom : 1em;
|
||||
padding : 5px 10px;
|
||||
background-color : @green;
|
||||
font-family : ScalaSans;
|
||||
border-top : 2px black solid;
|
||||
border-bottom : 2px black solid;
|
||||
box-shadow : 1px 4px 14px #888;
|
||||
p{
|
||||
font-family : ScalaSans;
|
||||
font-size : 10pt;
|
||||
line-height : 1.1em;
|
||||
em{
|
||||
font-family : ScalaSans;
|
||||
font-style : italic;
|
||||
}
|
||||
strong{
|
||||
font-weight : 800;
|
||||
font-family : ScalaSans;
|
||||
em{
|
||||
font-style : italic;
|
||||
font-weight : 800;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
pre{
|
||||
}
|
||||
h1,h2,h3,h4{
|
||||
margin-top : 0.2em;
|
||||
margin-bottom : 0.2em;
|
||||
font-family : MrEaves;
|
||||
font-weight : 800;
|
||||
color : @header;
|
||||
}
|
||||
h1{
|
||||
column-span : all;
|
||||
font-size : 28pt;
|
||||
-webkit-column-span : all;
|
||||
&+p{
|
||||
&::first-letter{
|
||||
float : left;
|
||||
margin-top : 20px;
|
||||
margin-bottom : 10px;
|
||||
font-family : Solbera;
|
||||
font-size : 4.5em;
|
||||
}
|
||||
}
|
||||
}
|
||||
h2{
|
||||
font-size : 20pt;
|
||||
}
|
||||
h3{
|
||||
font-size : 15pt;
|
||||
border-bottom : 2px solid @headerUnderline;
|
||||
}
|
||||
h4{
|
||||
margin-bottom : 0.00em;
|
||||
font-size : 12pt;
|
||||
}
|
||||
h5{
|
||||
margin-bottom : 0.2em;
|
||||
font-family : ScalaSansSmallCaps;
|
||||
font-size : 13pt;
|
||||
font-weight : 900;
|
||||
}
|
||||
}
|
||||
@@ -4,13 +4,12 @@ var cx = require('classnames');
|
||||
var CreateRouter = require('pico-router').createRouter;
|
||||
|
||||
var CombatManager = require('./combatManager/combatManager.jsx');
|
||||
var Homebrew = require('./homebrew/homebrew.jsx');
|
||||
//var Homebrew = require('./homebrew/homebrew.jsx');
|
||||
|
||||
|
||||
var Router = CreateRouter({
|
||||
'/' : <CombatManager />,
|
||||
'/combat' : <CombatManager />,
|
||||
'/homebrew' : <Homebrew />,
|
||||
});
|
||||
|
||||
|
||||
|
||||
Reference in New Issue
Block a user