web-dev-qa-db-fra.com

Existe-t-il un redresseur automatique de hauteur iframe inter-domaines qui fonctionne?

J'ai essayé quelques solutions mais sans succès. Je me demande s'il existe une solution, de préférence avec un tutoriel facile à suivre.

93
J82

Vous avez trois alternatives:

1. Utilisez iFrame-resizer

Ceci est une bibliothèque simple pour garder les iFrames dimensionnées à leur contenu. Il utilise les API PostMessage et MutationObserver, avec des solutions de rechange pour IE8-10. Il propose également des options permettant à la page de contenu de demander que l'iFrame contenant une certaine taille soit également fermé. Il peut également fermer l'iFrame lorsque vous avez terminé.

https://github.com/davidjbradshaw/iframe-resizer

2. Utilisez Easy XDM (combo PostMessage + Flash)

Easy XDM utilise un ensemble d’astuces pour permettre la communication interdomaine entre différentes fenêtres dans plusieurs navigateurs. Il existe des exemples pour l’utiliser pour le redimensionnement iframe:

http://easyxdm.net/wp/2010/03/17/resize-iframe-based-on-content/

http://kinsey.no/blog/index.php/2010/02/19/resizing-iframes-using-easyxdm/

Easy XDM fonctionne en utilisant PostMessage sur les navigateurs modernes et une solution basée sur Flash comme solution de secours pour les navigateurs plus anciens.

Voir aussi ce fil sur Stackoverflow (il y en a aussi d'autres, c'est une question fréquemment posée). En outre, Facebook semblerait utiliser une approche similaire .

3. Communiquer via un serveur

Une autre option consisterait à envoyer la hauteur d'iframe à votre serveur, puis à interroger ce serveur à partir de la page Web parent avec JSONP (ou à utiliser une interrogation longue si possible).

65
Janne Aukia

J'ai eu la solution pour régler la hauteur de l'iframe dynamiquement en fonction de son contenu. Cela fonctionne pour le contenu interdomaine. Il y a quelques étapes à suivre pour y parvenir.

  1. Supposons que vous ayez ajouté iframe dans la page Web "abc.com/page"

    <div> <iframe id="IframeId" src="http://xyz.pqr/contactpage" style="width:100%;" onload="setIframeHeight(this)"></iframe> </div>

  2. Ensuite, vous devez lier l'événement "message" Windows sous la page Web "abc.com/page".

window.addEventListener('message', function (event) {
//Here We have to check content of the message event  for safety purpose
//event data contains message sent from page added in iframe as shown in step 3
if (event.data.hasOwnProperty("FrameHeight")) {
        //Set height of the Iframe
        $("#IframeId").css("height", event.data.FrameHeight);        
    }
});

On iframe load you have to send message to iframe window content with "FrameHeight" message

function setIframeHeight(ifrm) {
   var height = ifrm.contentWindow.postMessage("FrameHeight", "*");   
}
  1. Sur la page principale qui a été ajoutée sous iframe ici "xyz.pqr/contactpage", vous devez lier un événement "message" à Windows, où tous les messages recevront de la fenêtre parente de "abc.com/page".
window.addEventListener('message', function (event) {
    
    // Need to check for safty as we are going to process only our messages
    // So Check whether event with data(which contains any object) contains our message here its "FrameHeight"
   if (event.data == "FrameHeight") {

        //event.source contains parent page window object 
        //which we are going to use to send message back to main page here "abc.com/page"
        
        //parentSourceWindow = event.source;
        
        //Calculate the maximum height of the page
        var body = document.body, html = document.documentElement;
        var height = Math.max(body.scrollHeight, body.offsetHeight,
            html.clientHeight, html.scrollHeight, html.offsetHeight);
       
       // Send height back to parent page "abc.com/page"
        event.source.postMessage({ "FrameHeight": height }, "*");       
    }
});

Enfin, votre hauteur d'iframe sera définie lors du chargement d'iframe.

Bon codage !!!

21
Sudhir

Ce que j'ai fait était de comparer le scrollWidth iframe jusqu'à ce qu'il change de taille tout en définissant de manière incrémentielle la hauteur IFrame. Et cela a bien fonctionné pour moi. Vous pouvez ajuster l’incrément à votre guise.

   <script type="text/javascript">
    function AdjustIFrame(id) {
        var frame = document.getElementById(id);
        var maxW = frame.scrollWidth;
        var minW = maxW;
        var FrameH = 100; //IFrame starting height
        frame.style.height = FrameH + "px"

        while (minW == maxW) {
            FrameH = FrameH + 100; //Increment
            frame.style.height = FrameH + "px";
            minW = frame.scrollWidth;
        }
    }

   </script>


<iframe id="RefFrame" onload="AdjustIFrame('RefFrame');" class="RefFrame"
    src="http://www.YourUrl.com"></iframe>
14
Troy Mitchel

Voici ma solution simple sur cette page. http://lab.ohshiftlabs.com/iframesize/

Voici comment cela fonctionne.

enter image description here

En gros, si vous êtes capable de modifier une page sur un autre domaine, vous pouvez placer une autre page iframe appartenant à votre serveur, qui évite les cookies. Avec un intervalle de lecture des cookies lors de la mise à jour, mettez à jour la hauteur de l'iframe. C'est tout.

Télécharger; http://lab.ohshiftlabs.com/iframesize/iframesizepost.Zip

