React Form with file submission - javascript

I am now practicing upload a file by using Reactjs. This is a simple problem, but I could not connect the solution to axios. I know how the state and Form works, but my JavaScript callback values does not contains any of my given input. Or I could not find my values. Here is my case.
import React, {Component, Fragment} from 'react';
import tokamakConfig from './Configuration_icon_by_obsilion.png';
import {Form} from 'semantic-ui-react';
class Advance extends Component {
handleSubmit(event, values){
console.log(event);
console.log(values);
}
render() {
return (
<Fragment>
<h1>Please provide necessary information for the operation</h1>
<img src={tokamakConfig} alt={'tokamak configuration'} />
<Form onSubmit={this.handleSubmit}>
<Form.Group inline>
<label>Load input file</label>
<input name={'file'} type='file' />
</Form.Group>
<Form.Group inline>
<label>Comment</label>
<input name={'comment'} type={'text'} placeholder={'This is an advanced mode'}/>
</Form.Group>
<button type={'submit'}>Submit</button>
</Form>
</Fragment>
)
}
}
export default Advance;
In my console.log(). I got proxy object and onSubmit object. I could not find any of my input there. Then I have no idea how can I dispatch my value to axios
Question:
How to POST file from form to endpoint

<input type="file" onChange={ (e) => this.handleChange(e.target.files) } />
You need to use onChange event to get the file data.
handleChange(selectorFiles: FileList)
{
console.log(selectorFiles);
}
Then you need to get the file info inside the method

Related

how to send the redux-form data

I have login component. Here I have used redux-form. As I am new to react, can you help to get the form data from redux-form (how to submit the form data)?
<form onSubmit={this.onSubmit}>
<div className="padding5">
<Field name="email" type="email" component={RenderField} label="Email Id" />
</div>
<div className="padding5">
<Field name="Password" type="Password" component={RenderField} label="Password" />
</div>
<div className='buttonSection'>
<button type="submit" disabled={this.state.errors} className='buttonField padding5'>Reset Password</button>
</div>
</form>
Your code looks fine.
You have to use Form from redux-form:
import { reduxForm, Form } from 'redux-form';
// Your form component
<Form onSubmit={this.onSubmit}>
// Your form
</Form>
Make sure you have add redux-form to your redux store:
import { combineReducers } from 'redux';
import { reducer as formReducer } from 'redux-form';
const combinedReducers = combineReducers({
form: formReducer
})
and you are exporting your form wrapped:
import { reduxForm, Form } from 'redux-form';
// Your form
export default reduxForm({
form: 'name-of-form'
})(MyForm);
First you should use Form component from redux-form
import { reduxForm, Form, Field } from 'redux-form';
Also when connected to redux-form your component receives a handleSubmit prop you should use in your onSubmit event listener so it should be :
<Form onSubmit={this.props.handleSubmit(this.onSubmit)} />
Then your submit button will do the job calling this.onSubmit with a collection of values with field names as keys :
onSubmit = values => {
console.log(values); // => { email: '', password: '' }
}

ReactJS and autofocus

I have a react-bootstrap modal with an <input>. I want to set the autofocus attribute on the <input>
The following works fine, but shows a warning in the console
<input type="text" autofocus='true' />
Warning: Invalid DOM property `autofocus`. Did you mean `autoFocus`?
The following options do not work, in the sense that they do not focus the input when opening the modal:
<input type="text" autoFocus='true' />
<input type="text" autoFocus={true} />
<input type="text" autoFocus />
What is the recommended way of setting autofocus. Or how should I mute the warnings for the example that works well?
Note: This is react 16.8.6
If you're using React Hooks, add useCallback() to your component and add a ref={callback} to the form control:
import React, { useCallback } from 'react'
function InputComponent() {
const autoFocus = useCallback(el => el ? el.focus() : null, [])
return <input type="text" ref={autoFocus} />
}
export default InputComponent
You can replace the <input> with a React Bootstrap FormControl too.
Refs is what you want,
constructor(props) {
super(props);
this.myRef = React.createRef();
}
componentDidMount(){
this.myRef.current.focus();
}
<input type="text" ref={this.myRef} />
If you are using react hooks, you could write your own simple auto focus hook:
import { useEffect, useState } from "react";
export const useAutoFocus = (inputId: string) => {
const [initialized, setInitialized] = useState(false);
useEffect(() => {
if(!initialized) {
document.getElementById("email").focus();
setInitialized(true);
}
});
};
and the simply use e.g.
useAutoFocus("email")
in your form.

Passing custom props to component with redux-form 7

