Javascript 不带按钮提交反应表单
尝试使用React中的select按钮处理窗体。选择按钮用于电子商务产品详细信息页面的不同产品变体。基本上,如何让组件在用户将大小/颜色更改为较小(或API具有的任何产品变体)时自动处理表单,因此在我发布时,它在请求中具有变体 理论上,我可以只按一个提交按钮,但他/她每次从小型变为中型时都必须重新提交Javascript 不带按钮提交反应表单,javascript,reactjs,Javascript,Reactjs,尝试使用React中的select按钮处理窗体。选择按钮用于电子商务产品详细信息页面的不同产品变体。基本上,如何让组件在用户将大小/颜色更改为较小(或API具有的任何产品变体)时自动处理表单,因此在我发布时,它在请求中具有变体 理论上,我可以只按一个提交按钮,但他/她每次从小型变为中型时都必须重新提交 import React, { Fragment } from 'react' import axios from 'axios' import { connect } from "react-r
import React, { Fragment } from 'react'
import axios from 'axios'
import { connect } from "react-redux";
import { withRouter } from 'react-router-dom'
import { productDetailURL, addToCartURL } from '../constants'
import { fetchCart } from "../store/actions/cart";
import { authAxios } from '../utils'
class ProductDetail extends React.Component {
state = {
loading: false,
error: null,
formData: {},
data: []
};
handleChange = (e) => {
const { formData } = this.state
const updatedFormData = {
...formData,
[e.target.name]: e.target.value
}
this.setState({formData: updatedFormData})
}
handleFormatData = formData => {
// convert {colour: 1, size: 2} to [1,2] - they're all variations
return Object.keys(formData).map(key => {
return formData[key];
});
};
componentDidMount() {
const {match: { params }} = this.props
axios
.get(productDetailURL(params.productID))
.then(res => {
this.setState({ data: res.data, loading: false });
})
.catch(err => {
this.setState({ error: err, loading: false });
});
}
handleAddToCart = slug => {
this.setState({ loading: true });
const { formData } = this.state
const variations = this.handleFormatData(formData)
console.log(variations)
authAxios
.post(addToCartURL, { slug, variations })
.then(res => {
this.setState({ loading: false });
})
.catch(err => {
this.setState({ error: err, loading: false });
});
};
render() {
console.log(this.state)
const { data, error, loading, formData } = this.state;
const item = data
return (
<div>
<div class="container">
{error && (
<div class="alert alert-danger" role="alert">
{JSON.stringify(error) }
</div>
)}
{loading && (
<div class="spinner-border" role="status">
<span class="sr-only">Loading...</span>
</div>
)}
<div class="card">
<div class="row no-gutters">
<aside class="col-md-6">
<article class="gallery-wrap">
<div class="img-big-wrap">
<div> <a href="#"><img src="/images/items/12.jpg"></img></a></div>
</div>
<div class="thumbs-wrap">
<a href="#" class="item-thumb"> <img src="/images/items/12.jpg"></img></a>
<a href="#" class="item-thumb"> <img src="/images/items/12-1.jpg"></img></a>
<a href="#" class="item-thumb"> <img src="/images/items/12-2.jpg"></img></a>
</div>
</article>
</aside>
<main class="col-md-6 border-left">
<article class="content-body">
<h2 class="title">{item.title}</h2>
<div class="rating-wrap my-3">
<ul class="rating-stars">
<li class="stars-active">
<i class="fa fa-star"></i> <i class="fa fa-star"></i>
<i class="fa fa-star"></i> <i class="fa fa-star"></i>
<i class="fa fa-star"></i>
</li>
<li>
<i class="fa fa-star"></i> <i class="fa fa-star"></i>
<i class="fa fa-star"></i> <i class="fa fa-star"></i>
<i class="fa fa-star"></i>
</li>
</ul>
<small class="label-rating text-muted">132 reviews</small>
<small class="label-rating text-success"> <i class="fa fa-clipboard-check"></i> 154 orders </small>
</div>
<div class="mb-3">
<var class="price h4">${item.price}</var>
</div>
<p>{item.description}</p>
<hr></hr>
<div class="form-row">
<div class="form-group col-md flex-grow-0">
<label>Quantity</label>
<div class="input-group mb-3 input-spinner">
<div class="input-group-prepend">
<button class="btn btn-light" type="button" id="button-plus"> + </button>
</div>
<input type="text" class="form-control" value="1"></input>
<div class="input-group-append">
<button class="btn btn-light" type="button" id="button-minus"> − </button>
</div>
</div>
</div>
<div class="form-group col-md flex-grow-0">
<form onSubmit={this.handleFormatData}>
{data.variations &&
data.variations.map(v => {
const name = v.name.toLowerCase()
return (
<Fragment key={v.id}>
{/* <div class="card"> */}
<div class="card-body">
<div class="form-inline d-inline-flex ml-luto">
<label as="h3">{v.name}</label>
<select className="ml-2 form-control" name={name} onChange={this.handleChange}>
{v.item_variations.map(iv => {
return (
<option
onChange={this.handleChange}
key={iv.id}
value={iv.id}
>
{iv.value}
</option>
);
})}
</select>
</div>
</div>
{/* </div> */}
</Fragment>
);
})}
</form>
</div>
</div>
<a href="#" class="btn btn-primary"> Buy now </a>
<a onClick={() => this.handleAddToCart(item.slug)} class="btn btn-outline-primary"> <span class="text">Add to cart</span> <i class="fas fa-shopping-cart"></i> </a>
</article>
</main>
</div>
</div>
</div>
</div>
)
}
}
const mapDispatchToProps = dispatch => {
return {
refreshCart: () => dispatch(fetchCart())
};
};
export default withRouter(
connect(
null,
mapDispatchToProps
)(ProductDetail)
);
import React,{Fragment}来自“React”
从“axios”导入axios
从“react redux”导入{connect};
从“react router dom”导入{withRouter}
从“../constants”导入{productDetailURL,addToCartURL}
从“./store/actions/cart”导入{fetchCart};
从“../utils”导入{authAxios}
类ProductDetail扩展了React.Component{
状态={
加载:false,
错误:null,
formData:{},
数据:[]
};
handleChange=(e)=>{
const{formData}=this.state
常量updatedFormData={
…表格数据,
[e.target.name]:e.target.value
}
this.setState({formData:updatedFormData})
}
handleFormatData=formData=>{
//将{color:1,size:2}转换为[1,2]-它们都是变体
返回Object.keys(formData.map)(key=>{
返回formData[键];
});
};
componentDidMount(){
常量{match:{params}}=this.props
axios
.get(productDetailURL(params.productID))
。然后(res=>{
this.setState({data:res.data,load:false});
})
.catch(错误=>{
this.setState({error:err,load:false});
});
}
HandLeadToCart=slug=>{
this.setState({loading:true});
const{formData}=this.state
常量变量=this.handleFormatData(formData)
console.log(变体)
奥塔克索斯
.post(addToCartURL,{slug,variances})
。然后(res=>{
this.setState({loading:false});
})
.catch(错误=>{
this.setState({error:err,load:false});
});
};
render(){
console.log(this.state)
const{data,error,loading,formData}=this.state;
常量项=数据
返回(
{错误&&(
{JSON.stringify(错误)}
)}
{加载&&(
加载。。。
)}
this.handleAddToCart(item.slug)}class=“btn btn outline primary”>添加到购物车
)
}
}
const mapDispatchToProps=调度=>{
返回{
refreshCart:()=>分派(fetchCart())
};
};
使用路由器导出默认值(
连接(
无效的
mapDispatchToProps
)(产品详情)
);
欢迎来到StackOverflow!因此,从您的问题来看,您似乎希望在您的本地州存储一些用户偏好(产品变体),并希望在提交表单之前可以使用这些偏好(产品变体)?看起来你是对的!我只看到一个bug-您在选择标记和选项上都有this.handleChange
。您只需要选择:)上的onChange处理程序,我这样做了,并将add-to-cart移动到表单内部。工作!非常感谢。完美的我还要说的是,您不必只使用
标记来提交表单。您也可以在onClick上执行相同的操作。您可以通过任何方式单独存储表单状态,也可以使用提交处理程序。