summaryrefslogtreecommitdiff
path: root/ui/app/components/list_editor/index.js
blob: 4fff1cab9c0fded9e63679995c520e66fb96224d (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
//
// A simple list of items, with minus and plus buttons to add and remove
// items.
//

import React from 'react'
import {Button, ButtonGroup, ButtonToolbar, Glyphicon, FormControl} from 'react-bootstrap'

import './list_editor.less'

class ListEdit extends React.Component {

  static get defaultProps() {return{
    width: null,
    items: [
      'aaaaaaa',
      'bbbbbbb',
      'ccccccc'
    ],
    selected: null,  // string of the selected item
    onRemove: null,
    onAdd: null,
    onSelect: null,
    onKeyDown: null
  }}

  constructor(props) {
    super(props)
    this.click  = this.click.bind(this)
    this.add    = this.add.bind(this)
    this.remove = this.remove.bind(this)
  }

  row(str) {
    return this.props.items.indexOf(str)
  }

  click(e) {
    let row = parseInt(e.target.value)
    if (row >= 0) {
      if (this.props.onSelect) {
        this.props.onSelect(this.props.items[row])
      }
    }
  }

  add() {
    if (this.props.onAdd) {
      this.props.onAdd()
    }
  }

  remove() {
    if (this.props.onRemove) {
      let currentRow = this.row(this.props.selected)
      let newSelected = null
      if (this.props.items.length == currentRow + 1) {
        // if we remove the last item, set the new selected to be
        // the new last item.
        newSelected = this.props.items[currentRow - 1]
      } else {
        newSelected = this.props.items[currentRow + 1]
      }
      this.props.onRemove(this.props.selected, newSelected)
    }
  }

  componentDidMount() {
    if (this.props.onKeyDown) {
      this.listEditorDiv.addEventListener("keydown", this.props.onKeyDown)
    }
  }

  componentWillUnmount() {
    if (this.props.onKeyDown) {
      this.listEditorDiv.removeEventListener("keydown", this.props.onKeyDown)
    }
  }

  render() {
    let options = null
    if (this.props.items) {
      options = this.props.items.map((item, i) => {
        return <option className="list-option" key={i} value={i}>{item}</option>
      }, this)
    }
    return(
      <div
        ref={(div) => { this.listEditorDiv = div; }}
        className="list-editor" >
        <FormControl
          value={this.row(this.props.selected)}
          className="list-select"
          componentClass="select"
          size="5"
          onChange={this.click}
        >
          {options}
        </FormControl>
        <ButtonToolbar className="pull-right list-toolbar">
          <ButtonGroup>
            <Button onClick={this.add}>
              <Glyphicon glyph="plus" />
            </Button>
            <Button disabled={this.props.selected < 0} onClick={this.remove}>
              <Glyphicon glyph="minus" />
            </Button>
          </ButtonGroup>
        </ButtonToolbar>
      </div>
    )
  }

}

ListEdit.propTypes = {
  children: React.PropTypes.oneOfType([
    React.PropTypes.element,
    React.PropTypes.arrayOf(React.PropTypes.element)
  ])
}

export default ListEdit