I am using the following libraries
"#material-ui/core": "^3.0.3",
"react": "^16.5.0",
"redux": "^4.0.0",
"redux-form": "^7.4.2",
How do I pass custom props to my component property of the redux-form <Field />?
According to this example from redux-form everything I have below should work, but it is not pulling the multiline={true} or rows={2} props into the <TextField /> component.
I am not sure how it is supposed to work as I am a novice with javascript. Any help would be appreciated.
PostForm.js
import React from 'react'
import { Link, withRouter } from 'react-router-dom';
import { reduxForm, Field } from 'redux-form';
import Button from '#material-ui/core/Button';
import TextField from '#material-ui/core/TextField'
class PostForm extends React.Component {
renderTextField = ({ input,
label,
meta: { error, touched } },
...custom) => {
return (
<TextField
name={label}
label={label}
{...input}
{...custom}
/>
);
};
onSubmit(event) {
event.preventDefault();
const { submitPost, history, formValues } = this.props;
submitPost(formValues.values, history);
}
render() {
<form onSubmit={this.onSubmit.bind(this)}>
<Field
name="title"
component={this.renderTextField}
label="Title"
/>
<Field
name="body"
component={this.renderTextField}
label="Body"
multiline={true}
rows={2}
/>
<div className={classes.buttonContainer}>
<Button to="/posts" component={Link} className={classes.button} color='secondary'>
Cancel
</Button>
<Button type='submit' className={classes.button} color='primary'>
Next
</Button>
</div>
</form>
}
}
export default reduxForm({
validate,
form: 'postForm',
destroyOnUnmount: false
})(PostForm)
To render multi line fields, you need to pass multiLine={true} (notice the camel casing - this is important). This is based on docs linked from https://github.com/erikras/redux-form-material-ui which seem like old version. According to newer docs, it seems multiline is all lowercase (leaving it here for posterity's sake).
Update
Also, ...custom is outside of the curly braces. Should be
renderTextField = ({ input, label, meta: { error, touched } , ...custom })
A bit about how Field passes props down - it's not enough to cover everything in this answer but I can give a few pointers to help you get started.
<Field ... /> is JSX notation. While JSX makes it easy to read and wirte HTML constructs, [React actually doesn't need JSX][1]. Internally, they all compile to pure JS functions (using React.createElement and other factory functions).
After that, passing ...custom etc. is just rest/spread operators introduced in ES6. They are shortcuts, and you can use React without them as well (meaning you can use just ES5 syntax).

How to get the value of TextInput in React Native without using state

I know I can do this using this.state but I want to make my code uniform. I have both web app and mobile app connected via an API.
This is what my ReactJS Web App looks like (this one works):
import React from 'react'
export default class SignIn extends React.Component {
signIn = () => {
var username = this.refs.username.value;
var password = this.refs.password.value;
console.log(username); //works
console.log(password); //works
}
render () {
return (
<div>
<input ref='username' placeholder='Username' />
<input ref='password' type='password' placeholder='Password' />
<button onClick={this.signIn.bind(this)}>Submit</button>
</div>
);
}
}
The above code does not use any states to get the values of the textboxes and I want to achieve the same thing in React Native.
In my mobile app I have the following code (this doesn't work):
import React from 'react';
import {Alert, TextInput, View, Button} from 'react-native';
export default class App extends React.Component {
signIn = () => {
var username = this.refs.username.value;
var password = this.refs.password.value;
Alert.alert(username); //doesn't work
Alert.alert(password); //doesn't work
}
render() {
return (
<View style={{marginTop: 60}}>
<TextInput ref='username' placeholder='Username' autoCapitalize='none' />
<TextInput ref='password' placeholder='Password' autoCapitalize='none' secureTextEntry={true} />
<Button title='Submit' onPress={this.signIn.bind(this)} />
</View>
);
}
}
I want the code to be uniform as possible but the same logic does not work in React Native. Is it possible to do this without using state?
Use this.refs.username._lastNativeText to get the inner text value of the username field.
However, going forward, this is not the best way to do it according to official RN guide. Refer to this SO answer for more details.

Redux form props & typescript

Was looking for years, didn't find anything worthy tho.
When I was working with flow, I could simply:
import { type FieldProps, FormProps } from 'redux-form';
Is there a similar (and that easy) way to properly set props to redux form in typescript?
Docs aren't saying anything about typescript, there's only a page for Flow typings.
However, I found that I can import something like propTypes from redux-form:
import { reduxForm, propTypes } from 'redux-form'
However - redux-form has nothing like propTypes exported, so docs are kinda deprecated.
Link: https://redux-form.com/7.2.1/docs/api/props.md/
Thanks in advance for any kind of help.
tl;dr class RegistrationForm extends React.PureComponent<any> {
what to drop here ^^^^^
You need to install the #types/redux-form package with your package manager. The #types/redux-form package includes types definitions for redux-form package.
Then you can import type definitions from redux-form, for example InjectedFormProps.
Your form that will be wrapped with reduxForm() should has props that extends InjectedFormProps<FormData = {}, P = {}>.
reduxForm() type is generic reduxForm<FormData = {}, P = {}>(...
See the example:
import * as React from 'react';
import { reduxForm, InjectedFormProps, Field } from 'redux-form';
import { IUser } from './index';
interface IProps {
message: string;
}
class UserForm extends React.Component<InjectedFormProps<IUser, IProps> & IProps> {
render() {
const { pristine, submitting, reset, handleSubmit, message } = this.props;
return (
<form onSubmit={handleSubmit}>
<div>{message}</div>
<div>
<label>First Name </label>
<Field
name="firstName"
component="input"
type="text"
placeholder="First Name"
/>
</div>
<div>
<label>Last Name </label>
<Field
name="lastName"
component="input"
type="text"
placeholder="Last Name"
/>
</div>
<div>
<button type="submit" disabled={pristine || submitting}>
Submit
</button>
<button type="button" disabled={pristine || submitting} onClick={reset}>
Clear Values
</button>
</div>
</form>
);
}
}
export default reduxForm<IUser, IProps>({
form: 'userForm',
})(UserForm);
The source code of #types/redux-form package is located here. You can see the types there and more complicated examples in the redux-form-tests.tsx file that is used for types checking.

Categories

Resources