мультизагрузка изображений в админке

remotes/origin/tests
Slava Kyrachevsky 9 years ago
parent a8b7ab3282
commit 0074d64068
  1. 4
      apps/conference/admin.py
  2. 6
      apps/exposition/admin.py
  3. 44
      apps/functions/admin_views.py
  4. 78
      apps/photologue/admin.py
  5. 6
      apps/place_exposition/admin.py
  6. 22
      static/custom_js/main.js
  7. 94
      static/custom_js/make_select.js
  8. 340
      static/jQuery-filer/js/init.js
  9. 3
      templates/c_admin/accounts/user_change.html
  10. 3
      templates/c_admin/admin_list.html
  11. 1
      templates/c_admin/article/article_add.html
  12. 1
      templates/c_admin/article/blog_form.html
  13. 3
      templates/c_admin/blog/blog_add.html
  14. 1
      templates/c_admin/city/city_add.html
  15. 1
      templates/c_admin/company/company_add.html
  16. 1
      templates/c_admin/conference/conference.html
  17. 1
      templates/c_admin/conference/conference_add.html
  18. 1
      templates/c_admin/country/country_add.html
  19. 48
      templates/c_admin/exposition/exposition.html
  20. 1
      templates/c_admin/exposition/exposition_add.html
  21. 3
      templates/c_admin/import templates/export.html
  22. 3
      templates/c_admin/import templates/export_event.html
  23. 83
      templates/c_admin/includes/photogallery.html
  24. 1
      templates/c_admin/meta/create_seo_text.html
  25. 1
      templates/c_admin/meta/meta_setting.html
  26. 1
      templates/c_admin/news/news_add.html
  27. 1
      templates/c_admin/organiser/organiser_add.html
  28. 1
      templates/c_admin/page/new_page.html
  29. 1
      templates/c_admin/photogallery/admin_gallery.html
  30. 1
      templates/c_admin/photogallery/admin_photo.html
  31. 1
      templates/c_admin/photoreport/photoreport_add.html
  32. 1
      templates/c_admin/place_conference/place_conference.html
  33. 102
      templates/c_admin/place_conference/place_conference_add.html
  34. 1
      templates/c_admin/place_exposition/hall.html
  35. 1
      templates/c_admin/place_exposition/place_exposition.html
  36. 1
      templates/c_admin/place_exposition/place_exposition_add.html
  37. 1
      templates/c_admin/seminar/seminar_add.html
  38. 1
      templates/c_admin/service/service_add.html
  39. 1
      templates/c_admin/settings/main_page.html
  40. 1
      templates/c_admin/theme/tag_add.html
  41. 1
      templates/c_admin/theme/theme_add.html
  42. 1
      templates/c_admin/translator/translator.html
  43. 1
      templates/c_admin/translator/translator_add.html
  44. 1
      templates/c_admin/webinar/webinar_add.html

@ -37,7 +37,7 @@ from functions.admin_views import (
AdminListView,
AdminView,
stat_paginate_results,
upload_photo
# upload_photo
)
from functions.custom_views import delete_object, objects_list
from functions.views_help import get_referer
@ -45,6 +45,7 @@ from functions.admin import DefaultAdmin
from haystack.query import SearchQuerySet
from models import Conference, Statistic, TimeTable, Speaker
from photologue.forms import PhotoForm
from photologue.admin import upload_photo
from theme.models import Tag
@ -349,7 +350,6 @@ class ConferenceListView(AdminListView):
model = Conference
# FIXME: WTF?
@csrf_exempt
def upload_conference_photo(request, conf_id):
return upload_photo(request, conf_id, Conference)

