이 글에서는 React Event 이벤트 등록 구현에 대해 소개합니다. 필요한 친구가 참고할 수 있습니다.
React 요소의 이벤트 처리는 DOM 요소의 이벤트 처리와 매우 유사합니다. 하지만 약간의 문법적 차이가 있습니다.
React 이벤트 바인딩 속성은 소문자 대신 카멜 케이스로 이름이 지정됩니다.
JSX 구문을 사용하는 경우 문자열이 아닌 함수를 이벤트 핸들러로 전달해야 합니다(DOM 요소가 작성되는 방식)
그리고 React 자체는 React를 사용할 때 내부적으로 합성 이벤트를 구현합니다. , 일반적으로 이미 생성된 DOM 요소에 리스너를 추가하기 위해 addEventListener를 사용할 필요가 없습니다. 요소가 처음 렌더링될 때만 리스너를 제공하면 됩니다.
이것이 어떻게 구현되는지 살펴보겠습니다
React 이벤트 메커니즘은 이벤트 등록과 이벤트 배포, 두 부분으로 나누어집니다.
// 事件绑定 function handleClick(e) { e.preventDefault(); console.log('The link was clicked.'); } return ( <a> Click me </a> );
위 코드에서 onClick은 다음과 같이 전달됩니다. props handlerClick은 컴포넌트가 업데이트되고 마운트되면 props를 처리합니다. 프로세스는 다음과 같습니다:
핵심 코드:
ReactDOMComponent.js가 로드(mountComponent)되고 업데이트(updateComponent)될 때 를 호출합니다. props 처리 방법:_updateDOMProperties
_updateDOMProperties: function(lastProps, nextProps, transaction) { ... if (registrationNameModules.hasOwnProperty(propKey)) { if (nextProp) { // 如果传入的是事件,去注册事件 enqueuePutListener(this, propKey, nextProp, transaction); } else if (lastProp) { deleteListener(this, propKey); } } ... } // 注册事件 function enqueuePutListener(inst, registrationName, listener, transaction) { var containerInfo = inst._nativeContainerInfo; var doc = containerInfo._ownerDocument; ... // 去doc上注册 listenTo(registrationName, doc); // 事务结束之后 putListener transaction.getReactMountReady().enqueue(putListener, { inst: inst, registrationName: registrationName, listener: listener, }); }
//registrationName:需要绑定的事件 //当前component所属的document,即事件需要绑定的位置 listenTo: function (registrationName, contentDocumentHandle) { var mountAt = contentDocumentHandle; //获取当前document上已经绑定的事件 var isListening = getListeningForDocument(mountAt); ... if (...) { //冒泡处理 ReactBrowserEventEmitter.ReactEventListener.trapBubbledEvent(...); } else if (...) { //捕捉处理 ReactBrowserEventEmitter.ReactEventListener.trapCapturedEvent(...); } ... },결국 실제로는 doc.addEventLister(event, callback, false);You 모든 이벤트가 문서에 바인딩되어 있음을 볼 수 있습니다
그래서 트리거된 이벤트는 ReactEventListener의 dispatchEvent 메서드입니다
이전 이벤트 등록 방법으로 돌아가기
function enqueuePutListener(inst, registrationName, listener, transaction) { var containerInfo = inst._nativeContainerInfo; var doc = containerInfo._ownerDocument; if (!doc) { // Server rendering. return; } listenTo(registrationName, doc); transaction.getReactMountReady().enqueue(putListener, { inst: inst, registrationName: registrationName, listener: listener, }); }putListener는 바인딩이 완료된 후 실행됩니다.
var listenerBank = {}; var getDictionaryKey = function (inst) { //inst为组建的实例化对象 //_rootNodeID为组件的唯一标识 return '.' + inst._rootNodeID; } var EventPluginHub = { //inst为组建的实例化对象 //registrationName为事件名称 //listner为我们写的回调函数,也就是列子中的this.autoFocus putListener: function (inst, registrationName, listener) { ... var key = getDictionaryKey(inst); var bankForRegistrationName = listenerBank[registrationName] || (listenerBank[registrationName] = {}); bankForRegistrationName[key] = listener; ... } }EventPluginHub는 React당 한 번만 인스턴스화됩니다. 즉, 프로젝트 그룹의 모든 이벤트에 대한 콜백은 고유한 ListenerBank에 저장됩니다. 관련 권장 사항:
React 사용: React 구성 요소 내부의 상태 관리
위 내용은 React Event 이벤트 등록 구현의 상세 내용입니다. 자세한 내용은 PHP 중국어 웹사이트의 기타 관련 기사를 참조하세요!