-1

I'm trying to layout an n x n matrix using Reactstrap in a React component. My thought was to add a <Row> element before the start of every row, and an </Row> at the end of every row. But I can't get it to work with JSX, which keeps complaining Parsing error: Unexpected token, expected ","

I am passing an array of 'characters' to my component and trying to use Array.prototype.map in my render method to generate the JSX layout, laying out a matrix of CharacterCards, one for each component. Imagine a set of playing cards: I simply wish to lay them out in a square.

render() {
    const {props: {characters, rowSize, cardSize}} = this
    const rowUnit = 12 / rowSize

    const cardLayout = characters.map((character, i) => {
      let isRow = (i % rowSize === 0)
      let isRowFinish = ((i + 1) % rowSize === 0)
      return (
        {isRow && <Row>}
        <Col xs='6' md={rowUnit}>
          <CharacterCard key={i + Math.random()}
                         character={character}
                         cardSize={cardSize}
          />
        </Col>
        {isRowFinish && </Row>}
        )

        })

        return <div>
          <Container>
            {cardLayout}
          </Container>
        </div>
    }

but I get the following error

enter image description here

Where is the error I am clearly making? Thanks for any advice...

Cerulean
  • 5,543
  • 9
  • 59
  • 111

1 Answers1

2

Came up with two ways to render your grid. There is a slight difference in the behavior depending on how you wish to define rows.

You can see an example of both approaches on Stackblitz.

Method 1:

Place all the columns in a single row and use the column sizing props.

export default ({ characters, cardSize, rowSize }) => {
  const rowUnit = 12 / rowSize;
  const cardLayout = characters
    .map((character, i) => (
        <Col xs={6} sm={rowUnit} key={`col-${i}`}>
          <CharacterCard
            key={i + Math.random()}
            character={character}
            cardSize={cardSize}
          />
        </Col>
      )
    )

  return (
    <div>
      <Container>
        <Row>
        {cardLayout}
        </Row>
      </Container>
    </div>
  )
}

Method 2:

Reduce the array of columns into an array of rows.

export default ({ characters, cardSize, rowSize }) => {
  const rowUnit = 12 / rowSize;
  const cardLayout = characters
    .map((character, i) => (
        <Col sm={rowUnit} key={`col-${i}`}>
          <CharacterCard
            key={i + Math.random()}
            character={character}
            cardSize={cardSize}
          />
        </Col>
      )
    )
    .reduce((rows, col, index) => {
      let currentRow
      if (index % rowSize === 0) {
        currentRow = [];
        rows.push(currentRow)
      } else {
        currentRow = rows[rows.length - 1]
      }
      currentRow.push(col)
      return rows;
      }, []
    )
    .map((cols, i) => <Row key={`row-${i}`}>{...cols}</Row>)

  return (
    <div>
      <Container>
        {cardLayout}
      </Container>
    </div>
  )
}
webprojohn
  • 958
  • 7
  • 14