0

React doesn't render the element when I use this form of code:

class ListaPratitelja extends React.Component {
    constructor(props) {
        super(props);
    }

    render() {
        const items = this.props.pratitelji;
        const listItems = items.map((name, index) => {
            e(Pratitelj, { key: index, name: name });
        });
        return listItems;
    }
}

I've used a debugger to see what's going on, and the e function (which is just React.createElement) returns undefined.

But it works just fine when I use it like this:

class ListaPratitelja extends React.Component {
    constructor(props) {
        super(props);
    }

    render() {
        const items = this.props.pratitelji;
        const listItems = items.map((name, index) => e(Pratitelj, { key: index, name: name }));
        return listItems;
    }
}

The question is why? Is this a bug or I did something wrong in the first example. Also this is the full code:

'use strict';

const e = React.createElement;

class ListaPratitelja extends React.Component {
    constructor(props) {
        super(props);
    }

    render() {
        const items = this.props.pratitelji;
        const listItems = items.map((name, index) => e(Pratitelj, { key: index, name: name }));
        return listItems;
    }
}

class Pratitelj extends React.Component {
    constructor(props) {
        super(props);
        this.state = { deleted: false };

        this.handleDeleteChange = this.handleDeleteChange.bind(this);
    }

    handleDeleteChange(deletedState) {
        this.setState({ deleted: deletedState });
    }

    render() {
        console.log("rendered");
        if (this.state.deleted) {
            return '';
        }

        return e(
            'div',
            null,
            e(PratiteljIme, { name: this.props.name }),
            e(PratiteljDeleteButton, { handleDeleteChange: this.handleDeleteChange})
        );
    }
}

class PratiteljIme extends React.Component {
    constructor(props) {
        super(props);
    }

    render() {
        return e(
            "span",
            null,
            this.props.name)
    }
}

class PratiteljDeleteButton extends React.Component {
    constructor(props) {
        super(props);
    }

    render() {
        return e(
            "button",
            { type: "button", "onClick": this.props.handleDeleteChange},
            "X"
            )
    }
}

function loadListaPratitelja(pratitelji) {
    const lista = pratitelji.split(",");
    const domContainer = document.querySelector('#listaPratitelja');
    ReactDOM.render(e(ListaPratitelja, {pratitelji: lista}), domContainer);
}

The input variable "pratitelji" is just a string with a couple of CSV (for ex. p1,p2,p3,p4). The versions of react I use are these: https://unpkg.com/react@16/umd/react.development.js https://unpkg.com/react-dom@16/umd/react-dom.development.js The browser I tested it on is the latest version of firefox for development.

Warix3
  • 91
  • 1
  • 10
  • 2
    An arrow function without a body `() => ...` will implicitly return the one and only expression, but an arrow function with a body `() => { ... }` is like any other function in that you need to explicitly `return` a value from it. – Tholle Nov 08 '18 at 17:08

2 Answers2

1

with using { and } you are creating a function that doesn't return anything, unless you return something. Hence .map will return an array filled with undefined.

Daniel A. White
  • 174,715
  • 42
  • 343
  • 413
0

Update your code to this:

const listItems = items.map((name, index) => {
    return e(Pratitelj, { key: index, name: name });
});

If you open up a function after the arrow, you must state what you're returning.

Keith Brewster
  • 1,651
  • 1
  • 13
  • 24