Skip to content

Commit

Permalink
add attributes in different way and bump up the version to 1.1.0
Browse files Browse the repository at this point in the history
  • Loading branch information
Filip Vitas committed Aug 26, 2017
1 parent cda37b6 commit 0a207c0
Show file tree
Hide file tree
Showing 9 changed files with 249 additions and 12 deletions.
3 changes: 2 additions & 1 deletion package.json
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"name": "erdesigner",
"version": "1.0.0",
"version": "1.1.0",
"description": "Create beautiful ER diagrams",
"main": "./main.js",
"scripts": {
Expand Down Expand Up @@ -63,6 +63,7 @@
"highlight.js": "^9.12.0",
"lodash": "^4.17.4",
"preact": "^8.2.1",
"preact-portal": "^1.1.2",
"preact-redux": "^2.0.2",
"redux": "^3.7.2",
"uuid": "^3.1.0"
Expand Down
4 changes: 2 additions & 2 deletions rollup.config.js
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,7 @@ export default {
uuid: 'uuid',
lodash: 'lodash',
'preact-redux': 'preact-redux',
linkState: 'linkState'
'preact-portal': 'preact-portal'
},
external: [
'preact',
Expand All @@ -20,7 +20,7 @@ export default {
'uuid',
'lodash',
'preact-redux',
'linkState'
'preact-portal'
],
plugins: [
babel()
Expand Down
2 changes: 1 addition & 1 deletion src/browser/js/components/er-diagram-canvas.js
Original file line number Diff line number Diff line change
Expand Up @@ -107,7 +107,7 @@ class ERDiagramCanvas extends Component {

@bind
removeConnectionDestination(destinationNode) {
if (!!this.state.temporaryConnection.destination && this.state.temporaryConnection.destination.nodeId === destinationNode.nodeId) {
if (this.state.temporaryConnection && this.state.temporaryConnection.destination && this.state.temporaryConnection.destination.nodeId === destinationNode.nodeId) {
this.setState({
temporaryConnection: {
source: this.state.temporaryConnection.source,
Expand Down
10 changes: 5 additions & 5 deletions src/browser/js/components/node-picker.js
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@ import nodeStore from '../redux/store'
import NODE_TYPE from './../constants/node-type'

import Entity from './../components/svg/node-types/node-entity'
import Attribute from './../components/svg/node-types/node-attribute'
// import Attribute from './../components/svg/node-types/node-attribute'
import AssociativeEntity from './../components/svg/node-types/node-associative-entity'
import Relationship from './../components/svg/node-types/node-relationship'
import WeakEntity from './../components/svg/node-types/node-weak-entity'
Expand Down Expand Up @@ -107,9 +107,9 @@ class NodePicker extends Component {
<li class='node node-associative-entity' draggable='true' onDragStart={this.dragStartedAssociativeEntity} onDragEnd={this.addNodeAssociativeEntity}>
<AssociativeEntity />
</li>
<li class='node node-attribute' draggable='true' onDragStart={this.dragStartedAttribute} onDragEnd={this.addNodeAttribute}>
<Attribute />
</li>
{/* <li class='node node-attribute' draggable='true' onDragStart={this.dragStartedAttribute} onDragEnd={this.addNodeAttribute}> */}
{/* <Attribute /> */}
{/* </li> */}
<li class='node node-relationship' draggable='true' onDragStart={this.dragStartedRelationship} onDragEnd={this.addNodeRelationship}>
<Relationship />
</li>
Expand All @@ -122,7 +122,7 @@ class NodePicker extends Component {
<div class='node' id='node-drag-tween-entity' style='position:absolute;left: -1000px'><Entity /></div>
<div class='node' id='node-drag-tween-weak-entity' style='position:absolute;left: -1100px'><WeakEntity /></div>
<div class='node' id='node-drag-tween-associative-entity' style='position:absolute;left: -1200px'><AssociativeEntity /></div>
<div class='node' id='node-drag-tween-attribute' style='position:absolute;left: -1300px'><Attribute /></div>
{/* <div class='node' id='node-drag-tween-attribute' style='position:absolute;left: -1300px'><Attribute /></div> */}
<div class='node' id='node-drag-tween-relationship' style='position:absolute;left: -1400px'><Relationship /></div>
<div class='node' id='node-drag-tween-inheritance' style='position:absolute;left: -1500px'><Inheritance /></div>
</div>
Expand Down
30 changes: 30 additions & 0 deletions src/browser/js/components/svg/attributes.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,30 @@
import { h, Component } from 'preact'
import { bind } from 'decko'
import _ from 'lodash'
// import nodeStore from '../../redux/store'
// import {ACTION} from '../../redux/actions'

class Attributes extends Component {
@bind
onAttributeDelete() {}

render(props) {
if (_.isEmpty(props.attributes)) {
return null
}

return (
<div>
{
props.attributes.map(attribute => (
<div class='node-attribute'>
<span class={attribute.isPrimary ? 'primary-key' : ''}>{attribute.name}</span>
</div>
))
}
</div>
)
}
}

export default Attributes
87 changes: 85 additions & 2 deletions src/browser/js/components/svg/node.js
Original file line number Diff line number Diff line change
@@ -1,9 +1,12 @@
import { h, Component } from 'preact'
import { bind } from 'decko'
import _ from 'lodash'
import nodeStore from '../../redux/store'
import {ACTION} from '../../redux/actions'
import getNodeTypeComponent from './../../constants/node-type-components'
import NodeResize from './node-resize'
import Attributes from './attributes'
import Portal from 'preact-portal'

class Node extends Component {
constructor({nodeId, nodeName, x, y}) {
Expand Down Expand Up @@ -308,6 +311,43 @@ class Node extends Component {
event.preventDefault()
}

@bind
open() {
this.setState({ open: true })
}

@bind
close() {
this.setState({ open: false })
}

@bind
submit(event) {
event.preventDefault()

let attributeName = event.target[0].value
let attributeType = event.target[1].value
let attributeIsPrimary = event.target[2].checked

if (_.isEmpty(attributeName)) {
this.close()
return
}

nodeStore.dispatch({type: ACTION.ADD_ATTRIBUTE,
value: {
nodeId: this.nodeId,
attribute: {
name: attributeName,
type: attributeType,
isPrimary: attributeIsPrimary
}
}
})

this.close()
}

render(props, state) {
let rootStyle = {
transform: `translate(${state.dragX}px, ${state.dragY}px) scale(${props.zoom})`
Expand All @@ -320,15 +360,14 @@ class Node extends Component {
{/* <circle cx='0' cy='0' r='10' fill='#ef4836' stroke='none' style='-webkit-tap-highlight-color: rgba(0, 0, 0, 0);' onClick={this.removeNode} /> */}
</div>

{ props.selected && <NodeResize onStartNodeResize={this.startNodeResize} /> }
{ <NodeResize onStartNodeResize={this.startNodeResize} ng-if='props.selected' /> }

<div id='svg-rect' style={{width: state.width, height: state.height}}
onMouseDown={this.onMouseDown}
onMouseEnter={this.onConnectionEnterDestination}
onMouseLeave={this.onConnectionLeaveDestination}
onClick={this.selectNode}
>

{ getNodeTypeComponent(props.type, {width: state.width, height: state.height, color: props.color}) }

{
Expand All @@ -344,6 +383,50 @@ class Node extends Component {
</div>
}
</div>

<div class='attributes-wrapper'>
<Attributes attributes={props.attributes} />

{ props.selected && props.type !== 'inheritance' && <button class='button-add-attribute' onClick={this.open}>Add property</button> }
</div>

{
state.open &&
<Portal into='body'>
<div class='modal' >
<form class='modal-form' name='attributeForm' onSubmit={this.submit} style='z-index: 101'>
{/* <input value='' onInput={this.linkState('text')} placeholder='New ToDo...' /> */}
<input type='text' value='' name='attributeName' onChange={this.preventDefault} placeholder='type name...' />

<select name='attributeType'>
<option value='CHAR'>CHAR</option>
<option value='INTEGER'>INTEGER</option>
<option value='FLOAT'>FLOAT</option>
<option value='TIMESTAMP'>TIMESTAMP</option>
</select>

<label class='label--checkbox'>
<input type='checkbox' class='checkbox' name='attributeIsKey' />
<span>Is primary key</span>
</label>

<div style='text-align: right; margin: 30px 5px 0px;'>
<input type='submit' value='Submit' />
<input type='button' value='Cancel' onClick={this.close} />
</div>
</form>

<div class='modal-mask' style='
width: 100vw;
height: 100vh;
position: absolute;
top: 0;
background: rgba(21, 21, 21, 0.32);
z-index: 100;
' />
</div>
</Portal>
}
</div>
)
}
Expand Down
1 change: 1 addition & 0 deletions src/browser/js/redux/actions.js
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,7 @@ const ACTION = {
NODE_TO_FRONT: 'NODE_TO_FRONT',
NODE_TO_BACK: 'NODE_TO_BACK',
MOVE_CANVAS: 'MOVE_CANVAS',
ADD_ATTRIBUTE: 'ADD_ATTRIBUTE',
UNDO: 'UNDO',
REDO: 'REDO'
}
Expand Down
11 changes: 11 additions & 0 deletions src/browser/js/redux/reducers/node.reducer.js
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@ const actions = {
nodeId: v4(),
nodeName: action.value.type.replace(/-/, ' '),
type: action.value.type,
attributes: [],
x: action.value.x - 0,
y: action.value.y - 50,
selected: true,
Expand Down Expand Up @@ -130,6 +131,15 @@ const actions = {
node.y += action.value.y
})

return newState
},

addAttributeToNode(state, action) {
let newState = _.cloneDeep(state)

let nodeForUpdate = _.find(newState, { nodeId: action.value.nodeId })
nodeForUpdate.attributes.push(action.value.attribute)

return newState
}
}
Expand All @@ -150,6 +160,7 @@ export default function nodeReducer(state = [], action) {
case ACTION.NODE_TO_BACK: return actions.moveNodeToBack(state, action)
case ACTION.IMPORT: return actions.importNodes(state, action)
case ACTION.MOVE_CANVAS: return actions.moveNodesOnCanvas(state, action)
case ACTION.ADD_ATTRIBUTE: return actions.addAttributeToNode(state, action)
default: return state
}
}
113 changes: 112 additions & 1 deletion src/browser/styl/main.styl
Original file line number Diff line number Diff line change
Expand Up @@ -68,7 +68,7 @@ li
////////////////////////////////
// prettier layout
width: 164px
height: 70vh
height: 60vh
position: absolute
left: -1px
top: 50vh
Expand Down Expand Up @@ -242,3 +242,114 @@ label[for=connect-nodes] input
fill: #ffffff
stroke: #222222
stroke-width: 1


.attributes-wrapper
width: 100%
position: absolute
overflow: hidden

.button-add-attribute
bottom: -30px
width: 100%
height: 25px
margin: 0
margin-top: 5px
outline: none
box-shadow: none
border: 1px solid black

.modal-form
position: absolute
left: 50%
top: 50%
transform: translate(-50%, -50%)
padding: 10px
box-shadow: 0 3px 10px 2px rgba(0, 0, 0, 0.42)
background: #fff
border-radius: 3px
overflow: auto
text-align: center
cursor: pointer
animation: zoom .4s forwards ease 1

input[type=text]
select
width: 91%
height: 25px
padding: 6px 12px
color: #555
background-color: #fff
border: 1px solid #ccc
border-radius: 4px
box-shadow: inset 0 1px 1px rgba(0,0,0,0.075)
margin: 5px

.label--checkbox
display: block
text-align: left
margin: 5px 14px
user-select: none

span
margin-left: 15px


.checkbox
position: relative
cursor: pointer

&:before
content: ""
position: absolute
left: 0
top: -1px
width: .75rem
height: .375rem
border: 2px solid #17ad3e
border-top-style: none
border-right-style: none
transition: transform 0.4s cubic-bezier(0.45, 1.8, 0.5, 0.75)
transform: rotate(-45deg) scale(0,0)
z-index: 1

&:checked
&:before
transform: rotate(-45deg) scale(1, 1)

&:after
content: ""
position: absolute
top: -4px
left: -2px
width: 16px
height: 16px
background: #fff
border: 1px solid #ccc
border-radius: 3px
cursor: pointer


.node-attribute
padding: 3px
border-right: 1px solid black
border-left: 1px solid black
border-top: 1px dashed black
background-color: $white
user-select: none

&:first-child
margin-top: -1px
border-top: 1px solid black

&:last-child
border-bottom: 1px solid black


.primary-key
border-bottom: 1px solid black

span
text-overflow: ellipsis
overflow: hidden
white-space: nowrap

0 comments on commit 0a207c0

Please sign in to comment.