Bootstrap 3 con Modal remoto


Acabo de empezar un nuevo proyecto con la nueva versión de Twitter Bootstrap : bootstrap 3. No puedo hacer que el Modal funcione en el modo remoto. Solo quiero que cuando haga clic en un enlace muestre el modal con el contenido de la url remota. Funciona, pero el diseño modal está completamente destruido.

Aquí hay un enlace a un jsfiddle : http://jsfiddle.net/NUCgp/5/

El código:

<a data-toggle="modal" href="http://fiddle.jshell.net/Sherbrow/bHmRB/0/show/" data-target="#myModal">Click me !</a>

<!-- Modal -->
<div class="modal fade" id="myModal" tabindex="-1" role="dialog" aria-labelledby="myModalLabel" aria-hidden="true">
    <div class="modal-dialog">
        <div class="modal-content">
            <div class="modal-header">
                <button type="button" class="close" data-dismiss="modal" aria-hidden="true">&times;</button>
                 <h4 class="modal-title">Modal title</h4>

            </div>
            <div class="modal-body"><div class="te"></div></div>
            <div class="modal-footer">
                <button type="button" class="btn btn-default" data-dismiss="modal">Close</button>
                <button type="button" class="btn btn-primary">Save changes</button>
            </div>
        </div>
        <!-- /.modal-content -->
    </div>
    <!-- /.modal-dialog -->
</div>
<!-- /.modal -->

¿Puede alguien hacer que este simple ejemplo funcione ?

Author: Ian Kemp, 2013-08-22

9 answers

En cuanto a la opción remota para modales, desde los documentos :

Si se proporciona una URL remota, el contenido se cargará a través de la carga de jQuery método e inyectado en la raíz del elemento modal.

Eso significa que su archivo remoto debe proporcionar la estructura modal completa, no solo lo que desea mostrar en el cuerpo.

Bootstrap 3.1 Actualización:

En la v3. 1 se cambió el comportamiento anterior y ahora se carga el contenido remoto hacia .modal-content

Ver esto Violín de demostración

Actualización de Boostrap 3.3:

Esta opción está obsoleta desde la versión 3.3.0 y se ha eliminado en la versión 4. Recomendamos usar plantillas del lado del cliente o un marco de enlace de datos, o llamar a jQuery.cargue usted mismo.

 105
Author: koala_dev,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2016-04-08 11:57:03

Para Bootstrap 3

El flujo de trabajo con el que tuve que lidiar era cargar contenido con un contexto url que podía cambiar. Así que por defecto configurar su modal con javascript o el href para el contexto predeterminado que desea mostrar:

$('#myModal').modal({
        show: false,
        remote: 'some/context'
});

Destruir el modal no funcionaría para mí porque no estaba cargando desde el mismo control remoto, por lo que tuve que :

$(".some-action-class").on('click', function () {
        $('#myModal').removeData('bs.modal');
        $('#myModal').modal({remote: 'some/new/context?p=' + $(this).attr('buttonAttr') });
        $('#myModal').modal('show');
});

Esto, por supuesto, se refactorizó fácilmente en una biblioteca js y le da mucha flexibilidad con la carga de modales

Espero esto le ahorra a alguien 15 minutos de retoques.

 28
Author: zorkle,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2014-01-25 14:35:42

Si no desea enviar la estructura modal completa, puede replicar el comportamiento anterior haciendo algo como esto:

// this is just an example, remember to adapt the selectors to your code!
$('.modal-link').click(function(e) {
    var modal = $('#modal'), modalBody = $('#modal .modal-body');

    modal
        .on('show.bs.modal', function () {
            modalBody.load(e.currentTarget.href)
        })
        .modal();
    e.preventDefault();
});
 18
Author: MM.,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2013-08-27 11:06:34

Aquí está mi solución (aprovechando algunas de las anteriores) que hace uso de la propia estructura de BS3 para restablecer el antiguo comportamiento de carga remota. Debe ser transparente.

Voy a mantener la variable de código pesada y descriptiva para mantener las cosas comprensibles. También estoy asumiendo la presencia de jQuery. Los tipos de levantadores pesados de Javascript simplificarán fácilmente el código.

Para referencia aquí hay un enlace que invoca un modal BS3:

<li><a data-toggle="modal" href="terms.html" data-target="#terms">Terms of Use</a></li>

En tu Javascript vas a necesitar el siguiente.

// Make sure the DOM elements are loaded and accounted for
$(document).ready(function() {

  // Match to Bootstraps data-toggle for the modal
  // and attach an onclick event handler
  $('a[data-toggle="modal"]').on('click', function(e) {

    // From the clicked element, get the data-target arrtibute
    // which BS3 uses to determine the target modal
    var target_modal = $(e.currentTarget).data('target');
    // also get the remote content's URL
    var remote_content = e.currentTarget.href;

    // Find the target modal in the DOM
    var modal = $(target_modal);
    // Find the modal's <div class="modal-body"> so we can populate it
    var modalBody = $(target_modal + ' .modal-body');

    // Capture BS3's show.bs.modal which is fires
    // immediately when, you guessed it, the show instance method
    // for the modal is called
    modal.on('show.bs.modal', function () {
            // use your remote content URL to load the modal body
            modalBody.load(remote_content);
        }).modal();
        // and show the modal

    // Now return a false (negating the link action) to prevent Bootstrap's JS 3.1.1
    // from throwing a 'preventDefault' error due to us overriding the anchor usage.
    return false;
  });
});

Estamos casi allí. Una cosa que puede querer hacer es diseñar el cuerpo modal con una altura máxima, para que el contenido largo se desplace.

En tu CSS, necesitarás lo siguiente:

