ResultList.js (2622B)
1 /* This Source Code Form is subject to the terms of the Mozilla Public 2 * License, v. 2.0. If a copy of the MPL was not distributed with this 3 * file, You can obtain one at <http://mozilla.org/MPL/2.0/>. */ 4 5 import React, { Component } from "devtools/client/shared/vendor/react"; 6 import { li, div, ul } from "devtools/client/shared/vendor/react-dom-factories"; 7 import PropTypes from "devtools/client/shared/vendor/react-prop-types"; 8 9 import DebuggerImage from "./DebuggerImage"; 10 11 const classnames = require("resource://devtools/client/shared/classnames.js"); 12 13 import { scrollList } from "../../utils/result-list"; 14 15 export default class ResultList extends Component { 16 static defaultProps = { 17 size: "small", 18 role: "listbox", 19 }; 20 21 static get propTypes() { 22 return { 23 items: PropTypes.array.isRequired, 24 role: PropTypes.oneOf(["listbox"]), 25 selectItem: PropTypes.func.isRequired, 26 selected: PropTypes.number.isRequired, 27 size: PropTypes.oneOf(["big", "small"]), 28 }; 29 } 30 31 constructor(props) { 32 super(props); 33 this.ref = React.createRef(); 34 } 35 36 componentDidUpdate() { 37 if (this.ref.current.childNodes) { 38 scrollList(this.ref.current.childNodes, this.props.selected); 39 } 40 } 41 42 renderListItem = (item, index) => { 43 if (item.value === "/" && item.title === "") { 44 item.title = "(index)"; 45 } 46 47 const { selectItem, selected } = this.props; 48 const props = { 49 onClick: event => selectItem(event, item, index), 50 key: `${item.id}${item.value}${index}`, 51 title: item.value, 52 "aria-labelledby": `${item.id}-title`, 53 "aria-describedby": `${item.id}-subtitle`, 54 role: "option", 55 className: classnames("result-item", { 56 selected: index === selected, 57 }), 58 }; 59 60 return li( 61 props, 62 item.icon && 63 div( 64 { 65 className: "icon", 66 }, 67 React.createElement(DebuggerImage, { 68 name: item.icon, 69 }) 70 ), 71 div( 72 { 73 id: `${item.id}-title`, 74 className: "title", 75 }, 76 item.title 77 ), 78 item.subtitle != item.title 79 ? div( 80 { 81 id: `${item.id}-subtitle`, 82 className: "subtitle", 83 }, 84 item.subtitle 85 ) 86 : null 87 ); 88 }; 89 render() { 90 const { size, items, role } = this.props; 91 return ul( 92 { 93 ref: this.ref, 94 className: classnames("result-list", size), 95 id: "result-list", 96 role, 97 "aria-live": "polite", 98 }, 99 items.map(this.renderListItem) 100 ); 101 } 102 }