1
0
mirror of https://github.com/BoostIo/Boostnote synced 2025-12-13 17:56:25 +00:00

addTag search

This commit is contained in:
Rokt33r
2015-10-22 08:30:39 +09:00
parent c507dfa6c4
commit f56df7c16d
10 changed files with 63 additions and 14 deletions

View File

@@ -6,7 +6,7 @@ import ArticleNavigator from './HomePage/ArticleNavigator'
import ArticleTopBar from './HomePage/ArticleTopBar' import ArticleTopBar from './HomePage/ArticleTopBar'
import ArticleList from './HomePage/ArticleList' import ArticleList from './HomePage/ArticleList'
import ArticleDetail from './HomePage/ArticleDetail' import ArticleDetail from './HomePage/ArticleDetail'
import { findWhere, findIndex, pick } from 'lodash' import _, { findWhere, findIndex, pick } from 'lodash'
import keygen from 'boost/keygen' import keygen from 'boost/keygen'
import api from 'boost/api' import api from 'boost/api'
import auth from 'boost/auth' import auth from 'boost/auth'
@@ -14,6 +14,7 @@ import io from 'boost/socket'
const TEXT_FILTER = 'TEXT_FILTER' const TEXT_FILTER = 'TEXT_FILTER'
const FOLDER_FILTER = 'FOLDER_FILTER' const FOLDER_FILTER = 'FOLDER_FILTER'
const TAG_FILTER = 'TAG_FILTER'
class HomePage extends React.Component { class HomePage extends React.Component {
componentDidMount () { componentDidMount () {
@@ -83,14 +84,18 @@ function remap (state) {
}) })
// Filter articles // Filter articles
let filters = status.search.split(' ').map(key => key.trim()).filter(key => key.length > 0).map(key => { let filters = status.search.split(' ').map(key => key.trim()).filter(key => key.length > 0 && !key.match(/^#$/)).map(key => {
if (key.match(/^in:.+$/)) { if (key.match(/^in:.+$/)) {
return {type: FOLDER_FILTER, value: key.match(/^in:(.+)$/)[1]} return {type: FOLDER_FILTER, value: key.match(/^in:(.+)$/)[1]}
} }
if (key.match(/^#(.+)/)) {
return {type: TAG_FILTER, value: key.match(/^#(.+)$/)[1]}
}
return {type: TEXT_FILTER, value: key} return {type: TEXT_FILTER, value: key}
}) })
let folderFilters = filters.filter(filter => filter.type === FOLDER_FILTER) let folderFilters = filters.filter(filter => filter.type === FOLDER_FILTER)
let textFilters = filters.filter(filter => filter.type === TEXT_FILTER) let textFilters = filters.filter(filter => filter.type === TEXT_FILTER)
let tagFilters = filters.filter(filter => filter.type === TAG_FILTER)
if (activeUser.Folders != null) { if (activeUser.Folders != null) {
let targetFolders = activeUser.Folders.filter(folder => { let targetFolders = activeUser.Folders.filter(folder => {
@@ -110,6 +115,14 @@ function remap (state) {
}) })
}, articles) }, articles)
} }
if (tagFilters.length > 0) {
articles = tagFilters.reduce((articles, tagFilter) => {
return articles.filter(article => {
return _.find(article.Tags, tag => tag.name.match(new RegExp(tagFilter.value, 'i')))
})
}, articles)
}
} }
// Grab active article // Grab active article

View File

