2012-04-19 25 views
15

Duplicar posible:
window.open(url) different behavior - same code, different timingwindow.open() funciona diferente en el éxito AJAX

Será más fácil para mí explicar el problema si sólo te muestre ese ejemplo - >http://jsfiddle.net/RU2SM/
Como puedes ver, hay 2 botones, uno llamado'JAX 'y otro llamado' Directo '... Así que si haces clic en' Directo 'se abre la ventana (nueva pestaña en Chrome) pero si trato de hacer window.open() en el controlador de éxito AJAX, no funciona mismo camino.
Estoy seguro de que el problema es de AJAX, pero no tengo idea de cómo solucionarlo.
apreciará cualquier buena idea. Gracias

+0

posible duplicación de [window.open (url) comportamiento diferente - mismo código, sincronización diferente] (http://stackoverflow.com/questions/9793774/window-openurl-different-behavior-same-code-different- timing) y el comportamiento [extjs 4.0 inconsistent window.open() cuando se llama dentro de Ext.Ajax.request()] (http://stackoverflow.com/questions/10049172/extjs-4-0-inconsistent-window-open-behavior -cuando-llamado-dentro-ext-ajax-reques) –

Respuesta

26

Esto funciona como un encanto:

// Direct window.open() 
$('#btnDirect').on('click',function(){ 
    window.open('http://google.com') 
}) 
var success = false; //NOTE THIS 

// AJAX window.open() 
$('#btnAJAX').on("click", function(){ 
    $.ajax({ 
     url: "/user/login/", 
     context: document.body, 
     async:false, //NOTE THIS 
     success: function(){ //THIS ALSO CHANGED 
     success = true 
     } 
    }); 
    if(success){ //AND THIS CHANGED 
     window.open('http://google.com') 
    } 
}) 

Lo que esto hace es cuando la llamada Ajax es el éxito que establece la variable de éxito en true.
La propiedad async:false se asegura de que la instrucción if se active después de que se complete la llamada Ajax.
Por lo tanto, window.open se activa en las mismas circunstancias que su enlace directo.

+1

Hay algunas dificultades con las solicitudes no asincrónicas, no debe usarlas si puede haber algún retraso con la página que está solicitando. De la [documentación de jQuery] (http://api.jquery.com/jQuery.ajax/): "Tenga en cuenta que las solicitudes sincrónicas pueden bloquear temporalmente el navegador, deshabilitando cualquier acción mientras la solicitud está activa." – Gareth

+0

Eso es cierto, debe tener cuidado al usar esta solución, pero es la única forma (hasta donde yo sé) de ejecutar ambas funciones en las mismas circunstancias. Porque incluso si permite ventanas emergentes con la versión Ajax crea una ventana emergente, no abre otra pestaña como la llamada directa. No sé exactamente por qué hay una diferencia en el comportamiento, pero esto parece ser el truco. –

+0

Gracias, como dices "funciona como un encanto ":) Para evitar la congelación prolongada del navegador he agregado timeout = 2000 ... – T1000

12

El problema es que los navegadores suelen bloquear window.open s a menos que se llamen en respuesta directa a una acción del usuario. Es por eso que su manejador de clics funciona (un clic es una acción del usuario) pero su manejador AJAX no.

Una solución es abrir la ventana durante la acción de clic inicial, luego actualizar su ubicación con éxito AJAX (o cerrarla nuevamente en caso de falla AJAX).

De lo contrario, tendrá que hacer que el usuario permita explícitamente las ventanas emergentes de su dominio en su navegador.

+1

Sí, esta también es una solución, pero necesito abrir una ventana SÓLO si hay alguna información específica en la respuesta ... así que esta no es una buena solución para mí, pero probablemente será útil para otra persona (1+) – T1000

0

Además, también vale la pena mencionar que usar async: false y llamar a window.open funciona en Chrome y Firefox pero puede causar problemas en Safari ... ni siquiera da información de que una ventana emergente fue bloqueada

1

mejor manera de poner en práctica cualquier lógica tras el éxito de la llamada AJAX, hay un evento disparado en cada establecimiento de llamada ajax es decir $ .ajax.Request.done y $ .ajax.Request.fail. $ .ajax.Request.done (function() {if (success) {// Implement logic}});

Cuestiones relacionadas