mirror of
https://github.com/BoostIo/Boostnote
synced 2025-12-22 22:22:12 +00:00
on Refactoring...
This commit is contained in:
@@ -1,25 +0,0 @@
|
||||
var React = require('react')
|
||||
|
||||
var BlueprintForm = require('./BlueprintForm')
|
||||
|
||||
var BlueprintEditModal = React.createClass({
|
||||
propTypes: {
|
||||
close: React.PropTypes.func,
|
||||
blueprint: React.PropTypes.object
|
||||
},
|
||||
stopPropagation: function (e) {
|
||||
e.stopPropagation()
|
||||
},
|
||||
render: function () {
|
||||
return (
|
||||
<div onClick={this.stopPropagation} className='BlueprintEditModal modal'>
|
||||
<div className='modal-header'>
|
||||
<h1>Edit Blueprint</h1>
|
||||
</div>
|
||||
<BlueprintForm blueprint={this.props.blueprint} close={this.props.close}/>
|
||||
</div>
|
||||
)
|
||||
}
|
||||
})
|
||||
|
||||
module.exports = BlueprintEditModal
|
||||
@@ -1,11 +1,14 @@
|
||||
var React = require('react')
|
||||
|
||||
var PlanetActions = require('../Actions/PlanetActions')
|
||||
var Hq = require('../Services/Hq')
|
||||
|
||||
var BlueprintDeleteModal = React.createClass({
|
||||
var PlanetStore = require('../Stores/PlanetStore')
|
||||
|
||||
module.exports = React.createClass({
|
||||
propTypes: {
|
||||
close: React.PropTypes.func,
|
||||
blueprint: React.PropTypes.object
|
||||
planet: React.PropTypes.object,
|
||||
code: React.PropTypes.object,
|
||||
close: React.PropTypes.func
|
||||
},
|
||||
componentDidMount: function () {
|
||||
React.findDOMNode(this).focus()
|
||||
@@ -13,20 +16,22 @@ var BlueprintDeleteModal = React.createClass({
|
||||
stopPropagation: function (e) {
|
||||
e.stopPropagation()
|
||||
},
|
||||
handleKeyDown: function (e) {
|
||||
if ((e.keyCode === 13 && e.metaKey)) {
|
||||
e.preventDefault()
|
||||
this.submit()
|
||||
}
|
||||
},
|
||||
submit: function () {
|
||||
PlanetActions.deleteBlueprint(this.props.blueprint.id)
|
||||
var planet = this.props.planet
|
||||
Hq.destroyCode(planet.userName, planet.name, this.props.code.localId)
|
||||
.then(function (res) {
|
||||
PlanetStore.Actions.destroyCode(res.body)
|
||||
this.props.close()
|
||||
}.bind(this))
|
||||
.catch(function (err) {
|
||||
console.error(err)
|
||||
})
|
||||
},
|
||||
render: function () {
|
||||
return (
|
||||
<div tabIndex='3' onKeyDown={this.handleKeyDown} onClick={this.stopPropagation} className='BlueprintDeleteModal modal'>
|
||||
<div className='CodeDeleteModal modal'>
|
||||
<div className='modal-header'>
|
||||
<h1>Delete Blueprint</h1>
|
||||
<h1>Delete Code</h1>
|
||||
</div>
|
||||
<div className='modal-body'>
|
||||
<p>Are you sure to delete it?</p>
|
||||
@@ -41,5 +46,3 @@ var BlueprintDeleteModal = React.createClass({
|
||||
)
|
||||
}
|
||||
})
|
||||
|
||||
module.exports = BlueprintDeleteModal
|
||||
20
browser/main/Components/CodeEditModal.jsx
Normal file
20
browser/main/Components/CodeEditModal.jsx
Normal file
@@ -0,0 +1,20 @@
|
||||
var React = require('react')
|
||||
var CodeForm = require('./CodeForm')
|
||||
|
||||
module.exports = React.createClass({
|
||||
propTypes: {
|
||||
close: React.PropTypes.func,
|
||||
code: React.PropTypes.object,
|
||||
planet: React.PropTypes.object
|
||||
},
|
||||
render: function () {
|
||||
return (
|
||||
<div className='CodeEditModal modal'>
|
||||
<div className='modal-header'>
|
||||
<h1>Edit Code</h1>
|
||||
</div>
|
||||
<CodeForm code={this.props.code} planet={this.props.planet} close={this.props.close}/>
|
||||
</div>
|
||||
)
|
||||
}
|
||||
})
|
||||
@@ -1,7 +1,8 @@
|
||||
var React = require('react/addons')
|
||||
|
||||
var ace = window.ace
|
||||
var CodeEditor = React.createClass({
|
||||
|
||||
module.exports = React.createClass({
|
||||
propTypes: {
|
||||
code: React.PropTypes.string,
|
||||
mode: React.PropTypes.string,
|
||||
@@ -48,5 +49,3 @@ var CodeEditor = React.createClass({
|
||||
)
|
||||
}
|
||||
})
|
||||
|
||||
module.exports = CodeEditor
|
||||
|
||||
@@ -1,96 +1,99 @@
|
||||
var React = require('react/addons')
|
||||
var ReactRouter = require('react-router')
|
||||
var CodeEditor = require('./CodeEditor')
|
||||
var Catalyst = require('../Mixins/Catalyst')
|
||||
var Select = require('react-select')
|
||||
var request = require('superagent')
|
||||
var PlanetActions = require('../Actions/PlanetActions')
|
||||
|
||||
var apiUrl = require('../../../config').apiUrl
|
||||
var Hq = require('../Services/Hq')
|
||||
|
||||
var LinkedState = require('../Mixins/LinkedState')
|
||||
|
||||
var PlanetStore = require('../Stores/PlanetStore')
|
||||
|
||||
var aceModes = require('../../../modules/ace-modes')
|
||||
|
||||
var getOptions = function (input, callback) {
|
||||
request
|
||||
.get(apiUrl + 'tags/search')
|
||||
.query({name: input})
|
||||
.send()
|
||||
.end(function (err, res) {
|
||||
if (err) {
|
||||
callback(err)
|
||||
return
|
||||
}
|
||||
Hq.searchTag(input)
|
||||
.then(function (res) {
|
||||
callback(null, {
|
||||
options: res.body.map(function (tag) {
|
||||
return {
|
||||
label: tag.name,
|
||||
value: tag.name
|
||||
}
|
||||
}),
|
||||
}),
|
||||
complete: false
|
||||
})
|
||||
})
|
||||
})
|
||||
.catch(function (err) {
|
||||
console.log(err)
|
||||
})
|
||||
}
|
||||
|
||||
var SnippetForm = React.createClass({
|
||||
mixins: [Catalyst.LinkedStateMixin, ReactRouter.State],
|
||||
module.exports = React.createClass({
|
||||
mixins: [LinkedState],
|
||||
propTypes: {
|
||||
planet: React.PropTypes.object,
|
||||
close: React.PropTypes.func,
|
||||
snippet: React.PropTypes.object
|
||||
transitionTo: React.PropTypes.func,
|
||||
code: React.PropTypes.object
|
||||
},
|
||||
getInitialState: function () {
|
||||
var snippet = Object.assign({
|
||||
var code = Object.assign({
|
||||
description: '',
|
||||
mode: '',
|
||||
content: '',
|
||||
callSign: '',
|
||||
Tags: []
|
||||
}, this.props.snippet)
|
||||
snippet.Tags = snippet.Tags.map(function (tag) {
|
||||
}, this.props.code)
|
||||
|
||||
code.Tags = code.Tags.map(function (tag) {
|
||||
return {
|
||||
label: tag.name,
|
||||
value: tag.name
|
||||
}
|
||||
})
|
||||
|
||||
return {
|
||||
snippet: snippet
|
||||
code: code
|
||||
}
|
||||
},
|
||||
componentDidMount: function () {
|
||||
React.findDOMNode(this.refs.description).focus()
|
||||
},
|
||||
handleModeChange: function (selected) {
|
||||
var snippet = this.state.snippet
|
||||
snippet.mode = selected
|
||||
console.log(selected, 'selected')
|
||||
this.setState({snippet: snippet})
|
||||
var code = this.state.code
|
||||
code.mode = selected
|
||||
this.setState({code: code})
|
||||
},
|
||||
handleTagsChange: function (selected, all) {
|
||||
var snippet = this.state.snippet
|
||||
snippet.Tags = all
|
||||
this.setState({snippet: snippet})
|
||||
var code = this.state.code
|
||||
code.Tags = all
|
||||
this.setState({code: code})
|
||||
},
|
||||
handleContentChange: function (e, value) {
|
||||
var snippet = this.state.snippet
|
||||
snippet.content = value
|
||||
this.setState({snippet: snippet})
|
||||
var code = this.state.code
|
||||
code.content = value
|
||||
this.setState({code: code})
|
||||
},
|
||||
submit: function () {
|
||||
var snippet = Object.assign({}, this.state.snippet)
|
||||
snippet.Tags = snippet.Tags.map(function (tag) {
|
||||
var planet = this.props.planet
|
||||
var code = this.state.code
|
||||
code.Tags = code.Tags.map(function (tag) {
|
||||
return tag.value
|
||||
})
|
||||
if (this.props.snippet == null) {
|
||||
var params = this.getParams()
|
||||
var userName = params.userName
|
||||
var planetName = params.planetName
|
||||
|
||||
PlanetActions.createSnippet(userName + '/' + planetName, snippet)
|
||||
if (this.props.code == null) {
|
||||
Hq.createCode(planet.userName, planet.name, this.state.code)
|
||||
.then(function (res) {
|
||||
var code = res.body
|
||||
PlanetStore.Actions.updateCode(code)
|
||||
this.props.close()
|
||||
this.props.transitionTo('codes', {userName: planet.userName, planetName: planet.name, localId: code.localId})
|
||||
}.bind(this))
|
||||
.catch(function (err) {
|
||||
console.error(err)
|
||||
})
|
||||
} else {
|
||||
var snippetId = snippet.id
|
||||
delete snippet.id
|
||||
|
||||
PlanetActions.updateSnippet(snippetId, snippet)
|
||||
Hq.updateCode(planet.userName, planet.name, this.props.code.localId, this.state.code)
|
||||
.then(function (res) {
|
||||
var code = res.body
|
||||
PlanetStore.Actions.updateCode(code)
|
||||
this.props.close()
|
||||
}.bind(this))
|
||||
}
|
||||
},
|
||||
handleKeyDown: function (e) {
|
||||
@@ -107,30 +110,29 @@ var SnippetForm = React.createClass({
|
||||
}
|
||||
})
|
||||
return (
|
||||
<div onKeyDown={this.handleKeyDown} className='SnippetForm'>
|
||||
<div className='CodeForm'>
|
||||
<div className='modal-body'>
|
||||
<div className='form-group'>
|
||||
<textarea ref='description' className='snippetDescription block-input' valueLink={this.linkState('snippet.description')} placeholder='Description'/>
|
||||
<textarea ref='description' className='codeDescription block-input' valueLink={this.linkState('code.description')} placeholder='Description'/>
|
||||
</div>
|
||||
<div className='form-group'>
|
||||
<input className='inline-input' valueLink={this.linkState('snippet.callSign')} type='text' placeholder='Callsign'/>
|
||||
<Select
|
||||
name='mode'
|
||||
className='modeSelect'
|
||||
value={this.state.snippet.mode}
|
||||
value={this.state.code.mode}
|
||||
placeholder='Select Language'
|
||||
options={modeOptions}
|
||||
onChange={this.handleModeChange}/>
|
||||
</div>
|
||||
<div className='form-group'>
|
||||
<CodeEditor onChange={this.handleContentChange} code={this.state.snippet.content} mode={this.state.snippet.mode}/>
|
||||
<CodeEditor onChange={this.handleContentChange} code={this.state.code.content} mode={this.state.code.mode}/>
|
||||
</div>
|
||||
<div className='form-group'>
|
||||
<Select
|
||||
name='Tags'
|
||||
multi={true}
|
||||
allowCreate={true}
|
||||
value={this.state.snippet.Tags}
|
||||
value={this.state.code.Tags}
|
||||
placeholder='Tags...'
|
||||
asyncOptions={getOptions}
|
||||
onChange={this.handleTagsChange}
|
||||
@@ -140,12 +142,10 @@ var SnippetForm = React.createClass({
|
||||
<div className='modal-footer'>
|
||||
<div className='modal-control'>
|
||||
<button onClick={this.props.close} className='btn-default'>Cancel</button>
|
||||
<button onClick={this.submit} className='btn-primary'>{this.props.snippet == null ? 'Launch' : 'Relaunch'}</button>
|
||||
<button onClick={this.submit} className='btn-primary'>{this.props.code == null ? 'Launch' : 'Relaunch'}</button>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
)
|
||||
}
|
||||
})
|
||||
|
||||
module.exports = SnippetForm
|
||||
@@ -1,7 +1,8 @@
|
||||
var React = require('react/addons')
|
||||
|
||||
var ace = window.ace
|
||||
var CodeViewer = React.createClass({
|
||||
|
||||
module.exports = React.createClass({
|
||||
propTypes: {
|
||||
code: React.PropTypes.string,
|
||||
mode: React.PropTypes.string
|
||||
@@ -42,5 +43,3 @@ var CodeViewer = React.createClass({
|
||||
)
|
||||
}
|
||||
})
|
||||
|
||||
module.exports = CodeViewer
|
||||
|
||||
167
browser/main/Components/EditProfileModal.jsx
Normal file
167
browser/main/Components/EditProfileModal.jsx
Normal file
@@ -0,0 +1,167 @@
|
||||
/* global localStorage */
|
||||
|
||||
var React = require('react/addons')
|
||||
|
||||
var Hq = require('../Services/Hq')
|
||||
|
||||
var LinkedState = require('../Mixins/LinkedState')
|
||||
|
||||
var UserStore = require('../Stores/UserStore')
|
||||
|
||||
module.exports = React.createClass({
|
||||
mixins: [LinkedState],
|
||||
propTypes: {
|
||||
targetUser: React.PropTypes.shape({
|
||||
name: React.PropTypes.string,
|
||||
profileName: React.PropTypes.string,
|
||||
email: React.PropTypes.string
|
||||
})
|
||||
},
|
||||
getInitialState: function () {
|
||||
var targetUser = this.props.targetUser
|
||||
return {
|
||||
currentTab: 'userInfo',
|
||||
user: {
|
||||
name: targetUser.name,
|
||||
profileName: targetUser.profileName,
|
||||
email: targetUser.email
|
||||
},
|
||||
userSubmitStatus: null,
|
||||
password: {
|
||||
currentPassword: '',
|
||||
newPassword: '',
|
||||
passwordConfirmation: ''
|
||||
},
|
||||
passwordSubmitStatus: null
|
||||
}
|
||||
},
|
||||
selectTab: function (tabName) {
|
||||
return function () {
|
||||
this.setState({currentTab: tabName})
|
||||
}.bind(this)
|
||||
},
|
||||
saveUserInfo: function () {
|
||||
this.setState({
|
||||
userSubmitStatus: 'sending'
|
||||
}, function () {
|
||||
Hq.updateUser(this.props.targetUser.name, this.state.user)
|
||||
.then(function (res) {
|
||||
this.setState({userSubmitStatus: 'done'}, function () {
|
||||
localStorage.setItem('currentUser', JSON.stringify(res.body))
|
||||
UserStore.Actions.update(res.body)
|
||||
})
|
||||
}.bind(this))
|
||||
.catch(function (err) {
|
||||
console.error(err)
|
||||
this.setState({userSubmitStatus: 'error'})
|
||||
}.bind(this))
|
||||
})
|
||||
},
|
||||
savePassword: function () {
|
||||
this.setState({
|
||||
passwordSubmitStatus: 'sending'
|
||||
}, function () {
|
||||
console.log(this.state.password)
|
||||
Hq.changePassword(this.state.password)
|
||||
.then(function (res) {
|
||||
this.setState({
|
||||
passwordSubmitStatus: 'done',
|
||||
currentPassword: '',
|
||||
newPassword: '',
|
||||
passwordConfirmation: ''
|
||||
})
|
||||
}.bind(this))
|
||||
.catch(function (err) {
|
||||
console.error(err)
|
||||
this.setState({
|
||||
passwordSubmitStatus: 'error',
|
||||
currentPassword: '',
|
||||
newPassword: '',
|
||||
passwordConfirmation: ''
|
||||
})
|
||||
}.bind(this))
|
||||
})
|
||||
},
|
||||
render: function () {
|
||||
var content
|
||||
|
||||
switch (this.state.currentTab) {
|
||||
case 'userInfo':
|
||||
content = this.renderUserInfoTab()
|
||||
break
|
||||
case 'password':
|
||||
content = this.renderPasswordTab()
|
||||
break
|
||||
}
|
||||
|
||||
return (
|
||||
<div className='EditProfileModal modal'>
|
||||
<div className='leftPane'>
|
||||
<div className='tabLabel'>Edit profile</div>
|
||||
<div className='tabList'>
|
||||
<button className={this.state.currentTab === 'userInfo' ? 'active' : ''} onClick={this.selectTab('userInfo')}><i className='fa fa-user fa-fw'/> User Info</button>
|
||||
<button className={this.state.currentTab === 'password' ? 'active' : ''} onClick={this.selectTab('password')}><i className='fa fa-lock fa-fw'/> Password</button>
|
||||
</div>
|
||||
</div>
|
||||
<div className='rightPane'>
|
||||
{content}
|
||||
</div>
|
||||
</div>
|
||||
)
|
||||
},
|
||||
renderUserInfoTab: function () {
|
||||
return (
|
||||
<div className='userInfoTab'>
|
||||
<div className='formField'>
|
||||
<label>Profile Name</label>
|
||||
<input valueLink={this.linkState('user.profileName')}/>
|
||||
</div>
|
||||
<div className='formField'>
|
||||
<label>Name</label>
|
||||
<input valueLink={this.linkState('user.name')}/>
|
||||
</div>
|
||||
<div className='formField'>
|
||||
<label>E-mail</label>
|
||||
<input valueLink={this.linkState('user.email')}/>
|
||||
</div>
|
||||
<div className='formConfirm'>
|
||||
<button disabled={this.state.userSubmitStatus === 'sending'} onClick={this.saveUserInfo}>Save</button>
|
||||
|
||||
<div className={'alertInfo' + (this.state.userSubmitStatus === 'sending' ? '' : ' hide')}>on Sending...</div>
|
||||
|
||||
<div className={'alertError' + (this.state.userSubmitStatus === 'error' ? '' : ' hide')}>Connection failed.. Try again.</div>
|
||||
|
||||
<div className={'alertSuccess' + (this.state.userSubmitStatus === 'done' ? '' : ' hide')}>Successfully done!!</div>
|
||||
</div>
|
||||
</div>
|
||||
)
|
||||
},
|
||||
renderPasswordTab: function () {
|
||||
return (
|
||||
<div className='paswordTab'>
|
||||
<div className='formField'>
|
||||
<label>Current password</label>
|
||||
<input valueLink={this.linkState('password.currentPassword')}/>
|
||||
</div>
|
||||
<div className='formField'>
|
||||
<label>New password</label>
|
||||
<input valueLink={this.linkState('password.newPassword')}/>
|
||||
</div>
|
||||
<div className='formField'>
|
||||
<label>Confirmation</label>
|
||||
<input valueLink={this.linkState('password.passwordConfirmation')}/>
|
||||
</div>
|
||||
|
||||
<div className='formConfirm'>
|
||||
<button disabled={this.state.password.newPassword.length === 0 || this.state.password.newPassword !== this.state.password.passwordConfirmation || this.state.passwordSubmitStatus === 'sending'} onClick={this.savePassword}>Save</button>
|
||||
|
||||
<div className={'alertInfo' + (this.state.passwordSubmitStatus === 'sending' ? '' : ' hide')}>on Sending...</div>
|
||||
|
||||
<div className={'alertError' + (this.state.passwordSubmitStatus === 'error' ? '' : ' hide')}>Connection failed.. Try again.</div>
|
||||
|
||||
<div className={'alertSuccess' + (this.state.passwordSubmitStatus === 'done' ? '' : ' hide')}>Successfully done!!</div>
|
||||
</div>
|
||||
</div>
|
||||
)
|
||||
}
|
||||
})
|
||||
154
browser/main/Components/HomeNavigator.jsx
Normal file
154
browser/main/Components/HomeNavigator.jsx
Normal file
@@ -0,0 +1,154 @@
|
||||
/* global localStorage */
|
||||
|
||||
var React = require('react/addons')
|
||||
var ReactRouter = require('react-router')
|
||||
var Navigation = ReactRouter.Navigation
|
||||
var State = ReactRouter.State
|
||||
var Link = ReactRouter.Link
|
||||
var Reflux = require('reflux')
|
||||
|
||||
var Modal = require('../Mixins/Modal')
|
||||
|
||||
var UserStore = require('../Stores/UserStore')
|
||||
|
||||
var PreferencesModal = require('./PreferencesModal')
|
||||
var PlanetCreateModal = require('./PlanetCreateModal')
|
||||
var ProfileImage = require('./ProfileImage')
|
||||
|
||||
module.exports = React.createClass({
|
||||
mixins: [Navigation, State, Reflux.listenTo(UserStore, 'onUserChange'), Modal],
|
||||
getInitialState: function () {
|
||||
return {
|
||||
isPlanetCreateModalOpen: false,
|
||||
currentUser: JSON.parse(localStorage.getItem('currentUser'))
|
||||
}
|
||||
},
|
||||
onUserChange: function (res) {
|
||||
switch (res.status) {
|
||||
case 'userUpdated':
|
||||
if (this.state.currentUser.id === res.data.id) {
|
||||
this.setState({currentUser: res.data})
|
||||
}
|
||||
break
|
||||
}
|
||||
},
|
||||
openPreferencesModal: function () {
|
||||
this.openModal(PreferencesModal)
|
||||
},
|
||||
openPlanetCreateModal: function () {
|
||||
this.openModal(PlanetCreateModal, {transitionTo: this.transitionTo})
|
||||
},
|
||||
handleKeyDown: function (e) {
|
||||
if (this.state.currentUser == null) return
|
||||
if (e.metaKey && e.keyCode > 48 && e.keyCode < 58) {
|
||||
var planet = this.state.currentUser.Planets[e.keyCode - 49]
|
||||
if (planet != null) {
|
||||
this.transitionTo('planet', {userName: planet.userName, planetName: planet.name})
|
||||
}
|
||||
e.preventDefault()
|
||||
}
|
||||
},
|
||||
toggleProfilePopup: function () {
|
||||
this.openProfilePopup()
|
||||
},
|
||||
openProfilePopup: function () {
|
||||
this.setState({isProfilePopupOpen: true}, function () {
|
||||
document.addEventListener('click', this.closeProfilePopup)
|
||||
})
|
||||
},
|
||||
closeProfilePopup: function () {
|
||||
document.removeEventListener('click', this.closeProfilePopup)
|
||||
this.setState({isProfilePopupOpen: false})
|
||||
},
|
||||
handleLogoutClick: function () {
|
||||
localStorage.removeItem('currentUser')
|
||||
localStorage.removeItem('token')
|
||||
this.transitionTo('login')
|
||||
},
|
||||
render: function () {
|
||||
var params = this.getParams()
|
||||
|
||||
if (this.state.currentUser == null) {
|
||||
return (
|
||||
<div className='HomeNavigator'>
|
||||
</div>
|
||||
)
|
||||
}
|
||||
|
||||
var planets = ((this.state.currentUser == null || this.state.currentUser.Planets == null) ? [] : this.state.currentUser.Planets).map(function (planet, index) {
|
||||
return (
|
||||
<li key={planet.id} className={params.userName === planet.userName && params.planetName === planet.name ? 'active' : ''}>
|
||||
<Link to='planet' params={{userName: planet.userName, planetName: planet.name}}>
|
||||
{planet.name[0]}
|
||||
<div className='planetTooltip'>{planet.userName}/{planet.name}</div>
|
||||
</Link>
|
||||
<div className='shortCut'>⌘{index + 1}</div>
|
||||
</li>
|
||||
)
|
||||
})
|
||||
|
||||
var popup = this.renderPopup()
|
||||
|
||||
return (
|
||||
<div className='HomeNavigator'>
|
||||
<button onClick={this.toggleProfilePopup} className='profileButton'>
|
||||
<ProfileImage size='55' email={this.state.currentUser.email}/>
|
||||
</button>
|
||||
{popup}
|
||||
<ul className='planetList'>
|
||||
{planets}
|
||||
</ul>
|
||||
<button onClick={this.openPlanetCreateModal} className='newPlanet'><i className='fa fa-plus'/></button>
|
||||
</div>
|
||||
)
|
||||
},
|
||||
renderPopup: function () {
|
||||
return (
|
||||
<div ref='profilePopup' className={'profilePopup' + (this.state.isProfilePopupOpen ? '' : ' close')}>
|
||||
<div className='profileGroup'>
|
||||
<div className='profileGroupLabel'>
|
||||
<span>You</span>
|
||||
</div>
|
||||
<ul className='profileGroupList'>
|
||||
<li>
|
||||
<Link to='userHome' params={{userName: this.state.currentUser.name}} className='userName'>Profile</Link>
|
||||
<div className='userSetting'><i className='fa fa-gear'/></div>
|
||||
</li>
|
||||
</ul>
|
||||
</div>
|
||||
|
||||
<div className='profileGroup'>
|
||||
<div className='profileGroupLabel'>
|
||||
<span>Team</span>
|
||||
</div>
|
||||
<ul className='profileGroupList'>
|
||||
<li>
|
||||
<div className='userName'>A team</div>
|
||||
<div className='userSetting'><i className='fa fa-gear'/></div>
|
||||
</li>
|
||||
<li>
|
||||
<div className='userName'>B team</div>
|
||||
<div className='userSetting'><i className='fa fa-gear'/></div>
|
||||
</li>
|
||||
<li>
|
||||
<div className='userName'>C team</div>
|
||||
<div className='userSetting'><i className='fa fa-gear'/></div>
|
||||
</li>
|
||||
<li>
|
||||
<button className='createNewTeam'><i className='fa fa-plus-square-o'/> create new team</button>
|
||||
</li>
|
||||
</ul>
|
||||
</div>
|
||||
|
||||
<ul className='controlGroup'>
|
||||
<li>
|
||||
<button onClick={this.openPreferencesModal}><i className='fa fa-gear fa-fw'/> Preferences</button>
|
||||
</li>
|
||||
<li>
|
||||
<button onClick={this.handleLogoutClick}><i className='fa fa-sign-out fa-fw'/> Logout</button>
|
||||
</li>
|
||||
</ul>
|
||||
</div>
|
||||
)
|
||||
}
|
||||
})
|
||||
@@ -1,54 +1,56 @@
|
||||
var React = require('react/addons')
|
||||
var ReactRouter = require('react-router')
|
||||
var Catalyst = require('../Mixins/Catalyst')
|
||||
|
||||
var SnippetForm = require('./SnippetForm')
|
||||
var BlueprintForm = require('./BlueprintForm')
|
||||
var CodeForm = require('./CodeForm')
|
||||
var NoteForm = require('./NoteForm')
|
||||
|
||||
var LaunchModal = React.createClass({
|
||||
mixins: [Catalyst.LinkedStateMixin, ReactRouter.State],
|
||||
module.exports = React.createClass({
|
||||
propTypes: {
|
||||
planet: React.PropTypes.object,
|
||||
transitionTo: React.PropTypes.func,
|
||||
close: React.PropTypes.func
|
||||
},
|
||||
getInitialState: function () {
|
||||
return {
|
||||
currentTab: 'snippet'
|
||||
currentTab: 'code'
|
||||
}
|
||||
},
|
||||
componentDidMount: function () {
|
||||
|
||||
},
|
||||
stopPropagation: function (e) {
|
||||
e.stopPropagation()
|
||||
},
|
||||
selectSnippetTab: function () {
|
||||
this.setState({currentTab: 'snippet'})
|
||||
selectCodeTab: function () {
|
||||
this.setState({currentTab: 'code'})
|
||||
},
|
||||
selectBlueprintTab: function () {
|
||||
this.setState({currentTab: 'blueprint'})
|
||||
selectNoteTab: function () {
|
||||
this.setState({currentTab: 'note'})
|
||||
},
|
||||
handleKeyDown: function (e) {
|
||||
if (e.keyCode === 37 && e.metaKey) {
|
||||
this.selectSnippetTab()
|
||||
this.selectCodeTab()
|
||||
}
|
||||
if (e.keyCode === 39 && e.metaKey) {
|
||||
this.selectBlueprintTab()
|
||||
this.selectNoteTab()
|
||||
}
|
||||
},
|
||||
render: function () {
|
||||
var modalBody
|
||||
if (this.state.currentTab === 'snippet') {
|
||||
if (this.state.currentTab === 'code') {
|
||||
modalBody = (
|
||||
<SnippetForm close={this.props.close}/>
|
||||
<CodeForm planet={this.props.planet} transitionTo={this.props.transitionTo} close={this.props.close}/>
|
||||
)
|
||||
} else {
|
||||
modalBody = (
|
||||
<BlueprintForm close={this.props.close}/>
|
||||
<NoteForm planet={this.props.planet} transitionTo={this.props.transitionTo} close={this.props.close}/>
|
||||
)
|
||||
}
|
||||
|
||||
return (
|
||||
<div onKeyDown={this.handleKeyDown} onClick={this.stopPropagation} className='LaunchModal modal'>
|
||||
<div className='LaunchModal modal'>
|
||||
<div className='modal-header'>
|
||||
<div className='modal-tab'>
|
||||
<button className={this.state.currentTab === 'snippet' ? 'btn-primary active' : 'btn-default'} onClick={this.selectSnippetTab}>Snippet</button><button className={this.state.currentTab === 'blueprint' ? 'btn-primary active' : 'btn-default'} onClick={this.selectBlueprintTab}>Blueprint</button>
|
||||
<button className={this.state.currentTab === 'code' ? 'btn-primary active' : 'btn-default'} onClick={this.selectCodeTab}>Code</button><button className={this.state.currentTab === 'note' ? 'btn-primary active' : 'btn-default'} onClick={this.selectNoteTab}>Note</button>
|
||||
</div>
|
||||
</div>
|
||||
{modalBody}
|
||||
@@ -56,5 +58,3 @@ var LaunchModal = React.createClass({
|
||||
)
|
||||
}
|
||||
})
|
||||
|
||||
module.exports = LaunchModal
|
||||
|
||||
@@ -1,23 +0,0 @@
|
||||
var React = require('react/addons')
|
||||
|
||||
var ModalBase = React.createClass({
|
||||
propTypes: {
|
||||
isOpen: React.PropTypes.bool,
|
||||
children: React.PropTypes.element,
|
||||
close: React.PropTypes.func
|
||||
},
|
||||
render: function () {
|
||||
if (this.props.isOpen) {
|
||||
return (
|
||||
<div ref='modal' onClick={this.props.close} className='ModalBase'>
|
||||
{this.props.children}
|
||||
</div>
|
||||
)
|
||||
}
|
||||
return (
|
||||
<div className='Modal hide'></div>
|
||||
)
|
||||
}
|
||||
})
|
||||
|
||||
module.exports = ModalBase
|
||||
@@ -1,7 +0,0 @@
|
||||
var React = require('react/addons')
|
||||
|
||||
var ModeSelect = React.createClass({
|
||||
|
||||
})
|
||||
|
||||
module.exports = ModeSelect
|
||||
@@ -1,33 +1,34 @@
|
||||
var React = require('react')
|
||||
|
||||
var PlanetActions = require('../Actions/PlanetActions')
|
||||
var Hq = require('../Services/Hq')
|
||||
|
||||
var SnippetDeleteModal = React.createClass({
|
||||
var PlanetStore = require('../Stores/PlanetStore')
|
||||
|
||||
module.exports = React.createClass({
|
||||
propTypes: {
|
||||
close: React.PropTypes.func,
|
||||
snippet: React.PropTypes.object
|
||||
planet: React.PropTypes.object,
|
||||
note: React.PropTypes.object,
|
||||
close: React.PropTypes.func
|
||||
},
|
||||
componentDidMount: function () {
|
||||
React.findDOMNode(this).focus()
|
||||
},
|
||||
stopPropagation: function (e) {
|
||||
e.stopPropagation()
|
||||
},
|
||||
handleKeyDown: function (e) {
|
||||
console.log(e)
|
||||
if (e.keyCode === 13 && e.metaKey) {
|
||||
e.preventDefault()
|
||||
this.submit()
|
||||
}
|
||||
},
|
||||
submit: function () {
|
||||
PlanetActions.deleteSnippet(this.props.snippet.id)
|
||||
var planet = this.props.planet
|
||||
Hq.destroyNote(planet.userName, planet.name, this.props.note.localId)
|
||||
.then(function (res) {
|
||||
PlanetStore.Actions.destroyNote(res.body)
|
||||
this.props.close()
|
||||
}.bind(this))
|
||||
.catch(function (err) {
|
||||
console.error(err)
|
||||
})
|
||||
},
|
||||
render: function () {
|
||||
return (
|
||||
<div tabIndex='3' onKeyDown={this.handleKeyDown} onClick={this.stopPropagation} className='SnippetDeleteModal modal'>
|
||||
<div className='NoteDeleteModal modal'>
|
||||
<div className='modal-header'>
|
||||
<h1>Delete Snippet</h1>
|
||||
<h1>Delete Note</h1>
|
||||
</div>
|
||||
<div className='modal-body'>
|
||||
<p>Are you sure to delete it?</p>
|
||||
@@ -42,5 +43,3 @@ var SnippetDeleteModal = React.createClass({
|
||||
)
|
||||
}
|
||||
})
|
||||
|
||||
module.exports = SnippetDeleteModal
|
||||
21
browser/main/Components/NoteEditModal.jsx
Normal file
21
browser/main/Components/NoteEditModal.jsx
Normal file
@@ -0,0 +1,21 @@
|
||||
var React = require('react')
|
||||
|
||||
var NoteForm = require('./NoteForm')
|
||||
|
||||
module.exports = React.createClass({
|
||||
propTypes: {
|
||||
close: React.PropTypes.func,
|
||||
note: React.PropTypes.object,
|
||||
planet: React.PropTypes.object
|
||||
},
|
||||
render: function () {
|
||||
return (
|
||||
<div className='NoteEditModal modal'>
|
||||
<div className='modal-header'>
|
||||
<h1>Edit Note</h1>
|
||||
</div>
|
||||
<NoteForm note={this.props.note} planet={this.props.planet} close={this.props.close}/>
|
||||
</div>
|
||||
)
|
||||
}
|
||||
})
|
||||
@@ -1,24 +1,19 @@
|
||||
var React = require('react/addons')
|
||||
var ReactRouter = require('react-router')
|
||||
var CodeEditor = require('./CodeEditor')
|
||||
var Catalyst = require('../Mixins/Catalyst')
|
||||
var Markdown = require('../Mixins/Markdown')
|
||||
var Select = require('react-select')
|
||||
var request = require('superagent')
|
||||
var PlanetActions = require('../Actions/PlanetActions')
|
||||
|
||||
var apiUrl = require('../../../config').apiUrl
|
||||
var Hq = require('../Services/Hq')
|
||||
|
||||
var LinkedState = require('../Mixins/LinkedState')
|
||||
var Markdown = require('../Mixins/Markdown')
|
||||
|
||||
var PlanetStore = require('../Stores/PlanetStore')
|
||||
|
||||
var CodeEditor = require('./CodeEditor')
|
||||
|
||||
var getOptions = function (input, callback) {
|
||||
request
|
||||
.get(apiUrl + 'tags/search')
|
||||
.query({name: input})
|
||||
.send()
|
||||
.end(function (err, res) {
|
||||
if (err) {
|
||||
callback(err)
|
||||
return
|
||||
}
|
||||
Hq.searchTag(input)
|
||||
.then(function (res) {
|
||||
callback(null, {
|
||||
options: res.body.map(function (tag) {
|
||||
return {
|
||||
@@ -26,96 +21,103 @@ var getOptions = function (input, callback) {
|
||||
value: tag.name
|
||||
}
|
||||
}),
|
||||
complete: true
|
||||
})
|
||||
complete: false
|
||||
})
|
||||
})
|
||||
.catch(function (err) {
|
||||
console.log(err)
|
||||
})
|
||||
}
|
||||
|
||||
var BlueprintForm = React.createClass({
|
||||
mixins: [Catalyst.LinkedStateMixin, ReactRouter.State, Markdown],
|
||||
var NoteForm = React.createClass({
|
||||
mixins: [LinkedState, ReactRouter.State, Markdown],
|
||||
propTypes: {
|
||||
planet: React.PropTypes.object,
|
||||
close: React.PropTypes.func,
|
||||
blueprint: React.PropTypes.object
|
||||
transitionTo: React.PropTypes.func,
|
||||
note: React.PropTypes.object
|
||||
},
|
||||
statics: {
|
||||
EDIT_MODE: 0,
|
||||
PREVIEW_MODE: 1
|
||||
},
|
||||
getInitialState: function () {
|
||||
var blueprint = Object.assign({
|
||||
var note = Object.assign({
|
||||
title: '',
|
||||
content: '',
|
||||
Tags: []
|
||||
}, this.props.blueprint)
|
||||
blueprint.Tags = blueprint.Tags.map(function (tag) {
|
||||
}, this.props.note)
|
||||
note.Tags = note.Tags.map(function (tag) {
|
||||
return {
|
||||
label: tag.name,
|
||||
value: tag.name
|
||||
}
|
||||
})
|
||||
return {
|
||||
blueprint: blueprint,
|
||||
mode: BlueprintForm.EDIT_MODE
|
||||
note: note,
|
||||
mode: NoteForm.EDIT_MODE
|
||||
}
|
||||
},
|
||||
componentDidMount: function () {
|
||||
React.findDOMNode(this.refs.title).focus()
|
||||
},
|
||||
handleTagsChange: function (selected, all) {
|
||||
var blueprint = this.state.blueprint
|
||||
blueprint.Tags = all
|
||||
this.setState({blueprint: blueprint})
|
||||
var note = this.state.note
|
||||
note.Tags = all
|
||||
this.setState({note: note})
|
||||
},
|
||||
handleContentChange: function (e, value) {
|
||||
var blueprint = this.state.blueprint
|
||||
blueprint.content = value
|
||||
this.setState({blueprint: blueprint})
|
||||
var note = this.state.note
|
||||
note.content = value
|
||||
this.setState({note: note})
|
||||
},
|
||||
togglePreview: function () {
|
||||
this.setState({mode: this.state.mode === BlueprintForm.EDIT_MODE ? BlueprintForm.PREVIEW_MODE : BlueprintForm.EDIT_MODE})
|
||||
this.setState({mode: this.state.mode === NoteForm.EDIT_MODE ? NoteForm.PREVIEW_MODE : NoteForm.EDIT_MODE})
|
||||
},
|
||||
submit: function () {
|
||||
console.log(this.state.blueprint)
|
||||
var blueprint = Object.assign({}, this.state.blueprint)
|
||||
blueprint.Tags = blueprint.Tags.map(function (tag) {
|
||||
var planet = this.props.planet
|
||||
var note = this.state.note
|
||||
note.Tags = note.Tags.map(function (tag) {
|
||||
return tag.value
|
||||
})
|
||||
if (this.props.blueprint == null) {
|
||||
var params = this.getParams()
|
||||
var userName = params.userName
|
||||
var planetName = params.planetName
|
||||
|
||||
PlanetActions.createBlueprint(userName + '/' + planetName, blueprint)
|
||||
if (this.props.note == null) {
|
||||
Hq.createNote(planet.userName, planet.name, this.state.note)
|
||||
.then(function (res) {
|
||||
var note = res.body
|
||||
PlanetStore.Actions.updateNote(note)
|
||||
this.props.close()
|
||||
this.props.transitionTo('notes', {userName: planet.userName, planetName: planet.name, localId: note.localId})
|
||||
}.bind(this))
|
||||
.catch(function (err) {
|
||||
console.error(err)
|
||||
})
|
||||
} else {
|
||||
var blueprintId = blueprint.id
|
||||
delete blueprint.id
|
||||
|
||||
PlanetActions.updateBlueprint(blueprintId, blueprint)
|
||||
}
|
||||
},
|
||||
handleKeyDown: function (e) {
|
||||
if (e.keyCode === 13 && e.metaKey) {
|
||||
this.submit()
|
||||
e.stopPropagation()
|
||||
Hq.updateNote(planet.userName, planet.name, this.props.note.localId, this.state.note)
|
||||
.then(function (res) {
|
||||
var note = res.body
|
||||
PlanetStore.Actions.updateNote(note)
|
||||
this.props.close()
|
||||
}.bind(this))
|
||||
}
|
||||
},
|
||||
render: function () {
|
||||
var content = this.state.mode === BlueprintForm.EDIT_MODE ? (
|
||||
var content = this.state.mode === NoteForm.EDIT_MODE ? (
|
||||
<div className='form-group'>
|
||||
<CodeEditor onChange={this.handleContentChange} code={this.state.blueprint.content} mode={'markdown'}/>
|
||||
<CodeEditor onChange={this.handleContentChange} code={this.state.note.content} mode={'markdown'}/>
|
||||
</div>
|
||||
) : (
|
||||
<div className='form-group relative'>
|
||||
<div className='previewMode'>Preview mode</div>
|
||||
<div className='marked' dangerouslySetInnerHTML={{__html: ' ' + this.markdown(this.state.blueprint.content)}}></div>
|
||||
<div className='marked' dangerouslySetInnerHTML={{__html: ' ' + this.markdown(this.state.note.content)}}></div>
|
||||
</div>
|
||||
)
|
||||
|
||||
return (
|
||||
<div onKeyDown={this.handleKeyDown} className='BlueprintForm'>
|
||||
<div className='NoteForm'>
|
||||
<div className='modal-body'>
|
||||
<div className='form-group'>
|
||||
<input ref='title' className='block-input' valueLink={this.linkState('blueprint.title')} placeholder='Title'/>
|
||||
<input ref='title' className='block-input' valueLink={this.linkState('note.title')} placeholder='Title'/>
|
||||
</div>
|
||||
{content}
|
||||
<div className='form-group'>
|
||||
@@ -123,7 +125,7 @@ var BlueprintForm = React.createClass({
|
||||
name='Tags'
|
||||
multi={true}
|
||||
allowCreate={true}
|
||||
value={this.state.blueprint.Tags}
|
||||
value={this.state.note.Tags}
|
||||
placeholder='Tags...'
|
||||
asyncOptions={getOptions}
|
||||
onChange={this.handleTagsChange}
|
||||
@@ -132,7 +134,7 @@ var BlueprintForm = React.createClass({
|
||||
</div>
|
||||
|
||||
<div className='modal-footer'>
|
||||
<button onClick={this.togglePreview} className={'btn-default' + (this.state.mode === BlueprintForm.PREVIEW_MODE ? ' active' : '')}>Preview mode</button>
|
||||
<button onClick={this.togglePreview} className={'btn-default' + (this.state.mode === NoteForm.PREVIEW_MODE ? ' active' : '')}>Preview mode</button>
|
||||
<div className='modal-control'>
|
||||
<button onClick={this.props.close} className='btn-default'>Cancel</button>
|
||||
<button onClick={this.submit} className='btn-primary'>Launch</button>
|
||||
@@ -143,4 +145,4 @@ var BlueprintForm = React.createClass({
|
||||
}
|
||||
})
|
||||
|
||||
module.exports = BlueprintForm
|
||||
module.exports = NoteForm
|
||||
@@ -3,22 +3,45 @@ var moment = require('moment')
|
||||
|
||||
var CodeViewer = require('../Components/CodeViewer')
|
||||
|
||||
var CodeEditModal = require('../Components/CodeEditModal')
|
||||
var CodeDeleteModal = require('../Components/CodeDeleteModal')
|
||||
var NoteEditModal = require('../Components/NoteEditModal')
|
||||
var NoteDeleteModal = require('../Components/NoteDeleteModal')
|
||||
|
||||
var Modal = require('../Mixins/Modal')
|
||||
var ForceUpdate = require('../Mixins/ForceUpdate')
|
||||
var Markdown = require('../Mixins/Markdown')
|
||||
|
||||
var PlanetArticleDetail = React.createClass({
|
||||
mixins: [ForceUpdate(60000), Markdown],
|
||||
module.exports = React.createClass({
|
||||
mixins: [ForceUpdate(60000), Markdown, Modal],
|
||||
propTypes: {
|
||||
article: React.PropTypes.object,
|
||||
onOpenEditModal: React.PropTypes.func,
|
||||
onOpenDeleteModal: React.PropTypes.func,
|
||||
showOnlyWithTag: React.PropTypes.func
|
||||
showOnlyWithTag: React.PropTypes.func,
|
||||
planet: React.PropTypes.object
|
||||
},
|
||||
getInitialState: function () {
|
||||
return {
|
||||
isEditModalOpen: false
|
||||
}
|
||||
},
|
||||
openEditModal: function () {
|
||||
switch (this.props.article.type) {
|
||||
case 'code' :
|
||||
this.openModal(CodeEditModal, {code: this.props.article, planet: this.props.planet})
|
||||
break
|
||||
case 'note' :
|
||||
this.openModal(NoteEditModal, {note: this.props.article, planet: this.props.planet})
|
||||
}
|
||||
},
|
||||
openDeleteModal: function () {
|
||||
switch (this.props.article.type) {
|
||||
case 'code' :
|
||||
this.openModal(CodeDeleteModal, {code: this.props.article, planet: this.props.planet})
|
||||
break
|
||||
case 'note' :
|
||||
this.openModal(NoteDeleteModal, {note: this.props.article, planet: this.props.planet})
|
||||
}
|
||||
},
|
||||
render: function () {
|
||||
var article = this.props.article
|
||||
if (article == null) {
|
||||
@@ -35,14 +58,14 @@ var PlanetArticleDetail = React.createClass({
|
||||
}.bind(this)) : (
|
||||
<a className='noTag'>Not tagged yet</a>
|
||||
)
|
||||
if (article.type === 'snippet') {
|
||||
if (article.type === 'code') {
|
||||
return (
|
||||
<div className='PlanetArticleDetail snippetDetail'>
|
||||
<div className='PlanetArticleDetail codeDetail'>
|
||||
<div className='viewer-header'>
|
||||
<i className='fa fa-code fa-fw'></i> {article.callSign} <small className='updatedAt'>{moment(article.updatedAt).fromNow()}</small>
|
||||
<span className='control-group'>
|
||||
<button onClick={this.props.onOpenEditModal} className='btn-default btn-square btn-sm'><i className='fa fa-edit fa-fw'></i></button>
|
||||
<button onClick={this.props.onOpenDeleteModal} className='btn-default btn-square btn-sm'><i className='fa fa-trash fa-fw'></i></button>
|
||||
<button onClick={this.openEditModal} className='btn-default btn-square btn-sm'><i className='fa fa-edit fa-fw'></i></button>
|
||||
<button onClick={this.openDeleteModal} className='btn-default btn-square btn-sm'><i className='fa fa-trash fa-fw'></i></button>
|
||||
</span>
|
||||
</div>
|
||||
<div className='viewer-body'>
|
||||
@@ -58,12 +81,12 @@ var PlanetArticleDetail = React.createClass({
|
||||
)
|
||||
}
|
||||
return (
|
||||
<div className='PlanetArticleDetail blueprintDetail'>
|
||||
<div className='PlanetArticleDetail noteDetail'>
|
||||
<div className='viewer-header'>
|
||||
<i className='fa fa-file-text-o fa-fw'></i> {article.title} <small className='updatedAt'>{moment(article.updatedAt).fromNow()}</small>
|
||||
<span className='control-group'>
|
||||
<button onClick={this.props.onOpenEditModal} className='btn-default btn-square btn-sm'><i className='fa fa-edit fa-fw'></i></button>
|
||||
<button onClick={this.props.onOpenDeleteModal} className='btn-default btn-square btn-sm'><i className='fa fa-trash fa-fw'></i></button>
|
||||
<button onClick={this.openEditModal} className='btn-default btn-square btn-sm'><i className='fa fa-edit fa-fw'></i></button>
|
||||
<button onClick={this.openDeleteModal} className='btn-default btn-square btn-sm'><i className='fa fa-trash fa-fw'></i></button>
|
||||
</span>
|
||||
</div>
|
||||
<div className='viewer-body'>
|
||||
@@ -74,5 +97,3 @@ var PlanetArticleDetail = React.createClass({
|
||||
)
|
||||
}
|
||||
})
|
||||
|
||||
module.exports = PlanetArticleDetail
|
||||
|
||||
@@ -5,15 +5,14 @@ var moment = require('moment')
|
||||
var ForceUpdate = require('../Mixins/ForceUpdate')
|
||||
var Markdown = require('../Mixins/Markdown')
|
||||
|
||||
var PlanetArticleList = React.createClass({
|
||||
var ProfileImage = require('../Components/ProfileImage')
|
||||
|
||||
module.exports = React.createClass({
|
||||
mixins: [ReactRouter.Navigation, ReactRouter.State, ForceUpdate(60000), Markdown],
|
||||
propTypes: {
|
||||
articles: React.PropTypes.array,
|
||||
showOnlyWithTag: React.PropTypes.func
|
||||
},
|
||||
handleKeyDown: function (e) {
|
||||
e.preventDefault()
|
||||
},
|
||||
render: function () {
|
||||
var articles = this.props.articles.map(function (article) {
|
||||
var tags = article.Tags.length > 0 ? article.Tags.map(function (tag) {
|
||||
@@ -24,14 +23,14 @@ var PlanetArticleList = React.createClass({
|
||||
<a className='noTag'>Not tagged yet</a>
|
||||
)
|
||||
var params = this.getParams()
|
||||
var isActive = article.type === 'snippet' ? this.isActive('snippets') && parseInt(params.localId, 10) === article.localId : this.isActive('blueprints') && parseInt(params.localId, 10) === article.localId
|
||||
var isActive = article.type === 'code' ? this.isActive('codes') && parseInt(params.localId, 10) === article.localId : this.isActive('notes') && parseInt(params.localId, 10) === article.localId
|
||||
|
||||
var handleClick
|
||||
|
||||
if (article.type === 'snippet') {
|
||||
if (article.type === 'code') {
|
||||
|
||||
handleClick = function () {
|
||||
this.transitionTo('snippets', {
|
||||
this.transitionTo('codes', {
|
||||
userName: params.userName,
|
||||
planetName: params.planetName,
|
||||
localId: article.localId
|
||||
@@ -39,14 +38,17 @@ var PlanetArticleList = React.createClass({
|
||||
}.bind(this)
|
||||
|
||||
return (
|
||||
<li onClick={handleClick} key={'snippet-' + article.id}>
|
||||
<div className={'articleItem snippetItem' + (isActive ? ' active' : '')}>
|
||||
<div className='itemHeader'>
|
||||
<div className='callSign'><i className='fa fa-code fa-fw'></i> {article.callSign}</div>
|
||||
<div className='updatedAt'>{moment(article.updatedAt).fromNow()}</div>
|
||||
<li onClick={handleClick} key={'code-' + article.id}>
|
||||
<div className={'articleItem' + (isActive ? ' active' : '')}>
|
||||
<div className='itemLeft'>
|
||||
<ProfileImage className='profileImage' size='25' email={article.User.email}/>
|
||||
<i className='fa fa-code fa-fw'></i>
|
||||
</div>
|
||||
<div className='itemRight'>
|
||||
<div className='updatedAt'>{moment(article.updatedAt).fromNow()}</div>
|
||||
<div className='description'>{article.description.length > 50 ? article.description.substring(0, 50) + ' …' : article.description}</div>
|
||||
<div className='tags'><i className='fa fa-tags'/>{tags}</div>
|
||||
</div>
|
||||
<div className='description'>{article.description.length > 50 ? article.description.substring(0, 50) + ' …' : article.description}</div>
|
||||
<div className='tags'><i className='fa fa-tags'/>{tags}</div>
|
||||
</div>
|
||||
<div className='divider'></div>
|
||||
</li>
|
||||
@@ -54,7 +56,7 @@ var PlanetArticleList = React.createClass({
|
||||
}
|
||||
|
||||
handleClick = function () {
|
||||
this.transitionTo('blueprints', {
|
||||
this.transitionTo('notes', {
|
||||
userName: params.userName,
|
||||
planetName: params.planetName,
|
||||
localId: article.localId
|
||||
@@ -62,13 +64,18 @@ var PlanetArticleList = React.createClass({
|
||||
}.bind(this)
|
||||
|
||||
return (
|
||||
<li onClick={handleClick} key={'blueprint-' + article.id}>
|
||||
<li onClick={handleClick} key={'note-' + article.id}>
|
||||
<div className={'articleItem blueprintItem' + (isActive ? ' active' : '')}>
|
||||
<div className='itemHeader'>
|
||||
<div className='callSign'><i className='fa fa-file-text-o fa-fw'></i> {article.title}</div>
|
||||
<div className='updatedAt'>{moment(article.updatedAt).fromNow()}</div>
|
||||
<div className='itemLeft'>
|
||||
<ProfileImage className='profileImage' size='25' email={article.User.email}/>
|
||||
<i className='fa fa-file-text-o fa-fw'></i>
|
||||
</div>
|
||||
|
||||
<div className='itemRight'>
|
||||
<div className='updatedAt'>{moment(article.updatedAt).fromNow()}</div>
|
||||
<div className='description'>{article.title}</div>
|
||||
<div className='tags'><i className='fa fa-tags'/>{tags}</div>
|
||||
</div>
|
||||
<div className='tags'><i className='fa fa-tags'/>{tags}</div>
|
||||
</div>
|
||||
<div className='divider'></div>
|
||||
</li>
|
||||
@@ -78,12 +85,10 @@ var PlanetArticleList = React.createClass({
|
||||
|
||||
return (
|
||||
<div className='PlanetArticleList'>
|
||||
<ul onKeyDown={this.handleKeyDown} tabIndex='2'>
|
||||
<ul>
|
||||
{articles}
|
||||
</ul>
|
||||
</div>
|
||||
)
|
||||
}
|
||||
})
|
||||
|
||||
module.exports = PlanetArticleList
|
||||
|
||||
@@ -1,26 +1,34 @@
|
||||
/* global localStorage */
|
||||
|
||||
var React = require('react/addons')
|
||||
var Catalyst = require('../Mixins/Catalyst')
|
||||
var Select = require('react-select')
|
||||
|
||||
var PlanetActions = require('../Actions/PlanetActions')
|
||||
var Hq = require('../Services/Hq')
|
||||
|
||||
var LinkedState = require('../Mixins/LinkedState')
|
||||
|
||||
var UserStore = require('../Stores/UserStore')
|
||||
var PlanetStore = require('../Stores/PlanetStore')
|
||||
|
||||
module.exports = React.createClass({
|
||||
mixins: [Catalyst.LinkedStateMixin],
|
||||
mixins: [LinkedState],
|
||||
propTypes: {
|
||||
transitionTo: React.PropTypes.func,
|
||||
close: React.PropTypes.func
|
||||
},
|
||||
getInitialState: function () {
|
||||
var currentUser = JSON.parse(localStorage.getItem('currentUser'))
|
||||
return {
|
||||
planetName: ''
|
||||
user: currentUser,
|
||||
planet: {
|
||||
name: '',
|
||||
OwnerId: currentUser.id,
|
||||
public: true
|
||||
}
|
||||
}
|
||||
},
|
||||
componentDidMount: function () {
|
||||
React.findDOMNode(this.refs.name).focus()
|
||||
this.unsubscribe = PlanetStore.listen(this.onListen)
|
||||
},
|
||||
componentWillUnmount: function () {
|
||||
this.unsubscribe()
|
||||
},
|
||||
onListen: function (res) {
|
||||
if (res.status === 'planetCreated') {
|
||||
@@ -28,26 +36,47 @@ module.exports = React.createClass({
|
||||
}
|
||||
},
|
||||
handleSubmit: function () {
|
||||
PlanetActions.createPlanet({
|
||||
name: this.state.planetName
|
||||
})
|
||||
},
|
||||
handleKeyDown: function (e) {
|
||||
if (e.keyCode === 13 && e.metaKey) {
|
||||
this.handleSubmit()
|
||||
return
|
||||
}
|
||||
if (e.keyCode === 27) {
|
||||
this.props.close()
|
||||
}
|
||||
},
|
||||
stopPropagation: function (e) {
|
||||
e.stopPropagation()
|
||||
Hq.createPlanet(this.state.user.name, this.state.planet)
|
||||
.then(function (res) {
|
||||
var planet = res.body
|
||||
|
||||
var currentUser = JSON.parse(localStorage.getItem('currentUser'))
|
||||
|
||||
var isNew = !currentUser.Planets.some(function (_planet, index) {
|
||||
if (planet.id === _planet) {
|
||||
currentUser.Planets.splice(index, 1, planet)
|
||||
return true
|
||||
}
|
||||
return false
|
||||
})
|
||||
if (isNew) currentUser.Planets.push(planet)
|
||||
|
||||
localStorage.setItem('currentUser', JSON.stringify(currentUser))
|
||||
UserStore.Actions.update(currentUser)
|
||||
this.props.transitionTo('planetHome', {userName: planet.userName, planetName: planet.name})
|
||||
this.props.close()
|
||||
}.bind(this))
|
||||
.catch(function (err) {
|
||||
console.error(err)
|
||||
})
|
||||
},
|
||||
render: function () {
|
||||
return (
|
||||
<div tabIndex='3' onKeyDown={this.handleKeyDown} onClick={this.stopPropagation} className='PlanetCreateModal modal'>
|
||||
<input ref='name' valueLink={this.linkState('planetName')} className='nameInput stripInput' placeholder='Crate new Planet'/>
|
||||
<div className='PlanetCreateModal modal'>
|
||||
<input ref='name' valueLink={this.linkState('planet.name')} className='nameInput stripInput' placeholder='Crate new Planet'/>
|
||||
|
||||
<div className='formField'>
|
||||
of
|
||||
<select valueLink={this.linkState('planet.OwnerId')}>
|
||||
<option value={this.state.user.id}>Me({this.state.user.name})</option>
|
||||
</select>
|
||||
as
|
||||
<select valueLink={this.linkState('planet.public')}>
|
||||
<option value={true}>Public</option>
|
||||
<option value={false}>Private</option>
|
||||
</select>
|
||||
</div>
|
||||
|
||||
<button onClick={this.handleSubmit} className='submitButton'>
|
||||
<i className='fa fa-check'/>
|
||||
</button>
|
||||
|
||||
@@ -1,16 +1,15 @@
|
||||
var shell = require('shell')
|
||||
|
||||
var React = require('react/addons')
|
||||
var ReactRouter = require('react-router')
|
||||
|
||||
var PlanetActions = require('../Actions/PlanetActions')
|
||||
|
||||
var PlanetHeader = React.createClass({
|
||||
module.exports = React.createClass({
|
||||
mixins: [ReactRouter.State],
|
||||
propTypes: {
|
||||
openSettingModal: React.PropTypes.func,
|
||||
currentPlanet: React.PropTypes.object,
|
||||
onSearchChange: React.PropTypes.func,
|
||||
search: React.PropTypes.string,
|
||||
openPersonalSettingModal: React.PropTypes.func
|
||||
fetchPlanet: React.PropTypes.func,
|
||||
onSearchChange: React.PropTypes.func,
|
||||
currentPlanet: React.PropTypes.object
|
||||
},
|
||||
getInitialState: function () {
|
||||
return {
|
||||
@@ -20,37 +19,37 @@ var PlanetHeader = React.createClass({
|
||||
componentDidMount: function () {
|
||||
React.findDOMNode(this.refs.search).focus()
|
||||
},
|
||||
interceptClick: function (e) {
|
||||
e.stopPropagation()
|
||||
handleLogoClick: function (e) {
|
||||
shell.openExternal('http://b00st.io')
|
||||
e.preventDefault()
|
||||
},
|
||||
refreshPlanet: function () {
|
||||
var params = this.getParams()
|
||||
PlanetActions.fetchPlanet(params.userName, params.planetName)
|
||||
refresh: function () {
|
||||
this.props.fetchPlanet()
|
||||
},
|
||||
render: function () {
|
||||
var currentPlanetName = this.props.currentPlanet.name
|
||||
var currentUserName = this.props.currentPlanet.userName
|
||||
|
||||
return (
|
||||
<div onClick={this.interceptClick} className='PlanetHeader'>
|
||||
<div className='PlanetHeader'>
|
||||
<div className='headerLabel'>
|
||||
<span className='userName'>{currentUserName}</span><br/>
|
||||
<span className='planetName'>{currentPlanetName}</span>
|
||||
<button onClick={this.props.openSettingModal} className='menuBtn'>
|
||||
<button className='menuBtn'>
|
||||
<i className='fa fa-chevron-down'></i>
|
||||
</button>
|
||||
</div>
|
||||
<div className='headerControl'>
|
||||
<div className='searchInput'>
|
||||
<i className='fa fa-search'/>
|
||||
<input onChange={this.props.onSearchChange} value={this.props.search} ref='search' tabIndex='1' type='text' className='inline-input circleInput' placeholder='Search...'/>
|
||||
<input onChange={this.props.onSearchChange} value={this.props.search} ref='search' type='text' className='inline-input circleInput' placeholder='Search...'/>
|
||||
</div>
|
||||
<button onClick={this.refreshPlanet} className='refreshButton'><i className='fa fa-refresh'/></button>
|
||||
<button onClick={this.props.openPersonalSettingModal} className='settingButton'><i className='fa fa-gears'/></button>
|
||||
<button onClick={this.refresh} className='refreshButton'><i className='fa fa-refresh'/></button>
|
||||
<a onClick={this.handleLogoClick} href='http://b00st.io' className='logo'>
|
||||
<img width='44' height='44' src='resources/favicon-230x230.png'/>
|
||||
</a>
|
||||
</div>
|
||||
</div>
|
||||
)
|
||||
}
|
||||
})
|
||||
|
||||
module.exports = PlanetHeader
|
||||
|
||||
@@ -1,20 +1,19 @@
|
||||
var React = require('react/addons')
|
||||
var ReactRouter = require('react-router')
|
||||
var Link = ReactRouter.Link
|
||||
var Navigation = ReactRouter.Navigation
|
||||
|
||||
var ProfileImage = require('./ProfileImage')
|
||||
var Modal = require('../Mixins/Modal')
|
||||
var LaunchModal = require('../Components/LaunchModal')
|
||||
|
||||
var PlanetNavigator = React.createClass({
|
||||
mixins: [Modal, Navigation],
|
||||
propTypes: {
|
||||
currentPlanet: React.PropTypes.shape({
|
||||
name: React.PropTypes.string,
|
||||
Users: React.PropTypes.array
|
||||
planet: React.PropTypes.shape({
|
||||
name: React.PropTypes.string
|
||||
}),
|
||||
search: React.PropTypes.string,
|
||||
openLaunchModal: React.PropTypes.func,
|
||||
openAddUserModal: React.PropTypes.func,
|
||||
toggleSnippetFilter: React.PropTypes.func,
|
||||
toggleBlueprintFilter: React.PropTypes.func
|
||||
toggleCodeFilter: React.PropTypes.func,
|
||||
toggleNoteFilter: React.PropTypes.func
|
||||
},
|
||||
getInitialState: function () {
|
||||
return {
|
||||
@@ -24,46 +23,33 @@ var PlanetNavigator = React.createClass({
|
||||
submitLaunchModal: function (ret) {
|
||||
this.setState({isLaunchModalOpen: false})
|
||||
},
|
||||
openLaunchModal: function () {
|
||||
this.openModal(LaunchModal, {planet: this.props.planet, transitionTo: this.transitionTo})
|
||||
},
|
||||
render: function () {
|
||||
var users = this.props.currentPlanet.Users.map(function (user) {
|
||||
return (
|
||||
<li key={'user-' + user.id}>
|
||||
<Link to='user' params={{userName: user.name}}>
|
||||
<ProfileImage className='userPhoto' size='44' email={user.email}/>
|
||||
<div className='userTooltip'>{user.profileName}</div>
|
||||
</Link>
|
||||
</li>
|
||||
)
|
||||
})
|
||||
|
||||
var keywords = this.props.search.split(' ')
|
||||
var usingSnippetFilter = keywords.some(function (keyword) {
|
||||
if (keyword === '$s') return true
|
||||
var usingCodeFilter = keywords.some(function (keyword) {
|
||||
if (keyword === '$c') return true
|
||||
return false
|
||||
})
|
||||
var usingBlueprintFilter = keywords.some(function (keyword) {
|
||||
if (keyword === '$b') return true
|
||||
var usingNoteFilter = keywords.some(function (keyword) {
|
||||
if (keyword === '$n') return true
|
||||
return false
|
||||
})
|
||||
|
||||
return (
|
||||
<div className='PlanetNavigator'>
|
||||
<button onClick={this.props.openLaunchModal} className='launchButton btn-primary btn-block'>
|
||||
<button onClick={this.openLaunchModal} className='launchButton btn-primary btn-block'>
|
||||
<i className='fa fa-rocket fa-fw'/> Launch
|
||||
</button>
|
||||
<nav>
|
||||
<a className={usingSnippetFilter && !usingBlueprintFilter ? 'active' : ''} onClick={this.props.toggleSnippetFilter}>
|
||||
<i className='fa fa-code fa-fw'/> Snippets
|
||||
<a className={usingCodeFilter && !usingNoteFilter ? 'active' : ''} onClick={this.props.toggleCodeFilter}>
|
||||
<i className='fa fa-code fa-fw'/> Codes
|
||||
</a>
|
||||
<a className={!usingSnippetFilter && usingBlueprintFilter ? 'active' : ''} onClick={this.props.toggleBlueprintFilter}>
|
||||
<i className='fa fa-file-text-o fa-fw'/> Blueprints
|
||||
<a className={!usingCodeFilter && usingNoteFilter ? 'active' : ''} onClick={this.props.toggleNoteFilter}>
|
||||
<i className='fa fa-file-text-o fa-fw'/> Notes
|
||||
</a>
|
||||
</nav>
|
||||
<div className='usersLabel'>Users</div>
|
||||
<ul className='users'>
|
||||
{users}
|
||||
<li onClick={this.props.openAddUserModal} className='addUserButton btn-default'><i className='fa fa-plus'/></li>
|
||||
</ul>
|
||||
</div>
|
||||
)
|
||||
}
|
||||
|
||||
@@ -1,37 +1,10 @@
|
||||
var React = require('react/addons')
|
||||
var request = require('superagent')
|
||||
var Select = require('react-select')
|
||||
|
||||
var Catalyst = require('../Mixins/Catalyst')
|
||||
|
||||
var ProfileImage = require('./ProfileImage')
|
||||
|
||||
var PlanetActions = require('../Actions/PlanetActions')
|
||||
|
||||
var apiUrl = require('../../../config').apiUrl
|
||||
|
||||
var getOptions = function (input, callback) {
|
||||
request
|
||||
.get(apiUrl + 'users/search')
|
||||
.query({name: input})
|
||||
.send()
|
||||
.end(function (err, res) {
|
||||
if (err) {
|
||||
callback(err)
|
||||
return
|
||||
}
|
||||
callback(null, {
|
||||
options: res.body.map(function (user) {
|
||||
return {
|
||||
label: user.name,
|
||||
value: user.name
|
||||
}
|
||||
}),
|
||||
complete: false
|
||||
})
|
||||
})
|
||||
}
|
||||
|
||||
module.exports = React.createClass({
|
||||
mixins: [Catalyst.LinkedStateMixin],
|
||||
propTypes: {
|
||||
@@ -48,10 +21,6 @@ module.exports = React.createClass({
|
||||
},
|
||||
activePlanetProfile: function () {
|
||||
this.setState({currentTab: 'planetProfile'})
|
||||
|
||||
},
|
||||
activeMembers: function () {
|
||||
this.setState({currentTab: 'members'})
|
||||
},
|
||||
saveProfile: function () {
|
||||
var currentPlanet = this.props.currentPlanet
|
||||
@@ -60,14 +29,6 @@ module.exports = React.createClass({
|
||||
handleChange: function (value) {
|
||||
this.setState({userName: value})
|
||||
},
|
||||
addUser: function () {
|
||||
PlanetActions.addUser(this.props.currentPlanet.userName + '/' + this.props.currentPlanet.name, this.state.userName)
|
||||
},
|
||||
removeUser: function (userName) {
|
||||
return function () {
|
||||
PlanetActions.removeUser(this.props.currentPlanet.userName + '/' + this.props.currentPlanet.name, userName)
|
||||
}.bind(this)
|
||||
},
|
||||
doubleCheckDeletePlanet: function () {
|
||||
if (this.state.isDeletePlanetChecked) {
|
||||
PlanetActions.deletePlanet(this.props.currentPlanet.userName, this.props.currentPlanet.name)
|
||||
@@ -84,61 +45,26 @@ module.exports = React.createClass({
|
||||
},
|
||||
render: function () {
|
||||
var content
|
||||
if (this.state.currentTab === 'planetProfile') {
|
||||
content = (
|
||||
<div className='planetProfile'>
|
||||
<div className='planetProfileForm'>
|
||||
<label>Planet name </label>
|
||||
<input valueLink={this.linkState('planetName')} className='inline-input'/>
|
||||
<button onClick={this.saveProfile} className='saveButton btn-primary'>Save</button>
|
||||
</div>
|
||||
|
||||
<div className='planetDeleteForm'>
|
||||
<div className='planetDeleteControl'>
|
||||
<div className={'toggle' + (this.state.isDeletePlanetChecked ? '' : ' hide')}>
|
||||
<div className='planetDeleteLabel'>Are you sure to delete this planet?</div>
|
||||
<button ref='deleteCancelButton' onClick={this.cancelDeletePlanet} className='cancelButton btn-default'>Cancel</button>
|
||||
</div>
|
||||
<button onClick={this.doubleCheckDeletePlanet} className='deleteButton btn-primary'>{!this.state.isDeletePlanetChecked ? 'Delete Planet' : 'Confirm'}</button>
|
||||
content = (
|
||||
<div className='planetProfile'>
|
||||
<div className='planetProfileForm'>
|
||||
<label>Planet name </label>
|
||||
<input valueLink={this.linkState('planetName')} className='inline-input'/>
|
||||
<button onClick={this.saveProfile} className='saveButton btn-primary'>Save</button>
|
||||
</div>
|
||||
|
||||
<div className='planetDeleteForm'>
|
||||
<div className='planetDeleteControl'>
|
||||
<div className={'toggle' + (this.state.isDeletePlanetChecked ? '' : ' hide')}>
|
||||
<div className='planetDeleteLabel'>Are you sure to delete this planet?</div>
|
||||
<button ref='deleteCancelButton' onClick={this.cancelDeletePlanet} className='cancelButton btn-default'>Cancel</button>
|
||||
</div>
|
||||
<button onClick={this.doubleCheckDeletePlanet} className='deleteButton btn-primary'>{!this.state.isDeletePlanetChecked ? 'Delete Planet' : 'Confirm'}</button>
|
||||
</div>
|
||||
</div>
|
||||
)
|
||||
} else {
|
||||
var members = this.props.currentPlanet.Users.map(function (user) {
|
||||
return (
|
||||
<li key={'user-' + user.id}>
|
||||
<ProfileImage className='userPhoto' size='44' email={user.email}/>
|
||||
<div className='userName'>{user.name}</div>
|
||||
<div className='userControl'>
|
||||
{this.props.currentPlanet.OwnerId !== user.id ? <button onClick={this.removeUser(user.name)} className='btn-default'>Delete</button> : <span className='ownerLabel'>Owner</span>}
|
||||
</div>
|
||||
</li>
|
||||
)
|
||||
}.bind(this))
|
||||
|
||||
content = (
|
||||
<div className='members'>
|
||||
<ul className='userList'>
|
||||
{members}
|
||||
</ul>
|
||||
<div className='addUserForm'>
|
||||
<div className='addUserLabel'>Invite user</div>
|
||||
<div className='addUserControl'>
|
||||
<Select
|
||||
name='userName'
|
||||
value={this.state.userName}
|
||||
placeholder='Username'
|
||||
asyncOptions={getOptions}
|
||||
onChange={this.handleChange}
|
||||
className='addUserSelect'
|
||||
/>
|
||||
<button onClick={this.addUser} className='addUserSubmit btn-primary'>Invite</button>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
)
|
||||
}
|
||||
</div>
|
||||
)
|
||||
|
||||
return (
|
||||
<div onClick={this.interceptClick} className='PlanetSettingModal modal'>
|
||||
@@ -146,7 +72,6 @@ module.exports = React.createClass({
|
||||
<h1>Planet setting</h1>
|
||||
<nav>
|
||||
<button className={this.state.currentTab === 'planetProfile' ? 'active' : ''} onClick={this.activePlanetProfile}><i className='fa fa-globe fa-fw'/> Planet profile</button>
|
||||
<button className={this.state.currentTab === 'members' ? 'active' : ''} onClick={this.activeMembers}><i className='fa fa-group fa-fw'/> Members</button>
|
||||
</nav>
|
||||
</div>
|
||||
|
||||
|
||||
@@ -1,19 +1,17 @@
|
||||
/* global localStorage */
|
||||
var React = require('react/addons')
|
||||
var ReactRouter = require('react-router')
|
||||
var Navigation = ReactRouter.Navigation
|
||||
var request = require('superagent')
|
||||
|
||||
var Catalyst = require('../Mixins/Catalyst')
|
||||
var LinkedState = require('../Mixins/LinkedState')
|
||||
|
||||
var ProfileImage = require('./ProfileImage')
|
||||
|
||||
var AuthActions = require('../Actions/AuthActions')
|
||||
|
||||
var AuthStore = require('../Stores/AuthStore')
|
||||
|
||||
var apiUrl = require('../../../config').apiUrl
|
||||
|
||||
module.exports = React.createClass({
|
||||
mixins: [Catalyst.LinkedStateMixin],
|
||||
mixins: [LinkedState, Navigation],
|
||||
propTypes: {
|
||||
close: React.PropTypes.func,
|
||||
currentUser: React.PropTypes.object
|
||||
@@ -32,10 +30,8 @@ module.exports = React.createClass({
|
||||
}
|
||||
},
|
||||
componentDidMount: function () {
|
||||
this.unsubscribe = AuthStore.listen(this.onListen)
|
||||
},
|
||||
componentWillUnmount: function () {
|
||||
this.unsubscribe()
|
||||
},
|
||||
onListen: function (res) {
|
||||
console.log(res)
|
||||
@@ -70,17 +66,6 @@ module.exports = React.createClass({
|
||||
this.setState({currentTab: 'logout'})
|
||||
},
|
||||
saveProfile: function () {
|
||||
this.setState({
|
||||
isUpdatingProfile: true,
|
||||
isUpdatingProfileDone: false,
|
||||
isUpdatingProfileFailed: false
|
||||
}, function () {
|
||||
AuthActions.updateProfile({
|
||||
profileName: this.state.profileName,
|
||||
name: this.state.userName,
|
||||
email: this.state.email
|
||||
})
|
||||
})
|
||||
},
|
||||
savePassword: function () {
|
||||
this.setState({
|
||||
@@ -160,7 +145,8 @@ module.exports = React.createClass({
|
||||
})
|
||||
},
|
||||
logOut: function () {
|
||||
AuthActions.logout()
|
||||
localStorage.removeItem('currentUser')
|
||||
localStorage.removeItem('token')
|
||||
},
|
||||
interceptClick: function (e) {
|
||||
e.stopPropagation()
|
||||
@@ -1,24 +0,0 @@
|
||||
var React = require('react')
|
||||
var SnippetForm = require('./SnippetForm')
|
||||
|
||||
var SnippetEditModal = React.createClass({
|
||||
propTypes: {
|
||||
close: React.PropTypes.func,
|
||||
snippet: React.PropTypes.object
|
||||
},
|
||||
stopPropagation: function (e) {
|
||||
e.stopPropagation()
|
||||
},
|
||||
render: function () {
|
||||
return (
|
||||
<div onClick={this.stopPropagation} className='SnippetEditModal modal'>
|
||||
<div className='modal-header'>
|
||||
<h1>Edit Snippet</h1>
|
||||
</div>
|
||||
<SnippetForm snippet={this.props.snippet} close={this.props.close}/>
|
||||
</div>
|
||||
)
|
||||
}
|
||||
})
|
||||
|
||||
module.exports = SnippetEditModal
|
||||
@@ -1,89 +0,0 @@
|
||||
var React = require('react/addons')
|
||||
var ReactRouter = require('react-router')
|
||||
var Link = ReactRouter.Link
|
||||
|
||||
var ModalBase = require('./ModalBase')
|
||||
var PlanetCreateModal = require('./PlanetCreateModal')
|
||||
var ProfileImage = require('./ProfileImage')
|
||||
|
||||
var AuthStore = require('../Stores/AuthStore')
|
||||
|
||||
module.exports = React.createClass({
|
||||
mixins: [ReactRouter.Navigation, ReactRouter.State],
|
||||
propTypes: {
|
||||
currentPlanet: React.PropTypes.object,
|
||||
currentUser: React.PropTypes.object
|
||||
},
|
||||
getInitialState: function () {
|
||||
return {
|
||||
isPlanetCreateModalOpen: false
|
||||
}
|
||||
},
|
||||
componentDidMount: function () {
|
||||
this.unsubscribe = AuthStore.listen(this.onLogout)
|
||||
document.addEventListener('keydown', this.handleKeyDown)
|
||||
},
|
||||
componentWillUnmount: function () {
|
||||
this.unsubscribe()
|
||||
document.removeEventListener('keydown', this.handleKeyDown)
|
||||
},
|
||||
onLogout: function () {
|
||||
this.transitionTo('login')
|
||||
},
|
||||
openPersonalSettingModal: function () {
|
||||
this.setState({isPersonalSettingModalOpen: true})
|
||||
},
|
||||
closePersonalSettingModal: function () {
|
||||
this.setState({isPersonalSettingModalOpen: false})
|
||||
},
|
||||
openPlanetCreateModal: function () {
|
||||
this.setState({isPlanetCreateModalOpen: true})
|
||||
},
|
||||
closePlanetCreateModal: function () {
|
||||
this.setState({isPlanetCreateModalOpen: false})
|
||||
},
|
||||
handleKeyDown: function (e) {
|
||||
if (e.metaKey && e.keyCode > 48 && e.keyCode < 58) {
|
||||
var planet = this.props.currentUser.Planets[e.keyCode - 49]
|
||||
if (planet != null) {
|
||||
this.transitionTo('planet', {userName: planet.userName, planetName: planet.name})
|
||||
}
|
||||
e.preventDefault()
|
||||
}
|
||||
},
|
||||
render: function () {
|
||||
var planets = this.props.currentUser.Planets.map(function (planet, index) {
|
||||
return (
|
||||
<li key={planet.id} className={this.props.currentPlanet != null && this.props.currentPlanet.userName === planet.userName && this.props.currentPlanet.name === planet.name ? 'active' : ''}>
|
||||
<Link to='planet' params={{userName: planet.userName, planetName: planet.name}}>
|
||||
{planet.name[0]}
|
||||
<div className='planetTooltip'>{planet.userName}/{planet.name}</div>
|
||||
</Link>
|
||||
<div className='shortCut'>⌘{index + 1}</div>
|
||||
</li>
|
||||
)
|
||||
}.bind(this))
|
||||
if (this.props.currentUser == null) {
|
||||
return (
|
||||
<div className='UserNavigator'>
|
||||
</div>
|
||||
)
|
||||
}
|
||||
|
||||
return (
|
||||
<div tabIndex='2' className='UserNavigator'>
|
||||
<Link to='userHome' params={{userName: this.props.currentUser.name}} className='userProfile'>
|
||||
<ProfileImage size='55' email={this.props.currentUser.email}/>
|
||||
</Link>
|
||||
<ul className='planetList'>
|
||||
{planets}
|
||||
</ul>
|
||||
<button onClick={this.openPlanetCreateModal} className='newPlanet'><i className='fa fa-plus'/></button>
|
||||
|
||||
<ModalBase isOpen={this.state.isPlanetCreateModalOpen} close={this.closePlanetCreateModal}>
|
||||
<PlanetCreateModal close={this.closePlanetCreateModal}/>
|
||||
</ModalBase>
|
||||
</div>
|
||||
)
|
||||
}
|
||||
})
|
||||
Reference in New Issue
Block a user