问题描述
我正在尝试使用API的响应来更新表。响应来自一个组件,而表位于另一个组件。我可以看到我已经成功更新了组件中的上下文,但是它似乎没有传递给其他组件。我尝试过更新上下文,然后通过道具钻探传递它,但这也不起作用。如何获取包含表的组件以侦听上下文中的更改?我组件的代码如下:
其中更新了上下文的组件:
import React,{ useState,useContext } from 'react';
import { Card } from 'react-bootstrap';
import axios from 'axios';
import Cd from './types/Cd';
import Bond from './types/Bond';
import AssetContext from '../../context/AssetContext';
const fixedCard = (props) => {
const [fixed,setFixed] = useContext(AssetContext);
const [bond,setBond] = useState(false);
const assets = fixed;
const getResult = (event) => {
const form = event.currentTarget;
event.preventDefault();
event.stopPropagation();
let principle = form.principle.value;
const iLength = form.investmentLength.value / 12;
let compound = form.compound.value
let rate = form.rate.value;
let amount;
if (form.amount) {
amount = form.amount.value;
principle = principle * amount;
}
if (isNaN(rate) || rate < 0) {
alert("As much fun as it would be to calculate the result with \"" + rate + "\",it can't be done. Please enter a valid number");
} else {
if (compound === "Monthly") {
compound = 12;
} else if (compound === "Annually") {
compound = 1;
} else if (compound === "Quarterly") {
compound = 4;
} else {
compound = 365;
}
const headers = {
'Content-type': 'application/json','Access-Control-Allow-Origin': 'localhost:3000/','Access-Control-Allow-Methods': 'POST',}
const body = {
principle: principle,interestRate: rate,length: iLength,compoundFrequency: compound
}
axios.post("http://localhost:8080/compound-calculator/savings",body,{ headers })
.then(res => {
assets.push(res.data);
setFixed(assets);
fixed.map(asset => console.log(asset));
});
}
}
const linkCursor = { cursor: 'pointer' }
const toggleBond = () => {
setBond(true);
}
const toggleCert = () => {
setBond(false);
}
return (
<Card body>
<Card.Title>
Compount interest calculator
</Card.Title>
<Card.Link onClick={() => toggleCert()} style={linkCursor}>Certificate</Card.Link>
<Card.Link onClick={() => toggleBond()} style={linkCursor}>Bond</Card.Link>
<hr></hr>
<br></br>
{!bond && <Cd getResult={getResult} />}
{bond && <Bond getResult={getResult} />}
<br></br>
</Card>
);
}
export default React.memo(fixedCard);
根组件:
import React,useEffect } from 'react';
import 'bootstrap/dist/css/bootstrap.min.css';
import './GrowthCalculator.css';
import { Container,CardDeck } from 'react-bootstrap';
import FixedCard from '../components/fixedAssets/FixedCard';
import StockCard from '../components/StockCard';
import ResultCard from '../components/ResultCard';
import Navigation from '../components/Navigation';
import AssetContext from '../context/AssetContext.js';
import HowTo from '../components/HowTo';
const growthCalculator = (props) => {
const [fixedState,setFixedState] = useState([]);
const [stockState,setStockState] = useState([]);
const assets = [fixedState,setFixedState,stockState,setStockState];
return (
<main>
<AssetContext.Provider value={[...assets]}>
<Container>
<br></br>
<Navigation />
</Container>
<br></br>
<CardDeck>
<FixedCard /> //context updated here
<StockCard />
<ResultCard /> //trying to pass it here
</CardDeck>
<br></br>
<HowTo />
</AssetContext.Provider>
</main>
);
}
export default React.memo(growthCalculator);
我正在尝试将其传递给组件(此处的布局仍在进行中):
import React,{ useContext,useState } from 'react';
import { Card,Row,Col,Table } from 'react-bootstrap';
import AssetContext from '../context/AssetContext';
const resultCard = (props) => {
// eslint-disable-next-line
const [fixed,setFixed,stocks,setStocks] = useContext(AssetContext);
return (
<Card body>
<Card.Title>
Result card
</Card.Title>
<br></br>
<hr></hr>
<br></br>
<section>
<Row>
<Col>
<Table striped borderless hover size="sm" variant="secondary" responsive>
<thead>
<tr>
<th>
Compounding assets
</th>
</tr>
</thead>
<tbody>
//This doesn't render anything when fixed is updated in FixedCard.js
{fixed.map(asset => (
<tr>
<td>
${asset.principle}
</td>
<td>
total: ${asset.endValue}
</td>
</tr>))
}
</tbody>
</Table>
</Col>
<Col>
<Table striped borderless hover size="sm" variant="secondary" responsive>
<thead>
<tr>
<th>
Stocks
</th>
</tr>
</thead>
<tbody>
<tr>
<td>
Ticker
</td>
<td>
Fair price
</td>
<td>
discount price
</td>
</tr>
</tbody>
</Table>
</Col>
</Row>
</section>
</Card>
);
}
export default resultCard;
要重申我的问题,如何获得resultCard来监听AssetContext中的更改?
谢谢
解决方法
要听更改然后实施更改,我要做的是使用useeffect,其中我必须听更改并进行更改。例如,您可以将来自api的传入响应作为道具传递给组件。在子组件中,您可以像这样使用useEffect
useEffect(() => {
code here or change states,whichever you need to do
})
},[props.responseIncomingFromParent])
让我知道这是否可行...
,另一个问题给出的答案是,我需要将上下文变量扩展为另一个常量,然后使用该常量。
import 'package:path/path.dart';
import 'package:sqflite/sqflite.dart';
import 'package:sql_demo/models/product.dart';
class DbHelper {
//Creates a singleton class (it only creates once)
static final DbHelper _singleton = DbHelper._internal();
factory DbHelper() => _singleton;
DbHelper._internal();
//Creating an object of type database
static Database _database;
//Initializing or creating the database named mydb.db
//Creating a products table with necessary fields
Future<Database> initDatabase() async {
//If this class was never instaciated,we will execute this method,otherwise return
if (_database != null) return _database;
String path = join(await getDatabasesPath(),'mydb.db');
_database = await openDatabase(
path,version: 1,onCreate: (Database db,int v) async {
await db.execute(
'CREATE TABLE Products (id INTEGER PRIMARY KEY AUTOINCREMENT,name TEXT,description TEXT,price REAL)');
},);
return _database;
}
//Select all products
Future<List> getProducts() async {
Database db = await initDatabase();
return await db.query('Products');
}
//Create new product
Future<int> createProduct(Product product) async {
Database db = await initDatabase();
print('Product added');
return await db.insert(
'Products',product.toMap(),);
}
//Update product
Future<int> updateProduct(Product product) async {
Database db = await initDatabase();
return await db.update(
'Products',where: 'id=?',whereArgs: [product.id],);
}
//Delete a product
Future<int> deleteProduct(int productID) async {
Database db = await initDatabase();
return await db.delete('Products',whereArgs: [productID]);
}
}