如何在不重新渲染的情况下正确设置组件的状态?

时间:2018-01-09 18:57:09

标签: javascript reactjs

我正在尝试使用React创建一个宏计算器。

我有一个setState的点击处理程序,但是当组件刷新时,一切都不会保存在状态中(我通过转到React Dev工具并查看组件来检查)。

我很确定这是因为当组件重新渲染时,状态会重新初始化为空白对象,在我的构造函数中编码(如果我错了,请帮助我理解为什么状态会继续显示空白)。

我知道在组件刷新之前它会短暂工作;我可以使用React Dev工具看到状态更改为正确的值,然后刷新组件,并且所有内容都再次为空。

我该如何解决这个问题?

我想过把它分解成更小的组件,但我不太确定它是否必要。

import React from 'react';


class Macro extends React.Component {
    constructor(props) {
        super(props);
        this.state = {};
        this.handleClick = this.handleClick.bind(this);
        this.lbsToKg = this.lbsToKg.bind(this);
        this.age = document.querySelector("#age");
    }

    ftToInch(ft) {
        return ft * 12;
    }

    inchesToCm (inches) {
        return inches * 2.54;
    }


    lbsToKg(lbs) {
        return (Math.round(lbs * 0.45359237));
    }

    // mifflinStJeor(sex) {
    //  if ('male') {
    //      10 * lbsToKg(this.state.weight) + 6.25 * height(cm) - 5 * this.state.age + 5
    //  } else {
    //      10 * lbsToKg(this.state.weight) + 6.25 * height(cm) - 5 * this.state.age  + 161
    //  }
    // }

    handleClick(e) {
        this.setState({
            weight: this.lbsToKg(document.querySelector("#weight").value),
            age: document.querySelector("#age").value,
            height: this.ftToInch(document.querySelector("#ft").value) + document.querySelector("#inches"),
        })
    }

    render() {
        return(
            <div className='calculator-wrapper'>
                <form>
                    <div className="sex">
                        <input type="radio" id="sex-male" />
                        <label htmlFor='sex-male'>Male</label>
                        <input type="radio" id="sex-female"/>
                        <label htmlFor='sex-female'>Female</label>
                    </div>
                    <div className="age">
                        <label htmlFor='age'>Age</label>
                        <input type="number" id='age' name="age" />
                    </div>
                    <div className="weight">
                        <label htmlFor='weight'>Weight</label>
                        <input type="number" id='weight' name="weight" />
                    </div>
                    <div className="height">
                        <label htmlFor='height'>Height</label>
                        <input type="number" id='ft' name="feet" placeholder="ft" />
                        <input type="number" id='inches'  placeholder="inch"  name="inches" />
                    </div>
                    <div className="output">
                        <input type="text" className="bmr-output" value={this.state.weight}/>
                    </div>
                    <div className="button">
                        <button className="bmr" onClick={this.handleClick}>Get BMR</button>
                    </div>
                </form>
            </div>
            )
    }
}


export default Macro;

1 个答案:

答案 0 :(得分:4)

