Tidak dapat mengetik di kolom teks input React

111

Saya mencoba React.js pertama saya dan saya bingung sejak awal ... Saya memiliki kode di bawah ini, yang membuat formulir pencarian menjadi <div id="search"></div>. Tetapi mengetik di kotak pencarian tidak melakukan apa-apa.

Agaknya ada sesuatu yang hilang melewati props dan keadaan naik turun, dan ini sepertinya masalah umum. Tapi saya bingung - saya tidak bisa melihat apa yang hilang.

var SearchFacet = React.createClass({
  handleChange: function() {
    this.props.onUserInput(
      this.refs.searchStringInput.value
    )
  },
  render: function() {
    return (
      <div>
        Search for:
        <input
          type="text"
          value={this.props.searchString}
          ref="searchStringInput"
          onchange={this.handleChange} />
      </div>
    );
  }
});

var SearchTool = React.createClass({
  render: function() {
    return (
      <form>
        <SearchFacet 
          searchString={this.props.searchString}
          onUserInput={this.props.onUserInput}
         />
        <button>Search</button>
      </form>
    );
  }
});

var Searcher = React.createClass({
  getInitialState: function() {
    return {
      searchString: ''
    }
  },

  handleUserInput: function(searchString) {
    this.setState({
      searchString: searchString
    })
  },

  render: function() {
    return (
      <div>
        <SearchTool 
          searchString={this.state.searchString}
          onUserInput={this.handleUserInput}
        />
      </div>
    );
  }
});

ReactDOM.render(
  <Searcher />,
  document.getElementById('searcher')
);

(Akhirnya saya akan memiliki jenis lain SearchFacet*tetapi saya hanya mencoba membuat yang ini berfungsi.)

Phil Gyford
sumber
Coba masuk thissaat Anda memasukkan bidang teks. Bisa jadi itu thisbukan Searcherkomponennya lagi.
FaureHu
Terima kasih FaureHu - masuk thispada titik mana dalam kode? Mencoba masuk Searcher.handleUserInput()atau SearchFacet.handleChange()tidak melakukan apa pun.
Phil Gyford
Anda dapat melihat jawaban saya untuk pertanyaan serupa. Anda dapat menemukan penjelasan rinci: stackoverflow.com/questions/34713718/…
prudhvi seeramreddi

Jawaban:

80

Anda belum membungkus onchangeprop Anda dengan benar di input. Itu harus onChangedi BEJ.

<input
  type="text"
  value={this.props.searchString}
  ref="searchStringInput"
  onchange={this.handleChange} <--[should be onChange]
/>  

Topik meneruskan valueprop ke <input>, dan kemudian entah bagaimana mengubah nilai yang diteruskan sebagai respons terhadap interaksi pengguna menggunakan onChangepenangan cukup dipertimbangkan dalam dokumen .

Mereka merujuk ke input seperti Komponen Terkontrol , dan merujuk ke input yang memungkinkan DOM menangani nilai input dan perubahan selanjutnya dari pengguna sebagai Komponen Tidak Terkontrol .

Setiap kali Anda menyetel valueprop dari suatu inputke beberapa variabel, Anda memiliki Komponen Terkendali . Ini berarti Anda harus mengubah nilai variabel dengan beberapa cara terprogram atau input akan selalu menyimpan nilai itu dan tidak akan pernah berubah, bahkan saat Anda mengetik - perilaku asli dari input, untuk memperbarui nilainya saat mengetik, diganti dengan React here.

Jadi, Anda benar mengambil variabel itu dari keadaan, dan memiliki penangan untuk memperbarui keadaan semua disiapkan dengan baik. Masalahnya adalah karena Anda memiliki onchangedan tidak benar onChangepenangan tidak pernah dipanggil dan karenanya valuetidak pernah diperbarui saat Anda mengetik ke dalam masukan. Ketika Anda menggunakan onChangepawang yang disebut, value adalah diperbarui ketika Anda mengetik, dan Anda melihat perubahan Anda.

davnicwil.dll
sumber
201

Menggunakan value={whatever}akan membuatnya jadi Anda tidak dapat mengetik di kolom input. Anda harus menggunakan defaultValue="Hello!".

Lihat https://facebook.github.io/react/docs/uncontrolled-components.html#default-values

Juga, onchangeharus onChangeseperti yang ditunjukkan @davnicwil.

