Reputation: 308
I'm struggling to supply a callback function to a stateless functional child component. I have these two components:
export const FrontDeskGUI = () => {
const callback = (event) => console.log(event.target.value);
return (
<Col xs={12}>
<Panel collapsible defaultExpanded header="Empfang">
<ButtonGrid/>
</Panel>
<Panel collapsible defaultExpanded header="Verwaltung">
<ButtonGrid/>
</Panel>
<CommandInput callback={callback}/>
</Col>);
};
export const CommandInput = (callback) => {
const style = {
textTransform: 'uppercase'
};
return (
<Col xs={12}>
<form>
<FormGroup
controlId="command">
<FormControl
type="text"
style={style}
placeholder="Kürzel eingeben"
onChange={callback}/>
</FormGroup>
</form>
</Col>);
};
During rendering I get the following error:
Warning: Failed form propType: Invalid prop
onChange
of typeobject
supplied toinput
, expectedfunction
. Check the render method ofFormControl
.
Everytime I input something into the text input, I get the following error:
Uncaught TypeError: inputProps.onChange.call is not a function at Object.executeOnChange (LinkedValueUtils.js:132)
Is this at all possible in a stateless environment? Technically the supplied callback function is constant, so there is no inherent state in the CommandInput component. I've seen some answers messing around with binding functions to the correct this pointer but I'd like to avoid that if possible.
Upvotes: 2
Views: 2711
Reputation: 1074385
The single argument your SFC receives is a properties object with a property for each property used on the component in the JSX markup.
So either accept the property and use its callback
property:
export const CommandInput = (props) => {
// ...use props.callback...
}
or use parameter destructuring:
export const CommandInput = ({callback}) => {
// ^--------^---------------- note { }
// ... use callback...
}
Currently, you're trying to use the props object itself as the onChange
, which is why you get the error.
Example using destructuring:
const Example = ({callback}) =>
<div onClick={callback}>Click me</div>;
ReactDOM.render(
<Example callback={() => console.log("Clicked")} />,
document.getElementById("root")
);
<div id="root"></div>
<script src="https://cdnjs.cloudflare.com/ajax/libs/react/15.1.0/react.min.js"></script>
<script src="https://cdnjs.cloudflare.com/ajax/libs/react/15.1.0/react-dom.min.js"></script>
Upvotes: 3