Pergunta

No momento, estou carregando um pop-up estilo lightbox que carrega seu HTML a partir de uma chamada XHR.Este conteúdo é então exibido em um pop-up 'modal' usando element.innerHTML = content Isso funciona perfeitamente.

Em outra seção deste site eu uso um 'emblema' do Flickr (http://www.elliotswan.com/2006/08/06/custom-flickr-badge-api-documentation/) para carregar imagens do flickr dinamicamente.Isso é feito incluindo uma tag de script que carrega um javascript do flickr, que por sua vez faz algumas document.write declarações.

Ambos funcionam perfeitamente quando incluídos no HTML.Somente ao carregar o código do emblema do flickr dentro na lightbox, nenhum conteúdo é renderizado.Parece que usar innerHTML escrever document.write declarações está indo longe demais, mas não consigo encontrar nenhuma pista nas implementações javascript (FF2 e 3, IE6 e 7) desse comportamento.

Alguém pode esclarecer se isso deve ou não funcionar?Obrigado.

Foi útil?

Solução

Em geral, as tags de script não são executadas ao usar innerHTML.No seu caso, isso é bom, porque o document.write call eliminaria tudo o que já está na página.No entanto, isso deixa você sem qualquer HTML document.write que deveria adicionar.

Os métodos de manipulação de HTML do jQuery executarão scripts em HTML para você, o truque é então capturar as chamadas para document.write e colocando o HTML no lugar apropriado.Se for bastante simples, algo assim servirá:

var content = '';
document.write = function(s) {
    content += s;
};
// execute the script
$('#foo').html(markupWithScriptInIt);
$('#foo .whereverTheDocumentWriteContentGoes').html(content);

Mas fica complicado.Se o script estiver em outro domínio, ele será carregado de forma assíncrona, então você terá que esperar até terminar para obter o conteúdo.Além disso, e se ele apenas gravar o HTML no meio do fragmento sem um elemento wrapper que você possa selecionar facilmente? writeCapture.js (transparência completa:Eu escrevi) lida com todos esses problemas.Eu recomendo apenas usá-lo, mas pelo menos você pode olhar o código para ver como ele lida com tudo.

EDITAR:Aqui está um página demonstrando o que parece ser o efeito que você deseja.

Outras dicas

Criei uma página de teste simples que ilustra o problema:

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN"
    "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">
<html>
    <head>
        <meta http-equiv="Content-type" content="text/html; charset=utf-8" />
        <title>Document Write Testcase</title>
    </head>
    <body>
        <div id="container">
        </div>
        <div id="container2">
        </div>

        <script>
            // This doesn't work!
            var container = document.getElementById('container');
            container.innerHTML = "<script type='text/javascript'>alert('foo');document.write('bar');<\/script>";

            // This does!
            var container2 = document.getElementById('container2');
            var script = document.createElement("script");
            script.type = 'text/javascript';
            script.innerHTML = "alert('bar');document.write('foo');";
            container.appendChild(script);
        </script>
    </body>
</html>

Esta página alerta 'bar' e imprime 'foo', enquanto eu esperava que ela também alertasse 'foo' e imprimisse 'bar'.Mas, infelizmente, desde o script tag faz parte de uma página HTML maior, não posso destacar essa tag e anexá-la como no exemplo acima.Bem, eu posso, mas isso exigiria digitalização innerHTML conteúdo para script tags e substituindo-as na string por espaços reservados e, em seguida, inserindo-as usando o DOM.Parece que não que trivial.

Usar document.writeln(content); em vez de document.write(content).

No entanto, o melhor método é usar a concatenação de innerHTML, assim:

element.innerHTML += content;

O element.innerHTML = content; método que substituirá o conteúdo antigo pelo novo, ele substituirá o innerHTML do seu elemento!

Considerando que o += operador em element.innerHTML += content; irá adicionar seu texto após o conteúdo antigo.(como o que document.write faz.)

document.write é tão obsoleto quanto parece.Graças às maravilhas do JavaScript, você pode simplesmente atribuir sua própria função ao write método do document objeto que usa innerHTML em um elemento de sua escolha para anexar o conteúdo fornecido.

Posso obter alguns esclarecimentos primeiro para ter certeza de que entendi o problema?

document.write as chamadas adicionarão conteúdo à marcação no ponto da marcação em que ocorrem.Por exemplo, se você incluir document.write chama uma função, mas chama a função em outro lugar, o document.write a saída acontecerá no ponto da marcação em que a função está definiram não onde está chamado.

Portanto para que isso funcione em todo o Flickr document.write declarações precisarão fazer parte do content em element.innerHTML = content.Este é definitivamente o caso?

Você pode testar rapidamente se isso deve funcionar adicionando um único e simples document.write chame o conteúdo que está definido como o innerHTML e veja o que isso faz:

<script>
  var content = "<p>1st para</p><script>document.write('<p>2nd para</p>');</script>"
  element.innerHTML = content;
</script>

Se isso funcionar, o conceito de document.write trabalhando em conteúdo definido como o innerHTML de um elemento pode simplesmente funcionar.

Meu pressentimento é que não funcionará, mas deve ser bastante simples testar o conceito.

Então você está usando um método DOM para criar um script elemento e anexá-lo a um elemento existente e isso faz com que o conteúdo do elemento anexado script elemento a ser executado?Isso soa bem.

Você diz que a tag script faz parte de uma página HTML maior e, portanto, não pode ser isolada.Você não pode fornecer um ID à tag do script e direcioná-la?Provavelmente estou perdendo algo óbvio aqui.

Em teoria, sim, posso destacar uma tag de script dessa forma.O problema é que potencialmente temos dezenas de situações em que isso ocorre, por isso estou tentando encontrar alguma causa ou documentação desse comportamento.

Também o script tag não parece mais fazer parte do DOM depois de carregada.Em nosso ambiente, meu container div permanece vazio, então não consigo buscar o script marcação.Deve funcionar, porém, porque no meu exemplo acima o script não é executado, mas ainda faz parte do DOM.

Licenciado em: CC-BY-SA com atribuição
Não afiliado a StackOverflow
scroll top