Ivan
sumber
2
Dalam kebutuhan saya, saya ingin memasukkan kolom dengan mengaktifkan pengetikan serta perlu diatur ke nilai default yang berasal dari variabel negara. Atribut defaultValue baik-baik saja tetapi ada masalah dalam memperbarui nilai default sesuai dengan perubahan status, adakah cara untuk memaksa nilai default berubah?
semira
1
Anda harus memposting masalah itu sebagai pertanyaan lain di Stackoverflow.
Ivan
1
@GeoffreyHale Saya tidak begitu yakin apa yang Anda maksud dengan bagaimana hal itu menyesatkan. Lihat contoh ini yang tidak menggunakan status: codepen.io/anon/pen/BQJZwr?editors=0010 . Atau yang satu ini: codepen.io/anon/pen/JbMJMX?editors=0010
Ivan
4
@Ivan Anda benar, keduanya tidak berubah: value={whatever}dan value={this.state.myvalue}. Saya seharusnya membuat klarifikasi ini sebagai gantinya: menggunakan onChange={this.handleChange}dan sesuatu seperti handleChange: function(e) { var newState = {}; newState[e.target.name] = e.target.value; this.setState(newState); },membuat bidang bisa berubah lagi.
Geoffrey Hale
1
@Ivan Yang satu ini Hanya Membantu saya Terima kasih banyak defaultValuemenyelamatkan hari saya.
Code Cooker
11

Ini mungkin disebabkan oleh fungsi onChange tidak memperbarui nilai yang tepat yang disebutkan dalam masukan.

Contoh:

<input type="text" value={this.state.textValue} onChange = {this.changeText}></input>

 changeText(event){
        this.setState(
            {textValue : event.target.value}
        );
    }

dalam fungsi onChange, perbarui bidang nilai yang disebutkan.

sunaina kotekar
sumber
Terima kasih, sangat membantu. Hanya jawaban Anda yang menjelaskan secara lengkap bagaimana menyelesaikan masalah.
M3RS
di mana mendefinisikan func changeText ini?
Jitendra Pancholi
Jika itu adalah komponen stateless, di dalam fungsinya, dan jika itu adalah komponen kelas, di dalam konstruktor.
Gal Grünfeld
Anda tidak perlu menulis this.state di dalam setState. Jika Anda hanya menulis textValue: event.target.value di dalam setState, Ini juga bekerja dengan sempurna
Pardeep Sharma
4

Saya juga memiliki masalah yang sama dan dalam kasus saya, saya menyuntikkan peredam dengan benar tetapi tetap saya tidak bisa mengetik di lapangan. Ternyata jika Anda menggunakan immutableAnda harus menggunakan redux-form/immutable.

import {reducer as formReducer} from 'redux-form/immutable';
const reducer = combineReducers{

    form: formReducer
}
import {Field, reduxForm} from 'redux-form/immutable';
/* your component */

Perhatikan bahwa negara Anda harus seperti state->formjika tidak, Anda harus secara eksplisit mengkonfigurasi perpustakaan juga nama untuk negara harus form. lihat masalah ini

Seyed Jalal Hosseini
sumber
4

Bagi saya, perubahan sederhana berikut bekerja dengan sempurna

<input type="text" 
        value={props.letter} 
        onChange={event => setTxtLetter(event.target.value)} /> {/* does not work */}

ubah ... value = {myPropVal} menjadi ... defaultValue = {myPropVal}

<input type="text" 
        defaultValue={props.letter} 
        onChange={event => setTxtLetter(event.target.value)} /> {/* Works!! */}
Nelles
sumber
Ini memperbaikinya untuk saya. Terima kasih!
mikeym
Saya pikir onChange tidak berfungsi dengan baik bila digunakan dalam Formik. Saya mencoba ini juga tetapi tidak berhasil untuk saya. Bisakah Anda melihat-lihat di sini? stackoverflow.com/questions/61689720/…
a125
0

Dalam konteks komponen kelas ...

Jika metode changeHandler adalah fungsi normal:

handleChange(e){
    this.setState({[e.target.name]:[e.target.value]});
}

bisa digunakan seperti ini ...onChange={(e)=>this.handleChange(e)}

<input type="text" name="any" value={this.state.any} onChange={(e)=>this.handleChange(e)}></input>

Jika metode changeHandler adalah fungsi panah:

handle = (e) =>{
        this.setState({[e.target.name]:[e.target.value]});
    }

bisa digunakan seperti ini ... onChange={this.handle}

 <input type="text" name="any2" value={this.state.any2} onChange={this.handle} ></input>

Dan ini memecahkan masalah "Can't type in React input text field" saya.

Aditya Patnaik
sumber