javascript - reactjs vs angular ماهو




ضبط التركيز على المدخلات بعد التقديم (16)

ما هي طريقة رد الفعل لوضع التركيز على حقل نص معين بعد تقديم المكون؟

يبدو أن الوثائق تشير إلى استخدام المراجع ، على سبيل المثال:

اضبط ref="nameInput" في حقل الإدخال الخاص بي في وظيفة التجسيد ، ثم اتصل:

this.refs.nameInput.getInputDOMNode().focus(); 

ولكن أين يجب أن أسمي هذا؟ لقد جربت بعض الأماكن ولكن لا يمكنني الحصول عليها.

https://code.i-harness.com


تحذير: ReactDOMComponent: لا تصل إلى .getDOMNode () لعقدة DOM؛ بدلاً من ذلك ، استخدم العقدة مباشرة. تم تقديم عقدة DOM هذه بواسطة App .

يجب ان يكون

componentDidMount: function () {
  this.refs.nameInput.focus();
}

التركيز على جبل

إذا كنت ترغب فقط في التركيز على عنصر عندما يتم تحديثه (يتم عرضه في البداية) ، فسيتم استخدام بسيط لخاصية التركيز التلقائي.

<input autoFocus type="text" />

التركيز التفاعلي

للتحكم في التركيز ، استخدم تركيبة الوظائف بشكل مشروط لإخفاء تفاصيل تطبيق dom والمتصفح من مكوناتك.

تتفاعل 16.8 + العنصر الوظيفي - useFocus هوك

componentDidMount() {
    this.refs.linkInput.focus()
}

ثم استخدمه في أي مكون وظيفي.

<input type="text" autoFocus />

Demo

رد 16.3 + مكونات الدرجة - utilizeFocus

const useFocus = () => {
    const htmlElRef = useRef(null)
    const setFocus = () => {htmlElRef.current &&  htmlElRef.current.focus()}

    return [ setFocus, htmlElRef ] 
}

ثم استخدامه في أي مكون فئة

const FocusDemo = () => {

    const [value, setValue] = useState("")
    const [setInputFocus, inputRef] = useFocus()
    const [setBtnFocus, btnRef] = useFocus()

    return (
        <> {/* React.Fragment */}

            <input
                value={value}
                onChange={(e)=>{
                    setValue(e.target.value)
                    if ( some logic ){ setBtnFocus() }
                }}
                ref={inputRef}
            />

            <button 
               onClick={setInputFocus}
               ref={btnRef}
            >
               Refocus
            </button>

        </>
    )

}

Demo


أضاف React 16.3 طريقة ملائمة جديدة للتعامل مع ذلك من خلال إنشاء مرجع في مُنشئ المكون واستخدامه كما يلي:

class MyForm extends Component {
  constructor(props) {
      super(props);

      this.textInput = React.createRef();
  }

  componentDidMount() {
    this.textInput.current.focus(); // one important change here is that we need to access the element via current.
  }

  render() {
    // instead of using arrow function, the created ref can be used directly.
    return(
      <div>
        <input ref={this.textInput} />
      </div>
    );
  }
}

لمزيد من التفاصيل ، يمكنك مراجعة هذه المقالة في React blog.

تحديث:

بدءاً من useRef 16.8 ، يمكن استخدام useRef في مكونات الوظيفة لتحقيق نفس النتيجة:

import React, { useEffect, useRef } from 'react';

const MyForm = () => {
  const textInput = useRef(null);

  useEffect(() => {
    textInput.current.focus();
  }, []);

  return (
    <div>
      <input ref={textInput} />
    </div>
  );
};

أواجه نفس المشكلة ولكن لدي بعض الرسوم المتحركة أيضًا ، لذلك يقترح زميلي استخدام window.requestAnimationFrame

هذا هو سمة المرجع للعنصر الخاص بي:

ref={(input) => {input && window.requestAnimationFrame(()=>{input.focus()})}}

إذا كنت تريد فقط إجراء ضبط تلقائي للصورة في React ، فهذا أمر بسيط.

const utilizeFocus = () => {
    const ref = React.createRef()
    const setFocus = () => {ref.current &&  ref.current.focus()}

    return {setFocus, ref} 
}

بينما إذا كنت تريد فقط معرفة مكان وضع هذا الرمز ، فإن الإجابة تكون في componentDidMount ().

v014.3

class App extends Component {
  constructor(props){
    super(props)
    this.input1Focus = utilizeFocus()
    this.BtnFocus = utilizeFocus()
  }

  render(){
    return (
      <> {/* React.Fragment */}

          <input
              value={value}
              onChange={(e)=>{
                  setValue(e.target.value)
                  if ( some logic ){ this.BtnFocus.setFocus() }
              }}
              ref={this.input1Focus.ref}
          />

          <button 
             onClick={this.input1Focus.setFocus()}
             ref={this.BtnFocus.ref}
          >
             Refocus
          </button>

      </>
    )
  } 
}