.modal-body{
    max-height: 300px;
    overflow-y: scroll;
}

Solo por referencia incluiré el HTML del modal, que es una copia de cada Ejemplo Modal de Bootsrap que hayas visto:

<div id="terms" class="modal fade">
  <div class="modal-dialog">
    <div class="modal-content">
      <div class="modal-header">
        <button type="button" class="close" data-dismiss="modal" aria-hidden="true">&times;</button>
        <h3 id="termsLabel" class="modal-title">TERMS AND CONDITIONS</h3>
      </div>
      <div class="modal-body">
      </div>
      <div class="modal-footer">
        <button type="button" class="btn btn-default" data-dismiss="modal">Close</button>
      </div>
    </div><!-- /.modal-content -->
  </div><!-- /.modal-dialog -->
</div><!-- /.modal -->
 14
Author: TheAdventurist,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2014-03-08 02:33:47

Hice esto:

$('#myModal').on 'shown.bs.modal', (e) ->  
  $(e.target).find('.modal-body').load('http://yourserver.com/content')
 9
Author: MBHNYC,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2014-01-07 03:17:30

Por mucho que no me guste modificar el código Bootstrap (hace que la actualización sea más difícil), simplemente puede agregar ".encontrar('.modal-body') a la sentencia load en modal.js as follows:

// original code
// if (this.options.remote) this.$element.load(this.options.remote)

// modified code
if (this.options.remote) this.$element.find('.modal-body').load(this.options.remote)
 8
Author: esvendsen,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2013-09-03 18:26:12

Aquí está el método que uso. No requiere ningún elemento DOM oculto en la página, y solo requiere una etiqueta de anclaje con el href del parcial modal, y una clase de 'modalTrigger'. Cuando el modal está cerrado (oculto) se elimina del DOM.

  (function(){
        // Create jQuery body object
        var $body = $('body'),

        // Use a tags with 'class="modalTrigger"' as the triggers
        $modalTriggers = $('a.modalTrigger'),

        // Trigger event handler
        openModal = function(evt) {
              var $trigger = $(this),                  // Trigger jQuery object

              modalPath = $trigger.attr('href'),       // Modal path is href of trigger

              $newModal,                               // Declare modal variable

              removeModal = function(evt) {            // Remove modal handler
                    $newModal.off('hidden.bs.modal');  // Turn off 'hide' event
                    $newModal.remove();                // Remove modal from DOM
              },

              showModal = function(data) {             // Ajax complete event handler
                    $body.append(data);                // Add to DOM
                    $newModal = $('.modal').last();    // Modal jQuery object
                    $newModal.modal('show');           // Showtime!
                    $newModal.on('hidden.bs.modal',removeModal); // Remove modal from DOM on hide
              };

              $.get(modalPath,showModal);             // Ajax request

              evt.preventDefault();                   // Prevent default a tag behavior
        };

        $modalTriggers.on('click',openModal);         // Add event handlers
  }());

Para usar, simplemente cree una etiqueta a con el href del parcial modal:

<a href="path/to/modal-partial.html" class="modalTrigger">Open Modal</a>
 5
Author: Brandon Fitzpatrick,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2015-07-22 08:44:30

Otra gran y fácil manera es tener un modal ciego en su diseño y llamarlo si es necesario.

JS

  var remote_modal = function(url) {
    // reset modal body with a spinner or empty content
    spinner = "<div class='text-center'><i class='fa fa-spinner fa-spin fa-5x fa-fw'></i></div>"

    $("#remote-modal .modal-body").html(spinner)
    $("#remote-modal .modal-body").load(url);
    $("#remote-modal").modal("show");
  }

Y su HTML

 <div class='modal fade' id='remote-modal'>
    <div class='modal-dialog modal-lg'>
      <div class='modal-content'>
        <div class='modal-body'></div>
        <div class='modal-footer'>
          <button class='btn btn-default'>Close</button>
        </div>
      </div>
    </div>
  </div>
</body>

Ahora puede simplemente llamar a remote_modal('/my/url.html') y el contenido se muestra dentro del modal

 4
Author: huan son,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2016-11-24 07:23:07

Lo hago de esta manera:

<!-- global template loaded in all pages // -->
     <div id="NewsModal" class="modal fade" tabindex="-1" role="dialog" data-ajaxload="true" aria-labelledby="newsLabel" aria-hidden="true">
            <div class="modal-dialog">
                <div class="modal-content">
                    <div class="modal-header">
                        <button type="button" class="close" data-dismiss="modal" aria-hidden="true">×</button>
                        <h3 class="newsLabel"></h3>
                    </div>
                    <div class="modal-body">
                            <div class="loading">
                                <span class="caption">Loading...</span>
                               <img src="/images/loading.gif" alt="loading">
                        </div>
                    </div>
                    <div class="modal-footer caption">
                        <button class="btn btn-right default modal-close" data-dismiss="modal">Close</button>
                    </div>
                </div>
            </div>
        </div>

Aquí está mi href:

<a href="#NewsModal" onclick="remote=\'modal_newsfeed.php?USER='.trim($USER).'&FUNCTION='.trim(urlencode($FUNCTIONCODE)).'&PATH_INSTANCE='.$PATH_INSTANCE.'&ALL=ALL\'
                                        remote_target=\'#NewsModal .modal-body\'" role="button" data-toggle="modal">See All Notifications <i class="m-icon-swapright m-icon-dark"></i></a>
 0
Author: yardpenalty,
Warning: date(): Invalid date.timezone value 'Europe/Kyiv', we selected the timezone 'UTC' for now. in /var/www/agent_stack/data/www/ajaxhispano.com/template/agent.layouts/content.php on line 61
2016-08-22 15:05:04