由于您的按钮没有与之关联的类型,因此它的格式为ant -f "C:\\Users\\Munteanu Mihail\\Desktop\\bibliotecaJFX" -Djavafx.main.class=bibliotecajfx.ui.adaugacarte.BibliotecaJFX jfxsa-run init: deps-clean: Updating property file: C:\Users\Munteanu Mihail\Desktop\bibliotecaJFX\build\built-clean.properties Deleting directory C:\Users\Munteanu Mihail\Desktop\bibliotecaJFX\build clean: init: deps-jar: Created dir: C:\Users\Munteanu Mihail\Desktop\bibliotecaJFX\build Updating property file: C:\Users\Munteanu Mihail\Desktop\bibliotecaJFX\build\built-jar.properties Created dir: C:\Users\Munteanu Mihail\Desktop\bibliotecaJFX\build\classes Created dir: C:\Users\Munteanu Mihail\Desktop\bibliotecaJFX\build\empty Created dir: C:\Users\Munteanu Mihail\Desktop\bibliotecaJFX\build\generated-sources\ap-source-output Compiling 4 source files to C:\Users\Munteanu Mihail\Desktop\bibliotecaJFX\build\classes warning: C:\Users\Munteanu Mihail\Desktop\bibliotecaJFX\jfoenix-9.0.0.jar(com/jfoenix/controls/JFXButton.class): major version 53 is newer than 52, the highest major version supported by this compiler. It is recommended that the compiler be upgraded. warning: C:\Users\Munteanu Mihail\Desktop\bibliotecaJFX\jfoenix-9.0.0.jar(com/jfoenix/controls/JFXTextField.class): major version 53 is newer than 52, the highest major version supported by this compiler. It is recommended that the compiler be upgraded. 2 warnings Copying 2 files to C:\Users\Munteanu Mihail\Desktop\bibliotecaJFX\build\classes compile: Created dir: C:\Users\Munteanu Mihail\Desktop\bibliotecaJFX\dist Copying 3 files to C:\Users\Munteanu Mihail\Desktop\bibliotecaJFX\dist\lib Detected JavaFX Ant API version 1.3 Going to create default keystore in C:\Users\Munteanu Mihail\Desktop\bibliotecaJFX\build\nb-jfx.jks Generating Key for nb-jfx Warning: The JKS keystore uses a proprietary format. It is recommended to migrate to PKCS12 which is an industry standard format using "keytool -importkeystore -srckeystore C:\Users\Munteanu Mihail\Desktop\bibliotecaJFX\build\nb-jfx.jks -destkeystore C:\Users\Munteanu Mihail\Desktop\bibliotecaJFX\build\nb-jfx.jks -deststoretype pkcs12". Launching <fx:jar> task from C:\Program Files\Java\jdk1.8.0_152\jre\..\lib\ant-javafx.jar Warning: From JDK7u25 the Codebase manifest attribute should be used to restrict JAR repurposing. Please set manifest.custom.codebase property to override the current default non-secure value '*'. Signing JAR: C:\Users\Munteanu Mihail\Desktop\bibliotecaJFX\dist\bibliotecaJFX.jar to C:\Users\Munteanu Mihail\Desktop\bibliotecaJFX\dist\bibliotecaJFX.jar as nb-jfx jar signed. Warning: The signer certificate will expire within six months. No -tsa or -tsacert is provided and this jar is not timestamped. Without a timestamp, users may not be able to validate this jar after the signer certificate's expiration date (2018-04-12) or after any future revocation date. Enter Passphrase for keystore: Enter key password for nb-jfx: Signing JAR: C:\Users\Munteanu Mihail\Desktop\bibliotecaJFX\dist\lib\derby.jar to C:\Users\Munteanu Mihail\Desktop\bibliotecaJFX\dist\lib\derby.jar as nb-jfx jar signed. Warning: The signer certificate will expire within six months. No -tsa or -tsacert is provided and this jar is not timestamped. Without a timestamp, users may not be able to validate this jar after the signer certificate's expiration date (2018-04-12) or after any future revocation date. Enter Passphrase for keystore: Enter key password for nb-jfx: Signing JAR: C:\Users\Munteanu Mihail\Desktop\bibliotecaJFX\dist\lib\derbyclient.jar to C:\Users\Munteanu Mihail\Desktop\bibliotecaJFX\dist\lib\derbyclient.jar as nb-jfx jar signed. Warning: The signer certificate will expire within six months. No -tsa or -tsacert is provided and this jar is not timestamped. Without a timestamp, users may not be able to validate this jar after the signer certificate's expiration date (2018-04-12) or after any future revocation date. Enter Passphrase for keystore: Enter key password for nb-jfx: Signing JAR: C:\Users\Munteanu Mihail\Desktop\bibliotecaJFX\dist\lib\jfoenix-9.0.0.jar to C:\Users\Munteanu Mihail\Desktop\bibliotecaJFX\dist\lib\jfoenix-9.0.0.jar as nb-jfx jar signed. Warning: The signer certificate will expire within six months. No -tsa or -tsacert is provided and this jar is not timestamped. Without a timestamp, users may not be able to validate this jar after the signer certificate's expiration date (2018-04-12) or after any future revocation date. Enter Passphrase for keystore: Enter key password for nb-jfx: Launching <fx:deploy> task from C:\Program Files\Java\jdk1.8.0_152\jre\..\lib\ant-javafx.jar No base JDK. Package will use system JRE. No base JDK. Package will use system JRE. jfx-deployment-script: jfx-deployment: jar: Copying 15 files to C:\Users\Munteanu Mihail\Desktop\bibliotecaJFX\dist\run1897499086 jfx-project-run: Executing C:\Users\Munteanu Mihail\Desktop\bibliotecaJFX\dist\run1897499086\bibliotecaJFX.jar using platform C:\Program Files\Java\jdk1.8.0_152\jre/bin/java Exception in Application start method java.lang.reflect.InvocationTargetException at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method) at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62) at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43) at java.lang.reflect.Method.invoke(Method.java:498) at com.sun.javafx.application.LauncherImpl.launchApplicationWithArgs(LauncherImpl.java:389) at com.sun.javafx.application.LauncherImpl.launchApplication(LauncherImpl.java:328) at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method) at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62) at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43) at java.lang.reflect.Method.invoke(Method.java:498) at sun.launcher.LauncherHelper$FXHelper.main(LauncherHelper.java:767) Caused by: java.lang.RuntimeException: Exception in Application start method at com.sun.javafx.application.LauncherImpl.launchApplication1(LauncherImpl.java:917) at com.sun.javafx.application.LauncherImpl.lambda$launchApplication$154(LauncherImpl.java:182) at java.lang.Thread.run(Thread.java:748) Caused by: java.lang.UnsupportedClassVersionError: com/jfoenix/controls/JFXButton has been compiled by a more recent version of the Java Runtime (class file version 53.0), this version of the Java Runtime only recognizes class file versions up to 52.0 at java.lang.ClassLoader.defineClass1(Native Method) at java.lang.ClassLoader.defineClass(ClassLoader.java:763) at java.security.SecureClassLoader.defineClass(SecureClassLoader.java:142) at java.net.URLClassLoader.defineClass(URLClassLoader.java:467) at java.net.URLClassLoader.access$100(URLClassLoader.java:73) at java.net.URLClassLoader$1.run(URLClassLoader.java:368) at java.net.URLClassLoader$1.run(URLClassLoader.java:362) at java.security.AccessController.doPrivileged(Native Method) at java.net.URLClassLoader.findClass(URLClassLoader.java:361) at java.lang.ClassLoader.loadClass(ClassLoader.java:424) at sun.misc.Launcher$AppClassLoader.loadClass(Launcher.java:338) at java.lang.ClassLoader.loadClass(ClassLoader.java:357) at javafx.fxml.FXMLLoader.loadTypeForPackage(FXMLLoader.java:2916) at javafx.fxml.FXMLLoader.loadType(FXMLLoader.java:2905) at javafx.fxml.FXMLLoader.importClass(FXMLLoader.java:2846) at javafx.fxml.FXMLLoader.processImport(FXMLLoader.java:2692) at javafx.fxml.FXMLLoader.processProcessingInstruction(FXMLLoader.java:2661) at javafx.fxml.FXMLLoader.loadImpl(FXMLLoader.java:2517) at javafx.fxml.FXMLLoader.loadImpl(FXMLLoader.java:2441) at javafx.fxml.FXMLLoader.loadImpl(FXMLLoader.java:3214) at javafx.fxml.FXMLLoader.loadImpl(FXMLLoader.java:3175) at javafx.fxml.FXMLLoader.loadImpl(FXMLLoader.java:3148) at javafx.fxml.FXMLLoader.loadImpl(FXMLLoader.java:3124) at javafx.fxml.FXMLLoader.loadImpl(FXMLLoader.java:3104) at javafx.fxml.FXMLLoader.load(FXMLLoader.java:3097) at bibliotecajfx.ui.adaugacarte.BibliotecaJFX.start(BibliotecaJFX.java:23) at com.sun.javafx.application.LauncherImpl.lambda$launchApplication1$161(LauncherImpl.java:863) at com.sun.javafx.application.PlatformImpl.lambda$runAndWait$174(PlatformImpl.java:326) at com.sun.javafx.application.PlatformImpl.lambda$null$172(PlatformImpl.java:295) at java.security.AccessController.doPrivileged(Native Method) at com.sun.javafx.application.PlatformImpl.lambda$runLater$173(PlatformImpl.java:294) at com.sun.glass.ui.InvokeLaterDispatcher$Future.run(InvokeLaterDispatcher.java:95) at com.sun.glass.ui.win.WinApplication._runLoop(Native Method) at com.sun.glass.ui.win.WinApplication.lambda$null$147(WinApplication.java:177) ... 1 more Exception running application bibliotecajfx.ui.adaugacarte.BibliotecaJFX Java Result: 1 Deleting directory C:\Users\Munteanu Mihail\Desktop\bibliotecaJFX\dist\run1897499086 jfxsa-run: BUILD SUCCESSFUL (total time: 20 seconds) 。 这使您的表单提交并刷新页面(实际提交表单)。

使其在type=submit处按钮标记。