4

Давайте представим, что мы имеем эти модели Django:Есть ли событие или другой способ вызова функции Javascript, когда Django Admin Popup (зеленый значок плюс) завершается?

class Band(models.Model): 
    name = models.CharField(max_length=256, default="Eagles of Death Metal") 

class Song(models.Model): 
    band = models.ForeignKey(Band) 

При использовании администратора для управления этими моделями, то band поле связано с Widget вынесенным Джанго как select HTML элемента.

администратора Django также добавляет значок зеленый плюс рядом с select, щелкнув по нему откроется всплывающее окно, в котором пользователю представлено с Form, чтобы добавить новую группу. При нажатии кнопки save в этом всплывающем окне новое имя группы сохраняется в БД и автоматически присваивается значению select.


Мы полагаемся на некоторые JavaScript будет запускаться каждый раз select изменения значения. В настоящее время он прослушивает событие change указанного элемента, который отлично работает, когда пользователь щелкает значение непосредственно в меню, предложенном select.

К сожалению, когда это select заполняется через функциональные возможности администратора Popup, это кажется change событие не уволили за select, как наш обратный вызов не выполняется, даже если значение элемента на самом деле изменилось.

Есть ли еще одно событие, которое мы можем прослушать, чтобы получить такое же поведение, чем когда пользователь щелкает значение непосредственно из списка?

ответ

5

Это фрагмент Javascript с хакерами, которые мы используем для запуска события изменения, когда всплывающее окно добавления/изменения админа Django отклонено.

Мы используем это с Django 1.7, поэтому он работает для этой версии как минимум.

Monkey-patch для JS-методов администратора Django для достижения этого - не очень элегантный способ выполнить эту работу, но это был наименее навязчивый вариант, который мы нашли. Если кто-то знает лучший способ, дайте нам все знать.

/* 
* Trigger change events when Django admin's popup window is dismissed 
*/ 
(function($) { 
    $(document).ready(function() { 

     // HACK to override `dismissRelatedLookupPopup()` and 
     // `dismissAddAnotherPopup()` in Django's RelatedObjectLookups.js to 
     // trigger change event when an ID is selected or added via popup. 
     function triggerChangeOnField(win, chosenId) { 
      var name = windowname_to_id(win.name); 
      var elem = document.getElementById(name); 
      $(elem).change(); 
     } 

     window.ORIGINAL_dismissRelatedLookupPopup = window.dismissRelatedLookupPopup 
     window.dismissRelatedLookupPopup = function(win, chosenId) { 
      ORIGINAL_dismissRelatedLookupPopup(win, chosenId); 
      triggerChangeOnField(win, chosenId); 
     } 

     window.ORIGINAL_dismissAddAnotherPopup = window.dismissAddAnotherPopup 
     window.dismissAddAnotherPopup = function(win, chosenId) { 
      ORIGINAL_dismissAddAnotherPopup(win, chosenId); 
      triggerChangeOnField(win, chosenId); 
     } 

    }); 
})(jQuery); 
+0

Это тот же ответ, который я отправил в список рассылки Django Users, но Stack Overflow лучше использовать для этого фрагмента кода, который будет использоваться или обсуждаться. Вот этот дискуссионный поток: https://groups.google.com/d/msg/django-users/7sIM2-9XirY/d6Yr5_fFBwAJ –

+0

Большое спасибо, это позволило реализовать функциональность. Мы используем ** Django 1.8 **, который требует только двух небольших изменений: 'rejectAddAnotherPopup' следует переименовать в' rejectAddRelatedObjectPopup', и он должен взять (и переслать) дополнительный аргумент ('newRepr'). –

+0

Открыт [еще один вопрос, связанный с всплывающим именем администратора Django] (http://stackoverflow.com/q/33941944/1027706), если у вас есть ключ? –