From 4a848948a06f079081bde94d33bb016a671877a4 Mon Sep 17 00:00:00 2001 From: Fabio Caccamo Date: Fri, 31 Aug 2018 15:21:30 +0200 Subject: [PATCH] Added modal to raw_id_fields #37 --- .../related-modal/related-modal.js | 93 ++++++++++++++----- 1 file changed, 68 insertions(+), 25 deletions(-) diff --git a/admin_interface/static/admin_interface/related-modal/related-modal.js b/admin_interface/static/admin_interface/related-modal/related-modal.js index cad11cb..5118b5c 100644 --- a/admin_interface/static/admin_interface/related-modal/related-modal.js +++ b/admin_interface/static/admin_interface/related-modal/related-modal.js @@ -1,23 +1,45 @@ -if(typeof django !== 'undefined' && typeof django.jQuery !== 'undefined' ) +if (typeof(django) !== 'undefined' && typeof(django.jQuery) !== 'undefined') { (function($) { $(document).ready(function(){ - // create the function that will close the modal - function dismissRelatedObjectModal() + function dismissModal() { - // close the popup as modal $.magnificPopup.close(); } - // assign the function to a global variable + // create the function that will close the modal + function dismissRelatedObjectModal() + { + dismissModal(); + } + + function dismissRelatedLookupModal(win, chosenId) + { + var windowRef = win; + var windowName = windowRef.name; + var widgetName = windowName.replace(/^(change|add|delete|lookup)_/, ''); + var widgetEl = $('#' + widgetName); + var widgetVal = widgetEl.val(); + if (widgetEl.hasClass('vManyToManyRawIdAdminField') && Boolean(widgetVal)) { + widgetEl.val(widgetVal + ', ' + chosenId); + } else { + widgetEl.val(chosenId); + } + dismissModal(); + } + + // assign functions to global variables window.dismissRelatedObjectModal = dismissRelatedObjectModal; + window.dismissRelatedLookupPopup = dismissRelatedLookupModal; function presentRelatedObjectModal(e) { - var href = ($(this).attr('href') || ''); - if( href == '' ){ + var linkEl = $(this); + + var href = (linkEl.attr('href') || ''); + if (href == '') { return; } @@ -26,40 +48,57 @@ if(typeof django !== 'undefined' && typeof django.jQuery !== 'undefined' ) e.stopImmediatePropagation(); // remove focus from clicked link - $(this).blur(); + linkEl.blur(); // use the clicked link id as iframe name // it will be available as window.name in the loaded iframe - var iframeName = $(this).attr('id'); - // var iframeName = String(window.name + '____' + $(this).attr('id')); - // console.log('open modal with name: "' + iframeName + '"'); - - // browsers stop loading nested iframes having the same src url - // create a random parameter and append it to the src url to prevent it - var iframeSrcRandom = String(Math.round(Math.random() * 999999)); + var iframeName = linkEl.attr('id'); var iframeSrc = href; - // fix for django 1.7 - if( iframeSrc.indexOf('_popup=1') == -1 ){ - iframeSrc += '&_popup=1'; + if (e.data.lookup !== true) + { + // browsers stop loading nested iframes having the same src url + // create a random parameter and append it to the src url to prevent it + // this workaround doesn't work with related lookup url + var iframeSrcRandom = String(Math.round(Math.random() * 999999)); + if( iframeSrc.indexOf('?') === -1 ){ + iframeSrc += '?_modal=' + iframeSrcRandom; + } else { + iframeSrc += '&_modal=' + iframeSrcRandom; + } } - iframeSrc += '&_modal=' + iframeSrcRandom; + // fix for django 1.7 + if (iframeSrc.indexOf('_popup=1') === -1) { + if (iframeSrc.indexOf('?') === -1) { + iframeSrc += '?_popup=1'; + } else { + iframeSrc += '&_popup=1'; + } + } // build the iframe html - // var iframeHTML = ''; var iframeHTML = ''; - // create the iframe jquery element var iframeEl = $(iframeHTML); + if (e.data.lookup === true) + { + // set current window as iframe opener because + // the callback is called on the opener window + iframeEl.load(function(){ + var iframeObj = $(this).get(0); + var iframeWindow = iframeObj.contentWindow; + iframeWindow.opener = window; + }); + } + // the modal css class var iframeInternalModalClass = 'related-modal'; // if the current window is inside an iframe, it means that it is already in a modal, // append an additional css class to the modal to offer more customization - if( window.top != window.self ) - { + if (window.top != window.self) { iframeInternalModalClass += ' related-modal__nested'; } @@ -79,10 +118,14 @@ if(typeof django !== 'undefined' && typeof django.jQuery !== 'undefined' ) // django 1.7 compatibility $('a.add-another').removeAttr('onclick'); - $('a.add-another').click( presentRelatedObjectModal ); + $('a.add-another').click({ lookup:false }, presentRelatedObjectModal); // django 1.8 and above - $('a.related-widget-wrapper-link').click( presentRelatedObjectModal ); + $('a.related-widget-wrapper-link').click({ lookup:false }, presentRelatedObjectModal); + + // raw_id_fields support + $('a.related-lookup').unbind('click'); + $('a.related-lookup').click({ lookup:true }, presentRelatedObjectModal); }); })(django.jQuery);