1
siniradam

J'ai trouvé une autre solution côté Web pour les développeurs Web en utilisant PHP pour obtenir la taille d'un iframe.

Le premier utilise le script de serveur PHP pour un appel externe via une fonction interne: (comme un file_get_contents Avec mais curl et dom).

function curl_get_file_contents($url,$proxyActivation=false) {
    global $proxy;
    $c = curl_init();
    curl_setopt($c, CURLOPT_RETURNTRANSFER, 1);
    curl_setopt($c, CURLOPT_USERAGENT, "Mozilla/5.0 (Windows; U; Windows NT 5.2; en-US; rv:1.8.1.7) Gecko/20070914 Firefox/2.0.0.7");
    curl_setopt($c, CURLOPT_REFERER, $url);
    curl_setopt($c, CURLOPT_URL, $url);
    curl_setopt($c, CURLOPT_FOLLOWLOCATION, 1);
    if($proxyActivation) {
        curl_setopt($c, CURLOPT_PROXY, $proxy);
    }
    $contents = curl_exec($c);
    curl_close($c);
    $dom = new DOMDocument();
    $dom->preserveWhiteSpace = false;
    @$dom->loadHTML($contents);
    $form = $dom->getElementsByTagName("body")->item(0);
    if ($contents) //si on a du contenu
        return $dom->saveHTML();
    else
        return FALSE;
}
$url = "http://www.google.com"; //Exernal url test to iframe
<html>
    <head>
    <script type="text/javascript">

    </script>
    <style type="text/css">
    #iframe_reserve {
        width: 560px;
        height: 228px
    }
    </style>
    </head>

    <body>
        <div id="iframe_reserve"><?php echo curl_get_file_contents($url); ?></div>

        <iframe id="myiframe" src="http://www.google.com" scrolling="no" marginwidth="0" marginheight="0" frameborder="0"  style="overflow:none; width:100%; display:none"></iframe>

        <script type="text/javascript">
            window.onload = function(){
            document.getElementById("iframe_reserve").style.display = "block";
            var divHeight = document.getElementById("iframe_reserve").clientHeight;
            document.getElementById("iframe_reserve").style.display = "none";
            document.getElementById("myiframe").style.display = "block";
            document.getElementById("myiframe").style.height = divHeight;
            alert(divHeight);
            };
        </script>
    </body>
</html>

Vous devez afficher sous la div (iframe_reserve) Le code HTML généré par l'appel de la fonction en utilisant un simple echo curl_get_file_contents("location url iframe","activation proxy")

Après cela, une fonction d’événement body onload avec javascript prend la hauteur de la page iframe avec un simple contrôle du contenu div (iframe_reserve)

J'ai donc utilisé divHeight = document.getElementById("iframe_reserve").clientHeight; pour obtenir la hauteur de la page externe que nous allons appeler après avoir masqué le conteneur div (iframe_reserve). Après cela, nous chargeons l’iframe avec sa bonne hauteur, c’est tout.

0
headmax

J'ai un script qui tombe dans l'iframe avec son contenu. Il s'assure également que iFrameResizer existe (il l'injecte sous forme de script), puis effectue le redimensionnement.

Je vais laisser tomber dans un exemple simplifié ci-dessous.

// /js/embed-iframe-content.js

(function(){
    // Note the id, we need to set this correctly on the script tag responsible for
    // requesting this file.
    var me = document.getElementById('my-iframe-content-loader-script-tag');

    function loadIFrame() {
        var ifrm = document.createElement('iframe');
        ifrm.id = 'my-iframe-identifier';
        ifrm.setAttribute('src', 'http://www.google.com');
        ifrm.style.width = '100%';
        ifrm.style.border = 0;
        // we initially hide the iframe to avoid seeing the iframe resizing
        ifrm.style.opacity = 0;
        ifrm.onload = function () {
            // this will resize our iframe
            iFrameResize({ log: true }, '#my-iframe-identifier');
            // make our iframe visible
            ifrm.style.opacity = 1;
        };

        me.insertAdjacentElement('afterend', ifrm);
    }

    if (!window.iFrameResize) {
        // We first need to ensure we inject the js required to resize our iframe.

        var resizerScriptTag = document.createElement('script');
        resizerScriptTag.type = 'text/javascript';

        // IMPORTANT: insert the script tag before attaching the onload and setting the src.
        me.insertAdjacentElement('afterend', ifrm);

        // IMPORTANT: attach the onload before setting the src.
        resizerScriptTag.onload = loadIFrame;

        // This a CDN resource to get the iFrameResizer code.
        // NOTE: You must have the below "coupled" script hosted by the content that
        // is loaded within the iframe:
        // https://unpkg.com/[email protected]/js/iframeResizer.contentWindow.min.js
        resizerScriptTag.src = 'https://unpkg.com/[email protected]/js/iframeResizer.min.js';
    } else {
        // Cool, the iFrameResizer exists so we can just load our iframe.
        loadIFrame();
    }    
}())

Ensuite, le contenu iframe peut être injecté n’importe où dans une autre page/site en utilisant le script de la manière suivante:

<script
  id="my-iframe-content-loader-script-tag"
  type="text/javascript"
  src="/js/embed-iframe-content.js"
></script>

Le contenu de l'iframe sera injecté ci-dessous où que vous placiez la balise de script.

J'espère que cela est utile à quelqu'un. ????

0
ctrlplusb