في معظم الحالات ، يمكنك إرفاق مرجع لعقدة DOM وتجنب استخدام findDOMNode على الإطلاق.

اقرأ وثائق واجهة برمجة التطبيقات هنا: https://facebook.github.io/react/docs/top-level-api.html#reactdom.finddomnode


اقرأ جميع الإجابات تقريبًا ولكن لم ترى getRenderedComponent().props.input

تعيين المرجع المدخلات النص الخاص بك

this.refs.username.getRenderedComponent().props.input.onChange('');


بعد تجربة الكثير من الخيارات أعلاه دون نجاح ، وجدت أن الأمر كان كما disabling ، ثم enabling الإدخال الذي تسبب في فقد التركيز.

كان عندي برسالة sendingAnswer والتي من شأنها تعطيل الإدخال أثناء استقصاء الواجهة الخلفية.

export default class DefaultRolesPage extends React.Component {

    addRole = ev => {
        ev.preventDefault();
        const roleKey = this.roleKey++;
        this::updateState({
            focus: {$set: roleKey},
            formData: {
                roles: {
                    $push: [{
                        id: null,
                        name: '',
                        permissions: new Set(),
                        key: roleKey,
                    }]
                }
            }
        })
    }

    render() {
        const {formData} = this.state;

        return (
            <GridForm onSubmit={this.submit}>
                {formData.roles.map((role, idx) => (
                    <GridSection key={role.key}>
                        <GridRow>
                            <GridCol>
                                <label>Role</label>
                                <TextBox value={role.name} onChange={this.roleName(idx)} autoFocus={role.key === this.state.focus}/>
                            </GridCol>
                        </GridRow>
                    </GridSection>
                ))}
            </GridForm>
        )
    }
}

بمجرد إزالة المعاقين ، بدأ كل شيء في العمل مرة أخرى.



لا تحتاج getInputDOMNode ؟؟ في هذه الحالة...

ما عليك سوى الحصول على ref focus() عند تثبيت المكون - componentDidMount ...

import React from 'react';
import { render } from 'react-dom';

class myApp extends React.Component {

  componentDidMount() {
    this.nameInput.focus();
  }

  render() {
    return(
      <div>
        <input ref={input => { this.nameInput = input; }} />
      </div>
    );
  }

}

ReactDOM.render(<myApp />, document.getElementById('root'));


لنقل التركيز إلى عنصر تم إنشاؤه حديثًا ، يمكنك تخزين معرف العنصر في الحالة واستخدامه لتعيين autoFocus . على سبيل المثال

<Input
  autoFocus={question}
  placeholder={
    gettingQuestion ? 'Loading...' : 'Type your answer here...'
  }
  value={answer}
  onChange={event => dispatch(updateAnswer(event.target.value))}
  type="text"
  autocomplete="off"
  name="answer"
  // disabled={sendingAnswer} <-- Causing focus to be lost.
/>

وبهذه الطريقة ، لا يتم التركيز على تحميل أي مربع من مربعات النص (مثلما أريد) ، ولكن عندما تضغط على الزر "إضافة" لإنشاء سجل جديد ، يصبح التركيز على هذا السجل الجديد.

نظرًا لأن " autoFocus " لا "يعمل" مرة أخرى ما لم يتم إعادة تثبيت المكون ، فلست مضطرًا إلى this.state.focus هذا this.state.focus (أي أنه لن يستمر في سرقة التركيز مرة أخرى أثناء تحديث حالات أخرى).


نسخة محدثة يمكنك التحقق من هنا

componentDidMount() {

    // Focus to the input as html5 autofocus
    this.inputRef.focus();

}
render() {
    return <input type="text" ref={(input) => { this.inputRef = input }} />
})

هذا لم يعد أفضل إجابة. اعتبارًا من الإصدار v0.13 ، قد لا يتوفر this.refs حتى يتم تشغيل AFTER componentDidMount() في بعض الحالات الفردية.

فقط أضف علامة autoFocus إلى حقل الإدخال الخاص بك ، كما هو موضح FakeRainBrigand أعلاه.


هذه هي الطريقة الصحيحة ، وكيفية ضبط تلقائي للصورة. عند استخدام رد الاتصال بدلاً من السلسلة كقيمة مرجع ، يتم استدعاؤه تلقائيًا. حصلت على المرجع الخاص بك من دون الحاجة إلى لمس DOM باستخدام getDOMNode

render: function() {
  return <TextInput ref={(c) => this._input = c} />;
},
componentDidMount: function() {
  this._input.focus();
},

يمكنك وضع هذه الطريقة داخل وظيفة التجسيد. أو داخل طريقة دورة الحياة ، componentDidUpdate


اعتبارًا من React 0.15 ، الطريقة الأكثر إيجازًا هي:

<input ref={input => input && input.focus()}/>




reactjs