Estou tentando usar event.stopPropagation () dentro de um componente ReactJS para impedir que um evento click borbulhe e desencadeie um evento click anexado ao JQuery no código legado, mas parece que o stopPropagation () do React apenas interrompe a propagação para eventos também anexado no React, e o stopPropagation () do JQuery não interrompe a propagação para eventos anexados ao React.
Existe alguma maneira de fazer stopPropagation () funcionar nesses eventos? Eu escrevi um JSFiddle simples para demonstrar esses comportamentos:
/** @jsx React.DOM */
var Propagation = React.createClass({
alert: function(){
alert('React Alert');
},
stopPropagation: function(e){
e.stopPropagation();
},
render: function(){
return (
<div>
<div onClick={this.alert}>
<a href="#" onClick={this.stopPropagation}>React Stop Propagation on React Event</a>
</div>
<div className="alert">
<a href="#" onClick={this.stopPropagation}>React Stop Propagation on JQuery Event</a>
</div>
<div onClick={this.alert}>
<a href="#" className="stop-propagation">JQuery Stop Propagation on React Event</a>
</div>
<div className="alert">
<a href="#" className="stop-propagation">JQuery Stop Propagation on JQuery Event</a>
</div>
</div>
);
}
});
React.renderComponent(<Propagation />, document.body);
$(function(){
$(document).on('click', '.alert', function(e){
alert('Jquery Alert');
});
$(document).on('click', '.stop-propagation', function(e){
e.stopPropagation();
});
});
javascript
jquery
reactjs
lofiinterstate
fonte
fonte
event.nativeEvent.stopImmediatePropagation
para impedir que outros ouvintes de eventos sejam acionados, mas a ordem de execução não é garantida.stopImmediatePropagation
ouvintes de evento de declarações serão chamados na ordem em que foram vinculados. Se o seu React JS for inicializado antes do seu jQuery (como está no seu violino), interromper a propagação imediata funcionará.componentDidMount
, mas isso pode interferir com outros manipuladores de eventos React de maneiras inesperadas..stop-propagation
necessariamente não vai funcionar. Seu exemplo usa delegação de eventos, mas está tentando parar a propagação no elemento O ouvinte precisa ser ligado ao próprio elemento:$('.stop-propagation').on('click', function(e) { e.stopPropagation(); });
. Isto evita violino tudo propagação como se você estivesse tentando: jsfiddle.net/7LEDT/6Respostas:
React usa delegação de eventos com um único ouvinte de eventos ativado
document
para eventos que borbulham, como 'clique' neste exemplo, o que significa que não é possível interromper a propagação; o evento real já foi propagado no momento em que você interage com ele no React.stopPropagation
no evento sintético do React é possível porque o React manipula a propagação de eventos sintéticos internamente.Trabalhando com o JSFiddle com as correções abaixo.
Reagir parar a propagação no evento jQuery
Use
Event.stopImmediatePropagation
para impedir que seus outros ouvintes (jQuery neste caso) na raiz sejam chamados. É suportado no IE9 + e em navegadores modernos.Propagação de parada do jQuery no evento React
Seu código jQuery também usa delegação de eventos, o que significa chamar
stopPropagation
o manipulador não está parando nada; o evento já foi propagadodocument
e o ouvinte do React será acionado.Para impedir a propagação além do elemento, o ouvinte deve estar vinculado ao próprio elemento:
Edit (14/01/2016): Esclareceu que a delegação é necessariamente usada apenas para eventos que borbulham. Para obter mais detalhes sobre o tratamento de eventos, a fonte do React possui comentários descritivos: ReactBrowserEventEmitter.js .
fonte
document
ou o componente React raiz? A página vinculada diz apenas "no nível superior", o que entendo como não o édocument
(mas não consigo descobrir se isso é relevante).window
invés dedocument
: stackoverflow.com/a/52879137/438273Vale ressaltar ( desta edição ) que se você estiver anexando eventos
document
,e.stopPropagation()
não ajudará. Como solução alternativa, você pode usar emwindow.addEventListener()
vez dedocument.addEventListener
eevent.stopPropagation()
interromper a propagação do evento para a janela.fonte
Ainda é um momento interessante:
Use essa construção, se sua função estiver envolvida por tag
fonte
event.nativeEvent
é a resposta correta; Eu era capaz de usarcomposedPath()
por meio dele:event.nativeEvent.composedPath()
wrapped by tag
? você poderia fornecer um exemplo?<div onClick=(firstHandler)> <div onClick=(secHandler)>active text</div> </div>
Consegui resolver isso adicionando o seguinte ao meu componente:
fonte
Encontrei este problema ontem, por isso criei uma solução amigável ao React.
Confira react-native-listener . Está funcionando muito bem até agora. Feedback apreciado.
fonte
react-native-listener
usosfindDomNode
que serão descontinuados github.com/yannickcr/eslint-plugin-react/issues/…Na documentação do React : Os manipuladores de eventos abaixo são acionados por um evento na fase de bolhas . Para registrar um manipulador de eventos para a fase de captura, anexe o Capture . (enfase adicionada)
Se você tem um ouvinte de evento de clique no código do React e não quer que ele borbulhe, acho que o que você quer fazer é usar em
onClickCapture
vez deonClick
. Em seguida, você passaria o evento para o manipulador e o fariaevent.nativeEvent.stopPropagation()
para impedir que o evento nativo borbulhasse para um ouvinte de eventos JS baunilha (ou qualquer coisa que não reaja).fonte
Atualização: agora você pode
<Elem onClick={ proxy => proxy.stopPropagation() } />
fonte
Uma solução rápida é usar em
window.addEventListener
vez dedocument.addEventListener
.fonte