@@ -10,6 +10,7 @@ import Select from 'react-select'
import linkState from 'boost/linkState' import linkState from 'boost/linkState'
import api from 'boost/api' import api from 'boost/api'
import FolderMark from 'boost/components/FolderMark' import FolderMark from 'boost/components/FolderMark'
import TagLink from 'boost/components/TagLink'
var modeOptions = aceModes.map(function (mode) { var modeOptions = aceModes.map(function (mode) {
return { return {
@@ -86,13 +87,13 @@ export default class ArticleDetail extends React.Component {
renderIdle () { renderIdle () {
let { activeArticle, activeUser } = this.props let { activeArticle, activeUser } = this.props
let tags = activeArticle.Tags.length > 0 ? activeArticle.Tags.map(tag => { let tags = activeArticle.Tags.length > 0
return ( ? activeArticle.Tags.map(tag => {
<a key={tag.name}>{tag.name}</a> return (<TagLink key={tag.name} tag={tag}/>)
})
: (
<span className='noTags'>Not tagged yet</span>
) )
}) : (
<span className='noTags'>Not tagged yet</span>
)
let folder = findWhere(activeUser.Folders, {id: activeArticle.FolderId}) let folder = findWhere(activeUser.Folders, {id: activeArticle.FolderId})
let folderName = folder != null ? folder.name : '(unknown)' let folderName = folder != null ? folder.name : '(unknown)'

View File

@@ -4,6 +4,7 @@ import ModeIcon from 'boost/components/ModeIcon'
import moment from 'moment' import moment from 'moment'
import { switchArticle, NEW } from 'boost/actions' import { switchArticle, NEW } from 'boost/actions'
import FolderMark from 'boost/components/FolderMark' import FolderMark from 'boost/components/FolderMark'
import TagLink from 'boost/components/TagLink'
export default class ArticleList extends React.Component { export default class ArticleList extends React.Component {
handleArticleClick (key) { handleArticleClick (key) {
@@ -19,7 +20,7 @@ export default class ArticleList extends React.Component {
let articlesEl = articles.map(article => { let articlesEl = articles.map(article => {
let tags = Array.isArray(article.Tags) && article.Tags.length > 0 let tags = Array.isArray(article.Tags) && article.Tags.length > 0
? article.Tags.map(tag => { ? article.Tags.map(tag => {
return (<a key={tag.name}>{tag.name}</a>) return (<TagLink key={tag.name} tag={tag}/>)
}) })
: (<span>Not tagged yet</span>) : (<span>Not tagged yet</span>)

View File

@@ -53,7 +53,7 @@
<div id="content"></div> <div id="content"></div>
<script src="../../submodules/ace/src-min/ace.js"></script> <script src="../../submodules/ace/src-min/ace.js"></script>
<script type="text/javascript"> <script>
var version = require('remote').require('app').getVersion() var version = require('remote').require('app').getVersion()
document.title = 'Boost' + ((version == null || version.length === 0) ? ' DEV' : '') document.title = 'Boost' + ((version == null || version.length === 0) ? ' DEV' : '')
document.addEventListener('mousewheel', function(e) { document.addEventListener('mousewheel', function(e) {

View File

@@ -158,6 +158,7 @@ noTagsColor = #999
margin 2px margin 2px
font-size 10px font-size 10px
opacity 0.8 opacity 0.8
cursor pointer
&:hover &:hover
opacity 1 opacity 1
span.noTags span.noTags

View File

@@ -9,6 +9,7 @@ export const SWITCH_FOLDER = 'SWITCH_FOLDER'
export const SWITCH_MODE = 'SWITCH_MODE' export const SWITCH_MODE = 'SWITCH_MODE'
export const SWITCH_ARTICLE = 'SWITCH_ARTICLE' export const SWITCH_ARTICLE = 'SWITCH_ARTICLE'
export const SET_SEARCH_FILTER = 'SET_SEARCH_FILTER' export const SET_SEARCH_FILTER = 'SET_SEARCH_FILTER'
export const SET_TAG_FILTER = 'SET_TAG_FILTER'
// Status - mode // Status - mode
export const IDLE_MODE = 'IDLE_MODE' export const IDLE_MODE = 'IDLE_MODE'
@@ -84,3 +85,10 @@ export function setSearchFilter (search) {
data: search data: search
} }
} }
export function setTagFilter (tag) {
return {
type: SET_TAG_FILTER,
data: tag
}
}

View File

@@ -1,5 +1,5 @@
import React from 'react' import React from 'react'
let ReactDOM = require('react-dom')
var ace = window.ace var ace = window.ace
module.exports = React.createClass({ module.exports = React.createClass({
@@ -16,7 +16,7 @@ module.exports = React.createClass({
} }
}, },
componentDidMount: function () { componentDidMount: function () {
var el = React.findDOMNode(this.refs.target) var el = ReactDOM.findDOMNode(this.refs.target)
var editor = ace.edit(el) var editor = ace.edit(el)
editor.$blockScrolling = Infinity editor.$blockScrolling = Infinity
editor.setValue(this.props.code) editor.setValue(this.props.code)

20
lib/components/TagLink.js Normal file
View File

@@ -0,0 +1,20 @@
import React, { PropTypes } from 'react'
import store from '../store'
import { setTagFilter } from '../actions'
export default class TagLink extends React.Component {
handleClick (e) {
store.dispatch(setTagFilter(this.props.tag.name))
}
render () {
return (
<a onClick={e => this.handleClick(e)}>{this.props.tag.name}</a>
)
}
}
TagLink.propTypes = {
tag: PropTypes.shape({
name: PropTypes.string
})
}

View File

@@ -27,7 +27,7 @@ export default class CreateNewFolder extends React.Component {
api.createFolder(input) api.createFolder(input)
.then(res => { .then(res => {
console.log(res) console.log(res.body)
close() close()
}) })
.catch(err => { .catch(err => {

View File

@@ -1,6 +1,6 @@
import { combineReducers } from 'redux' import { combineReducers } from 'redux'
import { findIndex } from 'lodash' import { findIndex } from 'lodash'
import { SWITCH_USER, SWITCH_FOLDER, SWITCH_MODE, SWITCH_ARTICLE, SET_SEARCH_FILTER, USER_UPDATE, ARTICLE_REFRESH, ARTICLE_UPDATE, ARTICLE_DESTROY, IDLE_MODE, CREATE_MODE } from './actions' import { SWITCH_USER, SWITCH_FOLDER, SWITCH_MODE, SWITCH_ARTICLE, SET_SEARCH_FILTER, SET_TAG_FILTER, USER_UPDATE, ARTICLE_REFRESH, ARTICLE_UPDATE, ARTICLE_DESTROY, IDLE_MODE, CREATE_MODE } from './actions'
import auth from 'boost/auth' import auth from 'boost/auth'
const initialStatus = { const initialStatus = {
@@ -40,6 +40,7 @@ function status (state, action) {
case SWITCH_USER: case SWITCH_USER:
state.userId = action.data state.userId = action.data
state.mode = IDLE_MODE state.mode = IDLE_MODE
state.search = ''
return state return state
case SWITCH_FOLDER: case SWITCH_FOLDER:
state.mode = IDLE_MODE state.mode = IDLE_MODE
@@ -58,6 +59,10 @@ function status (state, action) {
state.search = action.data state.search = action.data
state.mode = IDLE_MODE state.mode = IDLE_MODE
return state return state
case SET_TAG_FILTER:
state.search = `#${action.data}`
state.mode = IDLE_MODE
return state
default: default:
if (state == null) return initialStatus if (state == null) return initialStatus
return state return state