过滤后的渲染对象排序

时间:2018-09-11 09:17:44

标签: javascript react-bootstrap-typeahead

尝试显示带有react-bootstrap-typeahead的分类建议时,我遇到了问题。

JSON

{
  "Code": "ABC",
  "Name": "Random City, Town Office (ABC), Random Country",
  "CityName": "Random City",
  "CityCode": "ABC",
  "CountryName": "Random Country",
  "CountryCode": "XY",
  "Field": "Town Office"
},
{
  "Code": "CBA",
  "Name": "Random City, Town Office (CBA), Random Country",
  "CityName": "City",
  "CityCode": "CBA",
  "CountryName": "Country",
  "CountryCode": "CC",
  "Field": "Town Office"
}

如果期望的输出匹配,则应按城市按字母顺序搜索,如果不匹配,则应搜索国家/地区名称,然后按字母顺序对呈现的输出进行排序。

我尝试将回叫数据从typeahead的 filterBy 推入数组并进行排序,但是,由于未对服务中的JSON进行排序并且回叫数据是随机的,因此无法实现同样的目的。

还有其他方法可以实现相同目标吗?

<Typeahead
  {...this.state.typeProps}
  labelKey="Name"
  placeholder="Enter Origin..."
  bsSize="large"
  onChange={(selected) => {
    this.setState({ selected });
  }}
  filterBy={(option, props) => {
    if (this.filterAndPush(option, props)) {
      return true;
    }
    return false;
  }}
                }}
  options={this.state.originData}
  selected={this.state.selected}
/>

filterData = (option, props) => {
  const { text } = props;
  const { CityName, CityCode } = option;
  if (text) {
    if (CityName.toLowerCase().includes(text.toLowerCase())) {
      return true;
    } else if (CityCode.toLowerCase().includes(text.toLowerCase())) {
      return true;
    }
    return false;
  }
  return false;
}

filterAndPush = (option, props) => {
  //debugger;
  if (this.filterData(option, props)) {
    debugger;
    this.filterResultSet.push(option);
    this.filterResultSet.sort((a, b) => {
      if (a.CityName < b.CityName)
        return -1;
      if (a.CityName > b.CityName)
        return 1;
      return 0;
    });
    return true;
  }
  return false;
}

1 个答案:

答案 0 :(得分:1)

您可以通过两种方式对数据进行排序:

1)对选项进行预排序,然后再将其传递到options道具中。根据您的情况,这可能是最简单的方法。在您的render方法中,只需执行以下操作:

const options = this.state.originData.sort(sortCallback);

return (
  <Typeahead
    ...
    options={options}
  />
);

2)使用renderMenu对过滤的结果进行排序Check out the custom menu example观看此操作。基本上,您可以传递一个回调来接收过滤的结果并根据需要呈现它们:

_renderMenu(results, menuProps) {
  const items = results.sort(sortCallback);

  return (
    <Menu {...menuProps}>
      {items.map((item, index) => {
        <MenuItem key={index} option={item} position={index}>
          {...}
        </MenuItem>
      })}
    </Menu>
  );
}


render() {
  return (
    <Typeahead
      ...
      renderMenu={this._renderMenu}
    />
  );
}