2

I'm creating a form builder and need to be able to re-order the fields so I'd like to keep all the boilerplate drag / drop code in one re-usable place and a higher order component seemed like a good way to do that. So I have some code like this:

function SortableField(FieldComponent) {
    return class extends React.Component {
        render() {
            const { connectDragSource, connectDropTarget } = this.props;
            return connectDragSource(connectDropTarget(
                <FieldComponent {...this.props}/>
            ));
        }
    }
}
export default flow(
  DragSource('field', fieldSource, collect),
  DropTarget('field', fieldTarget, collectTarget)
)(SortableField);

Above that code is all the boilerplate drag / drop code.

I think wrap each field type component in that. The problem is if I run this I get the following error:

Uncaught TypeError: Cannot call a class as a function

Which I think is because it doesn't like me passing the SortableField function the DragSource / DragTarget partial function. Is there a way to make this work?

pogo
  • 2,287
  • 2
  • 25
  • 36

1 Answers1

1

You get this error, because your SortableField() returns a js class definition.

If you want to use FieldComponent you simply import it and then create a class which uses it. Your modified code below:

import FieldComponent from 'components/FieldComponent'

class SortableField extends React.Component {
    render() {
        const { connectDragSource, connectDropTarget } = this.props;
        return connectDragSource(connectDropTarget(
            <FieldComponent {...this.props}/>
        ));
    }
}
export default flow(
  DragSource('field', fieldSource, collect),
  DropTarget('field', fieldTarget, collectTarget)
)(SortableField);
Deividas
  • 6,437
  • 2
  • 26
  • 27
  • 1
    This isn't a higher order component anymore though. A higher order component is supposed to be a _function_ that accepts a component and then returns a component, not a component class itself. The code in this answer makes it so `SortableField` only works with `FieldComponent` and nothing else. – heylookltsme Jul 25 '17 at 14:11