@ -13,6 +13,7 @@ from django.forms.models import modelformset_factory
from django.http import HttpResponse, HttpResponseRedirect
from django.shortcuts import render_to_response
from django.utils import translation
from django.views.decorators.csrf import csrf_exempt
from file.forms import FileForm, FileModelForm
from file.models import FileModel, TmpFile
from forms import (
@ -26,13 +27,14 @@ from functions.admin_views import (
AdminListView,
AdminView,
stat_paginate_results,
upload_photo
# upload_photo
)
from functions.custom_views import delete_object, objects_list
from functions.views_help import get_referer
from haystack.query import SearchQuerySet
from models import Exposition, Statistic, TimeTable, TmpTimeTable
from photologue.forms import PhotoForm
from photologue.admin import upload_photo
from theme.models import Tag
@ -346,6 +348,8 @@ class ExpositionListView(AdminListView):
form_class = ExpositionFilterForm
model = Exposition
@csrf_exempt
def upload_exposition_photo(request, expo_id):
return upload_photo(request, expo_id, Exposition)

@ -147,26 +147,24 @@ class AdminListView(FormView):
return context
# FIXME: WTF?
@csrf_exempt
def upload_photo(request, id, Model):
"""
uploading photo to some instance of Model
instance must have upload_photo method, which download photo
"""
obj = get_object_or_404(Model, pk=id)
if request.method == 'POST':
response = {'success': False}
form = PhotoForm(request.POST, request.FILES)
if form.is_valid():
photo = form.save()
obj.upload_photo(photo)
response['success'] = True
else:
response.update({'errors': form.errors})
return HttpResponse(json.dumps(response), content_type='application/json')
else:
return HttpResponse('not post')
# @csrf_exempt
# def upload_photo(request, id, Model):
# """
# uploading photo to some instance of Model
# instance must have upload_photo method, which download photo
#
# """
# obj = get_object_or_404(Model, pk=id)
# if request.method == 'POST':
# response = {'success': False}
# form = PhotoForm(request.POST, request.FILES)
# if form.is_valid():
# photo = form.save()
# obj.upload_photo(photo)
# response['success'] = True
# else:
# response.update({'errors': form.errors})
#
# return HttpResponse(json.dumps(response), content_type='application/json')
# else:
# return HttpResponse('not post')

@ -1,26 +1,19 @@
import json
from django import forms
from django.conf import settings
from django.shortcuts import HttpResponse
from django.contrib import admin
from django.contrib.sites.models import Site
from django.contrib import messages
from django.utils.translation import ungettext, ugettext_lazy as _
from django.shortcuts import HttpResponse, get_object_or_404
from django.views.generic import ListView, FormView
from django.http import HttpResponseRedirect
from .models import Gallery, Photo, GalleryUpload, PhotoEffect, PhotoSize, \
Watermark
from .models import Gallery, Photo
from .forms import PhotoForm, GalleryForm
MULTISITE = getattr(settings, 'PHOTOLOGUE_MULTISITE', False)
from sorl.thumbnail import get_thumbnail
MULTISITE = getattr(settings, 'PHOTOLOGUE_MULTISITE', False)
ENABLE_TAGS = getattr(settings, 'PHOTOLOGUE_ENABLE_TAGS', False)
#------------------EXPOMAP VIEWS----------------------------------------------
from django.views.generic import ListView, FormView
from forms import PhotoForm, GalleryForm
from django.shortcuts import render_to_response, get_object_or_404
from django.http import HttpResponseRedirect
class AdminViewObject(FormView):
"""
need overwrite get_form method for every class
@ -56,7 +49,6 @@ class AdminViewObject(FormView):
return context
class PhotoView(AdminViewObject):
model = Photo
form_class = PhotoForm
@ -77,14 +69,14 @@ class PhotoView(AdminViewObject):
data['sort'] = photo.sort
for code, name in settings.LANGUAGES:
obj = Photo._meta.translations_model.objects.get(language_code = code,master__id=getattr(photo, 'id')) #access to translated fields
obj = Photo._meta.translations_model.objects.get(language_code=code, master__id=getattr(photo, 'id')) # access to translated fields
data['title_%s' % code] = obj.title
data['caption_%s' % code] = obj.caption
#form.fields['tag'].widget.attrs['data-init-text'] = [item.name for item in article.tag.all()]
return form_class(data)
else:
return form_class()
class GalleryView(AdminViewObject):
model = Gallery
form_class = GalleryForm
@ -103,10 +95,9 @@ class GalleryView(AdminViewObject):
data = {}
for code, name in settings.LANGUAGES:
obj = Gallery._meta.translations_model.objects.get(language_code = code,master__id=getattr(gallery, 'id')) #access to translated fields
obj = Gallery._meta.translations_model.objects.get(language_code=code, master__id=getattr(gallery, 'id')) # access to translated fields
data['title_%s' % code] = obj.title
data['description_%s' % code] = obj.description
#form.fields['tag'].widget.attrs['data-init-text'] = [item.name for item in article.tag.all()]
return form_class(data)
else:
return form_class()
@ -124,6 +115,53 @@ class GalleryListView(ListView):
template_name = 'c_admin/photogallery/admin_gallery_list.html'
def upload_photo(request, id, Model):
"""
uploading photo to some instance of Model
instance must have upload_photo method, which download photo
"""
def get_images_list(obj):
"""
:param obj: instance of Model
:return: images list
"""
images = []
if obj.photogallery:
for img in obj.photogallery.photos.all():
im = get_thumbnail(
img.image, '188x143', crop='center', quality=99
)
images.append({
'name': img.title or img.image.name,
'size': img.image.size,
'file': im.url,
'type': 'image',
'remove_url': img.get_delete_url(),
'detail_link': img.admin_url()
})
return images
data = {'success': False}
obj = get_object_or_404(Model, pk=id)
if request.is_ajax() and request.method == 'POST':
form = PhotoForm(request.POST, request.FILES)
if form.is_valid():
photo = form.save()
obj.upload_photo(photo)
data['success'] = True
else:
data['errors'] = form.errors
elif request.is_ajax() and request.method == 'GET':
data['success'] = True
data['images'] = get_images_list(obj)
return HttpResponse(json.dumps(data), content_type='application/json')
def delete_photo(request, photo_id):
photo = get_object_or_404(Photo, pk=photo_id)
photo.delete()

@ -11,11 +11,12 @@ from django.contrib.auth.decorators import login_required
from django.forms.formsets import formset_factory
from django.forms.models import modelformset_factory
from django.utils.translation import get_language
from django.views.decorators.csrf import csrf_exempt
from haystack.query import SearchQuerySet
from functions.custom_views import objects_list, delete_object
from functions.views_help import get_referer
from functions.admin_views import AdminView, AdminListView, upload_photo, FormView
from functions.admin_views import AdminView, AdminListView # , upload_photo, FormView
from functions.http import JsonResponse
from exposition.admin import get_by_lang
@ -25,6 +26,7 @@ from city.models import City
from file.models import FileModel, TmpFile
from file.forms import FileModelForm, FileForm
from photologue.forms import PhotoForm
from photologue.admin import upload_photo
from place_conference.models import PlaceConference
from place_exposition.models import PlaceExposition
@ -285,7 +287,7 @@ class PlaceExpositionListView(AdminListView):
model = PlaceExposition
@csrf_exempt
def upload_place_photo(request, place_id):
return upload_photo(request, place_id, PlaceExposition)

@ -235,7 +235,7 @@ $(document).ready(function(){
return false;
});
// end on-of events
if( $("#id_city" ).length ) {
if( $("#id_city" ).length && $("#id_city" ).is('select') ) {
$('#id_city').select2({
placeholder: "Город",
width: 'element',
@ -275,7 +275,7 @@ $(document).ready(function(){
});
}
if( $("#id_main_page_news" ).length ) {
if( $("#id_main_page_news" ).length && $("#id_main_page_news").is('select')) {
$('#id_main_page_news').select2({
placeholder: "Новости",
multiple: true,
@ -325,7 +325,7 @@ $(document).ready(function(){
}
if( $("#id_tag" ).length ) {
if( $("#id_tag" ).length && $("#id_tag").is('select')) {
$('#id_tag').select2({
placeholder: "Теги",
width: '550px',
@ -490,13 +490,17 @@ $(document).ready(function(){
}
});
});
if($('select').length){
$('select').select2({
width: 'element',
allowClear: true
});
}
/* FIXME: Проверить все select2 */
// if($('select').length){
// try{
// $('select').select2({
// width: 'element',
// allowClear: true
//
// });
// } catch (e){}
// }

@ -1,94 +0,0 @@
//replace
$(document).ready(function(){
//$('#id_city').attr('disabled', true)
$('select').select2({
width: 'element',
allowClear: true
});//end select
$('#id_city').select2({
placeholder: "Search city",
width: 'element',
ajax: {
url: "/admin/city/search/",
dataType: "json",
quietMillis: 200,
data: function(term, page, country){
var country = $('#id_country').val()
return {term: term,
page: page,
country: country};
},
results: function (data) {
var results = [];
$.each(data, function(index, item){
results.push({
id: item.id,
text: item.label
});
});
return {results: results};
}
},
initSelection : function(element, callback) {
var id= $(element).val();
var text = $(element).attr('data-init-text');
callback({id: id, text:text});
}
});
//
$('#id_tag').select2({
placeholder: "Search tag",
width: '550px',
multiple: true,
ajax: {
url: "/admin/theme/tag/search/",
dataType: "json",
quietMillis: 200,
multiple: true,
data: function(term, page, theme){
var theme = $('#id_theme').serialize();
return {term: term,
page: page,
theme: theme};
},
results: function (data) {
var results = [];
$.each(data, function(index, item){
results.push({
id: item.id,
text: item.label
});
});
return {results: results};
}
},
initSelection : function(element, callback) {
var data = [];
$(element.val().split(",")).each(function(i) {
var item = this.split(':');
data.push({
id: item[0],
text: item[1]
});
});
callback(data);
}
});
})//end ready

@ -1,195 +1,167 @@
function init_filer($target) {
$target.find('.file_uploader').filer({
limit: null,
maxSize: null,
extensions: null,
changeInput: '<div class="jFiler-input-dragDrop"><div class="jFiler-input-inner"><div class="jFiler-input-icon"><i class="icon-jfi-cloud-up-o"></i></div><div class="jFiler-input-text"><h3>Drag&Drop files here</h3> <span style="display:inline-block; margin: 15px 0">or</span></div><a class="jFiler-input-choose-btn blue">Browse Files</a></div></div>',
showThumbs: true,
theme: "dragdropbox",
afterRender: function(l, p, o, s){
s[0].name = s[0].name.replace('[]', '')
},
templates: {
box: '<ul class="jFiler-items-list jFiler-items-grid"></ul>',
item: '<li class="jFiler-item not_loaded">\
<div class="jFiler-item-container">\
<div class="jFiler-item-inner">\
<a href="javascript:void(0);" class="jFiler-item-thumb">\
<div class="jFiler-item-status"></div>\
<div class="jFiler-item-thumb-overlay">\
<div class="jFiler-item-info">\
<div style="display:table-cell;vertical-align: middle;">\
<span class="jFiler-item-title"><b title="{{fi-name}}">{{fi-name}}</b></span>\
<span class="jFiler-item-others">{{fi-size2}}</span>\
</div>\
</div>\
</div>\
{{fi-image}}\
</a>\
<div class="jFiler-item-assets jFiler-row">\
<ul class="list-inline pull-left">\
<li>{{fi-progressBar}}</li>\
</ul>\
<ul class="list-inline pull-right">\
<li><a class="icon-jfi-trash jFiler-item-trash-action"></a></li>\
</ul>\
</div>\
</div>\
</div>\
</li>',
itemAppend: '<li class="jFiler-item">\
<div class="jFiler-item-container">\
<div class="jFiler-item-inner">\
<a href="javascript:void(0);" class="jFiler-item-thumb">\
<div class="jFiler-item-status"></div>\
<div class="jFiler-item-thumb-overlay">\
<div class="jFiler-item-info">\
<div style="display:table-cell;vertical-align: middle;">\
<span class="jFiler-item-title"><b title="{{fi-name}}">{{fi-name}}</b></span>\
<span class="jFiler-item-others">{{fi-size2}}</span>\
</div>\
</div>\
</div>\
{{fi-image}}\
</a>\
<div class="jFiler-item-assets jFiler-row">\
<ul class="list-inline pull-left">\
<li><span class="jFiler-item-others">{{fi-icon}}</span></li>\
</ul>\
<ul class="list-inline pull-right">\
<li><a class="icon-jfi-trash jFiler-item-trash-action"></a>{{fi-remove}}</li>\
</ul>\
</div>\
</div>\
</div>\
</li>',
progressBar: '<div class="bar"></div>',
itemAppendToEnd: true,
canvasImage: true,
removeConfirmation: true,
_selectors: {
list: '.jFiler-items-list',
//item: '.jFiler-item',
progressBar: '.bar',
remove: '.jFiler-item-trash-action'
}
},
dragDrop: {
dragEnter: null,
dragLeave: null,
drop: null,
dragContainer: null
},
uploadFile: {
url: $target.data('upload-url'),
//data: null,
type: 'POST',
enctype: 'multipart/form-data',
synchron: true,
beforeSend: function() {},
success: function(data, itemEl, listEl, boxEl, newInputEl, inputEl, id){
console.log(data);
console.log(itemEl);
console.log(listEl);
console.log(boxEl);
console.log(newInputEl);
console.log(inputEl);
console.log(id);
console.log('----------------------------');
var parent = itemEl.find(".jFiler-jProgressBar").parent();
itemEl.find(".jFiler-jProgressBar").fadeOut("slow", function(){
$("<div class=\"jFiler-item-others text-success\"><i class=\"icon-jfi-check-circle\"></i> Success</div>").hide().appendTo(parent).fadeIn("slow");
});
},
error: function(el){
var parent = el.find(".jFiler-jProgressBar").parent();
el.find(".jFiler-jProgressBar").fadeOut("slow", function(){
$("<div class=\"jFiler-item-others text-error\"><i class=\"icon-jfi-minus-circle\"></i> Error</div>").hide().appendTo(parent).fadeIn("slow");
});
},
statusCode: null,
onProgress: null,
onComplete: null
},
files: [
{
name: "appended_file.jpg",
size: 5453,
type: "image",
file: "http://127.0.0.1:8000/media/photologue/photos/cache/am_admin_thumbnail.jpg", // 188x143 crop="center"
url: "google.com.ua",
remove_url: '/remove-url/1/',
detail_link: '/detail_link/1/'
},
{
name: "appended_file_2.jpg",
size: 9453,
type: "image",
file: "http://127.0.0.1:8000/media/photologue/photos/cache/am_admin_thumbnail.jpg", // 188x143 crop="center"
url: "/qwerty/qwerty/",
remove_url: '/remove-url/2/',
detail_link: '/detail_link/1/'
},
{
name: "appended_file_2.jpg",
size: 9453,
type: "image",
file: "http://127.0.0.1:8000/media/photologue/photos/cache/am_admin_thumbnail.jpg", // 188x143 crop="center"
url: "/qwerty/qwerty/",
remove_url: '/remove-url/3/',
detail_link: '/detail_link/1/'
}
],
addMore: false,
allowDuplicates: true,
clipBoardPaste: true,
excludeName: null,
beforeRender: null,
beforeShow: null,
beforeSelect: null,
onSelect: null,
afterShow: null,
onRemove: function(itemEl, file, id, listEl, boxEl, newInputEl, inputEl){
var filerKit = inputEl.prop("jFiler"),
file_name = filerKit.files_list[id].name;
$.get($target.data('upload-url'), function(response){
var files = [];
if (response['success']) {
files = response['images'];
}
$.post('./php/ajax_remove_file.php', {file: file_name});
},
onEmpty: null,
options: null,
dialogs: {
alert: function(text) {
return alert(text);
},
confirm: function (text, callback) {
confirm(text) ? callback() : null;
}
},
captions: {
button: "Выберите файлы",
feedback: "Выберите файлы для загрузки",
feedback2: "выбранные файлы",
drop: "Перетяните файлы для загрузки",
removeConfirmation: "Вы уверены что хотите удалить этот файл?",
errors: {
filesLimit: "Only {{fi-limit}} files are allowed to be uploaded.",
filesType: "Only Images are allowed to be uploaded.",
filesSize: "{{fi-name}} is too large! Please upload file up to {{fi-maxSize}} MB.",
filesSizeAll: "Files you've choosed are too large! Please upload files up to {{fi-maxSize}} MB."
}
}
});
$target.find('.file_uploader').filer({
limit: null,
maxSize: null,
extensions: null,
changeInput: '<div class="jFiler-input-dragDrop"><div class="jFiler-input-inner"><div class="jFiler-input-icon"><i class="icon-jfi-cloud-up-o"></i></div><div class="jFiler-input-text"><h3>Drag&Drop files here</h3> <span style="display:inline-block; margin: 15px 0">or</span></div><a class="jFiler-input-choose-btn blue">Browse Files</a></div></div>',
showThumbs: true,
theme: "dragdropbox",
afterRender: function(l, p, o, s){
s[0].name = s[0].name.replace('[]', '')
},
templates: {
box: '<ul class="jFiler-items-list jFiler-items-grid"></ul>',
item: '<li class="jFiler-item">\
<div class="jFiler-item-container">\
<div class="jFiler-item-inner">\
<a href="javascript:void(0);" class="jFiler-item-thumb">\
<div class="jFiler-item-status"></div>\
<div class="jFiler-item-thumb-overlay">\
<div class="jFiler-item-info">\
<div style="display:table-cell;vertical-align: middle;">\
<span class="jFiler-item-title"><b title="{{fi-name}}">{{fi-name}}</b></span>\
<span class="jFiler-item-others">{{fi-size2}}</span>\
</div>\
</div>\
</div>\
{{fi-image}}\
</a>\
<div class="jFiler-item-assets jFiler-row">\
<ul class="list-inline pull-left">\
<li>{{fi-progressBar}}</li>\
</ul>\
<ul class="list-inline pull-right">\
<li><a class="icon-jfi-trash jFiler-item-trash-action"></a></li>\
</ul>\
</div>\
</div>\
</div>\
</li>',
itemAppend: '<li class="jFiler-item">\
<div class="jFiler-item-container">\
<div class="jFiler-item-inner">\
<a href="javascript:void(0);" class="jFiler-item-thumb">\
<div class="jFiler-item-status"></div>\
<div class="jFiler-item-thumb-overlay">\
<div class="jFiler-item-info">\
<div style="display:table-cell;vertical-align: middle;">\
<span class="jFiler-item-title"><b title="{{fi-name}}">{{fi-name}}</b></span>\
<span class="jFiler-item-others">{{fi-size2}}</span>\
</div>\
</div>\
</div>\
{{fi-image}}\
</a>\
<div class="jFiler-item-assets jFiler-row">\
<ul class="list-inline pull-left">\
<li><span class="jFiler-item-others">{{fi-icon}}</span></li>\
</ul>\
<ul class="list-inline pull-right">\
<li><a class="icon-jfi-trash jFiler-item-trash-action"></a>{{fi-remove}}</li>\
</ul>\
</div>\
</div>\
</div>\
</li>',
progressBar: '<div class="bar"></div>',
itemAppendToEnd: true,
canvasImage: true,
removeConfirmation: true,
_selectors: {
list: '.jFiler-items-list',
//item: '.jFiler-item',
progressBar: '.bar',
remove: '.jFiler-item-trash-action'
}
},
dragDrop: {
dragEnter: null,
dragLeave: null,
drop: null,
dragContainer: null
},
uploadFile: {
url: $target.data('upload-url'),
//data: null,
type: 'POST',
enctype: 'multipart/form-data',
synchron: true,
beforeSend: function() {},
success: function(data, itemEl, listEl, boxEl, newInputEl, inputEl, id){
var parent = itemEl.find(".jFiler-jProgressBar").parent();
itemEl.find(".jFiler-jProgressBar").fadeOut("slow", function(){
$("<div class=\"jFiler-item-others text-success\"><i class=\"icon-jfi-check-circle\"></i> Success</div>").hide().appendTo(parent).fadeIn("slow");
});
},
error: function(el){
var parent = el.find(".jFiler-jProgressBar").parent();
el.find(".jFiler-jProgressBar").fadeOut("slow", function(){
$("<div class=\"jFiler-item-others text-error\"><i class=\"icon-jfi-minus-circle\"></i> Error</div>").hide().appendTo(parent).fadeIn("slow");
});
},
statusCode: null,
onProgress: null,
onComplete: null
},
files: files,
addMore: false,
allowDuplicates: true,
clipBoardPaste: true,
excludeName: null,
beforeRender: null,
beforeShow: null,
beforeSelect: null,
onSelect: null,
afterShow: null,
onRemove: function(itemEl, file, id, listEl, boxEl, newInputEl, inputEl){
var filerKit = inputEl.prop("jFiler"),
file_name = filerKit.files_list[id].name;
console.log(itemEl);
$.get(itemEl.find('.jFiler-item-trash-action').attr('href'))
},
onEmpty: null,
options: null,
dialogs: {
alert: function(text) {
return alert(text);
},
confirm: function (text, callback) {
confirm(text) ? callback() : null;
}
},
captions: {
button: "Выберите файлы",
feedback: "Выберите файлы для загрузки",
feedback2: "выбранные файлы",
drop: "Перетяните файлы для загрузки",
removeConfirmation: "Вы уверены что хотите удалить этот файл?",
errors: {
filesLimit: "Only {{fi-limit}} files are allowed to be uploaded.",
filesType: "Only Images are allowed to be uploaded.",
filesSize: "{{fi-name}} is too large! Please upload file up to {{fi-maxSize}} MB.",
filesSizeAll: "Files you've choosed are too large! Please upload files up to {{fi-maxSize}} MB."
}
}
});
});
}
var $uploaders = $('.file_upload_container');
$uploaders.each(function (i, uploader) {
var $uploader = $(uploader),
fields = $uploader.data('fields').split('|'), // Массив названий полей для создания фото
languages = $uploader.data('languages').split('|'); // Массив языков, будет использоватся для генерации инпутов
var $uploader = $(uploader),
fields = $uploader.data('fields').split('|'), // Массив названий полей для создания фото
languages = $uploader.data('languages').split('|'); // Массив языков, будет использоватся для генерации инпутов
init_filer($uploader);
});
init_filer($uploader);
});

@ -7,7 +7,6 @@
{# selects #}
<link href="{% static 'js/select/select2.css' %}" rel="stylesheet"/>
<script src="{% static 'js/select/select2.js' %}"></script>
<script src="{% static 'custom_js/make_select.js' %}"></script>
<script>
$(document).ready(function(){
@ -287,4 +286,4 @@
{% endfor %}
{% endcomment %}
{% endblock %}
{% endblock %}

@ -5,6 +5,5 @@
{# selects #}
<link href="{% static 'js/select/select2.css' %}" rel="stylesheet"/>
<script src="{% static 'js/select/select2.js' %}"></script>
<script src="{% static 'custom_js/make_select.js' %}"></script>
{% endblock %}
{% endblock %}

@ -8,7 +8,6 @@
{# selects #}
<link href="{% static 'js/select/select2.css' %}" rel="stylesheet"/>
<script src="{% static 'js/select/select2.js' %}"></script>
<script src="{% static 'custom_js/make_select.js' %}"></script>
{# ajax #}
<script src="{% static 'custom_js/file_post_ajax.js' %}"></script>
<script src="{% static 'custom_js/select_tag.js' %}"></script>

@ -9,7 +9,6 @@
{# selects #}
<link href="{% static 'js/select/select2.css' %}" rel="stylesheet"/>
<script src="{% static 'js/select/select2.js' %}"></script>
<script src="{% static 'custom_js/make_select.js' %}"></script>
{# ajax #}
<script src="{% static 'custom_js/file_post_ajax.js' %}"></script>
<script src="{% static 'custom_js/select_tag.js' %}"></script>

@ -7,7 +7,6 @@
{# selects #}
<link href="{% static 'js/select/select2.css' %}" rel="stylesheet"/>
<script src="{% static 'js/select/select2.js' %}"></script>
<script src="{% static 'custom_js/make_select.js' %}"></script>
{# ajax #}
<script src="{% static 'custom_js/file_post_ajax.js' %}"></script>
<script src="{% static 'custom_js/select_tag.js' %}"></script>
@ -22,4 +21,4 @@
<input type="reset" class="btn" value="Отменить" data-dismiss="modal">
</div>
</form>
{% endblock %}
{% endblock %}

@ -8,7 +8,6 @@
{# selects #}
<link href="{% static 'js/select/select2.css' %}" rel="stylesheet"/>
<script src="{% static 'js/select/select2.js' %}"></script>
<script src="{% static 'custom_js/make_select.js' %}"></script>
{# ajax #}
<script src="{% static 'custom_js/file_post_ajax.js' %}"></script>

@ -14,7 +14,6 @@
{# selects #}
<link href="{% static 'js/select/select2.css' %}" rel="stylesheet"/>
<script src="{% static 'js/select/select2.js' %}"></script>
<script src="{% static 'custom_js/make_select.js' %}"></script>
{# ajax #}
<script src="{% static 'custom_js/file_post_ajax.js' %}"></script>

@ -574,7 +574,6 @@
</form>
{% include 'c_admin/includes/photo_form.html' with form=photo_form object=object %}
{% include 'c_admin/includes/file_form.html' with file_form=file_form object=object %}
{% include 'c_admin/includes/stat_form.html' with form=stat_form object=object %}
{% endblock %}

@ -9,7 +9,6 @@
{# selects #}
<link href="{% static 'js/select/select2.css' %}" rel="stylesheet"/>
<script src="{% static 'js/select/select2.js' %}"></script>
<script src="{% static 'custom_js/make_select.js' %}"></script>
{# datetimepicker #}
<link href="{% static 'js/datetimepicker/css/datetimepicker.css' %}" rel="stylesheet"/>
<script src="{% static 'js/datetimepicker/js/bootstrap-datetimepicker.js' %}"></script>

@ -10,7 +10,6 @@
{# selects #}
<link href="{% static 'js/select/select2.css' %}" rel="stylesheet"/>
<script src="{% static 'js/select/select2.js' %}"></script>
<script src="{% static 'custom_js/make_select.js' %}"></script>
{# ajax #}
<script src="{% static 'custom_js/file_post_ajax.js' %}"></script>

@ -492,54 +492,7 @@
</div>
<a href="#stat_modal" id="stat_add" role="btn btn-success" class="btn btn-success" data-toggle="modal"><i class="icon-plus-sign icon-white"></i> Добавить год</a>
</div>
{% else %}
{% endif %}
{% comment %}
{% if formset_statistic.errors %}
<div class="alert alert-error">
{% for form in formset_statistic.forms %}
{% for key, value in form.errors.items %}
<p>{{ value }}</p>
{% endfor %}
{% endfor %}
</div>
{% endif %}
{# formset of stat #}
{{ formset_statistic.management_form }}
<div id="halls" style="padding-left: 160px;{% if object %} {% else %}display: none;{% endif %}">
<table class="table table-hover" style=" width: 100%;">
<thead>
<tr>
<td>Год</td>
<td>Посетители</td>
<td>Участники</td>
<td>Площадь</td>
<td></td>
</tr>
</thead>
<tbody>
{% for form in formset_statistic.forms %}
<tr class="item" {% if object %}{% else %}style="display: NONE"{% endif %}>
<td>{{ form.year }}</td>
<td>{{ form.visitors }}</td>
<td>{{ form.members }}</td>
<td>{{ form.area }}</td>
<td><a class="delete btn btn-danger" href="#"><i class="icon-trash icon-white"></i> Удалить</a></td>
</tr>
{% endfor %}
</tbody>
</table>
</div>
<p style=" padding-left: 20px"><a id="add" class="btn btn-success" href="#"><i class="icon-plus-sign icon-white"></i> Добавить год</a></p>
</div>
{% endcomment %}
</div>
<div class="box span8" id="file">
<div class="box-header well">
@ -661,7 +614,6 @@
</div>
</div>
{% include 'c_admin/includes/photo_form.html' with form=photo_form object=object %}
{% include 'c_admin/includes/file_form.html' with file_form=file_form object=object %}
{% include 'c_admin/includes/stat_form.html' with form=stat_form object=object %}
{% endblock %}

@ -18,7 +18,6 @@
{# <script src="{% static 'js/datepicker/js/bootstrap-datepicker.js' %}"></script> #}
<script src="{% static 'custom_js/make_select.js' %}"></script>
<script src="{% static 'custom_js/formset_add.js' %}"></script>
{# ajax #}
<script src="{% static 'custom_js/file_post_ajax.js' %}"></script>

@ -5,7 +5,6 @@
{# selects #}
<link href="{% static 'js/select/select2.css' %}" rel="stylesheet"/>
<script src="{% static 'js/select/select2.js' %}"></script>
<script src="{% static 'custom_js/make_select.js' %}"></script>
{# datetimepicker #}
<link href="{% static 'js/datetimepicker/css/datetimepicker.css' %}" rel="stylesheet"/>
<script src="{% static 'js/datetimepicker/js/bootstrap-datetimepicker.js' %}"></script>
@ -117,4 +116,4 @@
{% endif %}
{% endblock %}
{% endblock %}

@ -5,7 +5,6 @@
{# selects #}
<link href="{% static 'js/select/select2.css' %}" rel="stylesheet"/>
<script src="{% static 'js/select/select2.js' %}"></script>
<script src="{% static 'custom_js/make_select.js' %}"></script>
{# datetimepicker #}
<link href="{% static 'js/datetimepicker/css/datetimepicker.css' %}" rel="stylesheet"/>
<script src="{% static 'js/datetimepicker/js/bootstrap-datetimepicker.js' %}"></script>
@ -99,4 +98,4 @@
{% endif %}
{% endblock %}
{% endblock %}

@ -6,77 +6,22 @@
<div class="box-content">
{% if object %}
<a class="btn btn-success" href="#photopopup" data-toggle="modal"><i class="icon-plus-sign icon-white"></i> Фото</a>
<a href="{{ object.photogallery.admin_url }}" role="button" class="btn btn-info" data-toggle="modal">Просмотреть галерею</a><br><br>
{% else %}
<p>Фото можна добавлять только после введения основных даных</p>
{% endif %}
<div class="file_upload_container"
data-upload-url="{{ object.upload_photo_url }}"
data-get-url="{{ object.upload_photo_url }}"
data-languages="ru|en"
data-fields="title|caption">
{% with photos=object.photogallery.photos.all %}
<div class="clearfix">
{% for photo in photos %}
<div class="photo" style="float: left;margin-right: 15px;">
<div class="hover">
<a href="{{ photo.get_delete_url }}" class="btn-small btn-danger delete-photo">удалить</a>
</div>
<div>
<a href="/admin/photogallery/photo/{{ photo.slug }}/">
<img src="{{ photo.get_admin_thumbnail_url }}" class="thumbnail" alt="{{ photo.title }}">
</a>
</div>
</div>
{% endfor %}
<input type="file" name="image" class="file_uploader">
</div>
{% endwith %}
{# <form method="post" class="form-horizontal" id="photo_form" enctype="multipart/form-data" action="{{ object.upload_photo_url }}">#}
{# {% csrf_token %}#}
{# <div class="control-group{% if form.image.errors %}error{% endif %}">#}
{# <label class="control-label">{{ form.image.label }}:</label>#}
{# <div class="controls">#}
{# {{ form.image }}#}
{# <span class="help-inline">{{ form.image.errors }}</span>#}
{# </div>#}
{# </div>#}
{# <div class="control-group{% if form.sort.errors %}error{% endif %}">#}
{# <label class="control-label">{{ form.sort.label }}:</label>#}
{# <div class="controls">{{ form.sort }}#}
{# <span class="help-inline">{{ form.sort.errors }}</span>#}
{# </div>#}
{# </div>#}
{# {% with field='caption' form=form languages=languages %}#}
{# {% include 'c_admin/forms/multilang.html' %}#}
{# {% endwith %}#}
{##}
{# {% with field='title' form=form languages=languages %}#}
{# {% include 'c_admin/forms/multilang.html' %}#}
{# {% endwith %}#}
{##}
{# <div class="controls">#}
{# <input class="btn btn-primary" type="submit" value="Добавить">#}
{# </div>#}
{# </form>#}
<link rel="stylesheet" href="{% static 'jQuery-filer/css/jquery.filer.css' %}">
<link rel="stylesheet" href="{% static 'jQuery-filer/css/jquery.filer-dragdropbox-theme.css' %}">
<div class="file_upload_container"
data-upload-url="{{ object.upload_photo_url }}"
data-get-url="{{ object.upload_photo_url }}"
data-languages="ru|en"
data-fields="title|caption">
<input type="file" name="image" class="file_uploader">
<a href="#" class="btn btn-success upload_loaded_files">Загрузить файлы</a>
</div>
<link rel="stylesheet" href="{% static 'jQuery-filer/css/jquery.filer.css' %}">
<link rel="stylesheet" href="{% static 'jQuery-filer/css/jquery.filer-dragdropbox-theme.css' %}">
<script src="{% static 'jQuery-filer/js/jquery.filer.js' %}"></script>
<script src="{% static 'jQuery-filer/js/init.js' %}"></script>
<script src="{% static 'jQuery-filer/js/jquery.filer.js' %}"></script>
<script src="{% static 'jQuery-filer/js/init.js' %}"></script>
{% else %}
<p>Изображения можно добавлять только после введения основных данных</p>
{% endif %}
</div>
</div>
</div>

@ -8,7 +8,6 @@
{# selects #}
<link href="{% static 'js/select/select2.css' %}" rel="stylesheet"/>
<script src="{% static 'js/select/select2.js' %}"></script>
<script src="{% static 'custom_js/make_select.js' %}"></script>
{# ajax #}
<script src="{% static 'custom_js/file_post_ajax.js' %}"></script>
<script src="{% static 'custom_js/select_tag.js' %}"></script>

@ -8,7 +8,6 @@
{# selects #}
<link href="{% static 'js/select/select2.css' %}" rel="stylesheet"/>
<script src="{% static 'js/select/select2.js' %}"></script>
<script src="{% static 'custom_js/make_select.js' %}"></script>
{# ajax #}
<script src="{% static 'custom_js/file_post_ajax.js' %}"></script>
<script src="{% static 'custom_js/select_tag.js' %}"></script>

@ -8,7 +8,6 @@
{# selects #}
<link href="{% static 'js/select/select2.css' %}" rel="stylesheet"/>
<script src="{% static 'js/select/select2.js' %}"></script>
<script src="{% static 'custom_js/make_select.js' %}"></script>
{# datetimepicker #}
<link href="{% static 'js/datetimepicker/css/datetimepicker.css' %}" rel="stylesheet"/>
<script src="{% static 'js/datetimepicker/js/bootstrap-datetimepicker.js' %}"></script>

@ -14,7 +14,6 @@
{# selects #}
<link href="{% static 'js/select/select2.css' %}" rel="stylesheet"/>
<script src="{% static 'js/select/select2.js' %}"></script>
<script src="{% static 'custom_js/make_select.js' %}"></script>
{# ajax #}
<script src="{% static 'custom_js/file_post_ajax.js' %}"></script>
<script src="{% static 'custom_js/place_city_ajax.js' %}"></script>

@ -8,7 +8,6 @@
{# selects #}
<link href="{% static 'js/select/select2.css' %}" rel="stylesheet"/>
<script src="{% static 'js/select/select2.js' %}"></script>
<script src="{% static 'custom_js/make_select.js' %}"></script>
{# ajax #}
<script src="{% static 'custom_js/file_post_ajax.js' %}"></script>
<script src="{% static 'custom_js/select_tag.js' %}"></script>

@ -8,7 +8,6 @@
{# selects #}
<link href="{% static 'js/select/select2.css' %}" rel="stylesheet"/>
<script src="{% static 'js/select/select2.js' %}"></script>
<script src="{% static 'custom_js/make_select.js' %}"></script>
{# ajax #}
<script src="{% static 'custom_js/file_post_ajax.js' %}"></script>
<script src="{% static 'custom_js/select_tag.js' %}"></script>

@ -9,7 +9,6 @@
{# selects #}
<link href="{% static 'js/select/select2.css' %}" rel="stylesheet"/>
<script src="{% static 'js/select/select2.js' %}"></script>
<script src="{% static 'custom_js/make_select.js' %}"></script>
{# ajax #}
<script src="{% static 'custom_js/file_post_ajax.js' %}"></script>
<script src="{% static 'custom_js/select_tag.js' %}"></script>

@ -7,7 +7,6 @@
{# selects #}
<link href="{% static 'js/select/select2.css' %}" rel="stylesheet"/>
<script src="{% static 'js/select/select2.js' %}"></script>
<script src="{% static 'custom_js/make_select.js' %}"></script>
<script src="{% static 'custom_js/file_post_ajax.js' %}"></script>
{% endblock %}

@ -22,7 +22,6 @@
{# selects #}
<link href="{% static 'js/select/select2.css' %}" rel="stylesheet"/>
<script src="{% static 'js/select/select2.js' %}"></script>
<script src="{% static 'custom_js/make_select.js' %}"></script>
<script src="{% static 'custom_js/formset_add.js' %}"></script>
{# ajax #}

@ -2,25 +2,21 @@
{% load static %}
{% block scripts %}
<script src="{% static 'ckeditor/ckeditor/ckeditor.js' %}"></script>
{# google map не забыть скачать скрипты на локал #}
<link href='http://ajax.googleapis.com/ajax/libs/jqueryui/1.8.18/themes/redmond/jquery-ui.css' rel="stylesheet"/>
<script src='http://ajax.googleapis.com/ajax/libs/jquery/1.7.1/jquery.min.js'></script>
<script src='http://ajax.googleapis.com/ajax/libs/jqueryui/1.8.18/jquery-ui.min.js'></script>
<script src='http://maps.google.com/maps/api/js?sensor=false'></script>
{# selects #}
<link href="{% static 'js/select/select2.css' %}" rel="stylesheet"/>
<script src="{% static 'js/select/select2.js' %}"></script>
<script src="{% static 'custom_js/make_select.js' %}"></script>
<script src="{% static 'custom_js/formset_add.js' %}"></script>
{# ajax #}
<script src="{% static 'custom_js/file_post_ajax.js' %}"></script>
<script src="{% static 'custom_js/place_city_ajax.js' %}"></script>
{% endblock %}
{% block select2 %}
<link href="{% static 'js/select/select2.css' %}" rel="stylesheet"/>
<script src="{% static 'js/select/select2.js' %}"></script>
<script src="{% static 'custom_js/formset_add.js' %}"></script>
{% endblock %}
{% block body %}
@ -389,54 +385,54 @@
</form>
{# modal window #}
<div class="modal hide fade" id="myModal" >
<div class="modal-header">
<button type="button" class="close" data-dismiss="modal" aria-hidden="true" id="close">&times;</button>
<h3>Добавить файл</h3>
</div>
<div id="form_body">
<div class="modal-body">
<form method="post" class="form-horizontal" enctype="multipart/form-data" name="file_form" id="file_form" > {% csrf_token %}
{#<div class="modal hide fade" id="myModal" >#}
{# <div class="modal-header">#}
{# <button type="button" class="close" data-dismiss="modal" aria-hidden="true" id="close">&times;</button>#}
{# <h3>Добавить файл</h3>#}
{# </div>#}
{##}
{# <div id="form_body">#}
{# <div class="modal-body">#}
{# <form method="post" class="form-horizontal" enctype="multipart/form-data" name="file_form" id="file_form" > {% csrf_token %}#}
{##}
{# hidden inputs uses for comparing with Country form key#}
{{ file_form.key }}
{{ file_form.model }}
<input type="hidden" id="obj_id" value="{{ obj_id }}">
{# {{ file_form.key }}#}
{# {{ file_form.model }}#}
{# <input type="hidden" id="obj_id" value="{{ obj_id }}">#}
{# file_path #}
<div class="control-group{% if file_form.file_path.errors %}error{% endif %}">
<label class="control-label">{{ file_form.file_path.label }}:</label>
<div class="controls">{{ file_form.file_path }}
<span class="help-inline">{{ file_form.file_path.errors }}</span>
</div>
</div>
{# <div class="control-group{% if file_form.file_path.errors %}error{% endif %}">#}
{# <label class="control-label">{{ file_form.file_path.label }}:</label>#}
{# <div class="controls">{{ file_form.file_path }}#}
{# <span class="help-inline">{{ file_form.file_path.errors }}</span>#}
{# </div>#}
{# </div>#}
{# file purpose #}
<div class="control-group{% if file_form.purpose.errors %}error{% endif %}">
<label class="control-label">{{ file_form.purpose.label }}:</label>
<div class="controls">{{ file_form.purpose }}
<span class="help-inline">{{ file_form.purpose.errors }}</span>
</div>
</div>
{# <div class="control-group{% if file_form.purpose.errors %}error{% endif %}">#}
{# <label class="control-label">{{ file_form.purpose.label }}:</label>#}
{# <div class="controls">{{ file_form.purpose }}#}
{# <span class="help-inline">{{ file_form.purpose.errors }}</span>#}
{# </div>#}
{# </div>#}
{# file_name #}
{% with field='file_name' form=file_form languages=languages %}
{% include 'c_admin/forms/multilang.html' %}
{% endwith %}
{# {% with field='file_name' form=file_form languages=languages %}#}
{# {% include 'c_admin/forms/multilang.html' %}#}
{# {% endwith %}#}
{# file_description #}
{% with field='description' form=file_form languages=languages %}
{% include 'c_admin/forms/multilang.html' %}
{% endwith %}
</div>
<div class="modal-footer">
<div class="controls">
<input class="btn btn-primary" type="submit" value="Добавить">
<input type="reset" class="btn" value="Отменить" data-dismiss="modal">
</form>
</div>
</div>
</div>
</div>
{# {% with field='description' form=file_form languages=languages %}#}
{# {% include 'c_admin/forms/multilang.html' %}#}
{# {% endwith %}#}
{##}
{# </div>#}
{##}
{# <div class="modal-footer">#}
{# <div class="controls">#}
{# <input class="btn btn-primary" type="submit" value="Добавить">#}
{# <input type="reset" class="btn" value="Отменить" data-dismiss="modal">#}
{# </form>#}
{# </div>#}
{# </div>#}
{# </div>#}
{##}
{#</div>#}
{% endblock %}

@ -12,7 +12,6 @@
{# selects #}
<link href="{% static 'js/select/select2.css' %}" rel="stylesheet"/>
<script src="{% static 'js/select/select2.js' %}"></script>
<script src="{% static 'custom_js/make_select.js' %}"></script>
<script src="{% static 'custom_js/formset_add.js' %}"></script>
{# ajax #}

@ -22,7 +22,6 @@
{# selects #}
<link href="{% static 'js/select/select2.css' %}" rel="stylesheet"/>
<script src="{% static 'js/select/select2.js' %}"></script>
<script src="{% static 'custom_js/make_select.js' %}"></script>
<script src="{% static 'custom_js/formset_add.js' %}"></script>
{# ajax #}

@ -12,7 +12,6 @@
{# selects #}
<link href="{% static 'js/select/select2.css' %}" rel="stylesheet"/>
<script src="{% static 'js/select/select2.js' %}"></script>
<script src="{% static 'custom_js/make_select.js' %}"></script>
<script src="{% static 'custom_js/formset_add.js' %}"></script>
{# ajax #}
<script src="{% static 'custom_js/file_post_ajax.js' %}"></script>

@ -14,7 +14,6 @@
{# selects #}
<link href="{% static 'js/select/select2.css' %}" rel="stylesheet"/>
<script src="{% static 'js/select/select2.js' %}"></script>
<script src="{% static 'custom_js/make_select.js' %}"></script>
{# datetimepicker #}
<link href="{% static 'js/datetimepicker/css/datetimepicker.css' %}" rel="stylesheet"/>
<script src="{% static 'js/datetimepicker/js/bootstrap-datetimepicker.js' %}"></script>

@ -8,7 +8,6 @@
{# selects #}
<link href="{% static 'js/select/select2.css' %}" rel="stylesheet"/>
<script src="{% static 'js/select/select2.js' %}"></script>
<script src="{% static 'custom_js/make_select.js' %}"></script>
<script src="{% static 'custom_js/service.js' %}"></script>
<style>
li{

@ -11,7 +11,6 @@
<script src="{% static 'js/jquery-ui-1.12.0-rc.2/jquery-ui.min.js' %}"></script>
<script src="{% static 'js/select/select2.sortable.js' %}"></script>
<script src="{% static 'custom_js/make_select.js' %}"></script>
<script>
$(function() {
$('#id_exposition_themes, #id_conference_themes').select2('destroy');

@ -7,7 +7,6 @@
{# selects #}
<link href="{% static 'js/select/select2.css' %}" rel="stylesheet"/>
<script src="{% static 'js/select/select2.js' %}"></script>
<script src="{% static 'custom_js/make_select.js' %}"></script>

@ -7,7 +7,6 @@
{# selects #}
<link href="{% static 'js/select/select2.css' %}" rel="stylesheet"/>
<script src="{% static 'js/select/select2.js' %}"></script>
<script src="{% static 'custom_js/make_select.js' %}"></script>

@ -9,7 +9,6 @@
{# selects #}
<link href="{% static 'js/select/select2.css' %}" rel="stylesheet"/>
<script src="{% static 'js/select/select2.js' %}"></script>
<script src="{% static 'custom_js/make_select.js' %}"></script>
{# ajax #}
<script src="{% static 'custom_js/file_post_ajax.js' %}"></script>
{# datetimepicker #}

@ -9,7 +9,6 @@
{# selects #}
<link href="{% static 'js/select/select2.css' %}" rel="stylesheet"/>
<script src="{% static 'js/select/select2.js' %}"></script>
<script src="{% static 'custom_js/make_select.js' %}"></script>
{# ajax #}
<script src="{% static 'custom_js/file_post_ajax.js' %}"></script>
{# datetimepicker #}

@ -12,7 +12,6 @@
<script src="{% static 'custom_js/formset_add.js' %}"></script>
{# ajax #}
<script src="{% static 'custom_js/file_post_ajax.js' %}"></script>
<script src="{% static 'custom_js/make_select.js' %}"></script>
<script src="{% static 'custom_js/select_tag.js' %}"></script>
{# datetimepicker #}

Loading…
Cancel
Save