You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 
 
 
 
 

618 lines
29 KiB

# -*- coding: utf-8 -*-
from django import forms
from django.conf import settings
from ckeditor.widgets import CKEditorWidget
from django.forms.util import ErrorList
from django.core.validators import validate_email, URLValidator
from django.utils.translation import ugettext as _
#models
from events.models import TargetAudience
from models import Exposition, TimeTable, TmpTimeTable, CURRENCY, Statistic
from theme.models import Tag
from country.models import Country
from theme.models import Theme
from organiser.models import Organiser
from city.models import City
from place_exposition.models import PlaceExposition
#functions
from functions.translate import fill_with_signal
from functions.form_check import is_positive_integer
from functions.form_check import translit_with_separator
from settings.settings import date_formats
from functions.admin_forms import AdminFilterForm, EventsAdminFilterFormMixin
places = [(item.id, item.name) for item in PlaceExposition.objects.language().all()]
places.insert(0,('', 'Не выбрано'))
class ExpositionCreateForm(forms.Form):
"""
Create Exposition form for creating exposition
__init__ uses for dynamic creates fields
save function saves data in Exposition object. If it doesnt exist create new object
"""
PERIODIC = ((0, _(u'Не выбрано')), (1.0, _(u'Ежегодно')), (2.0, _(u'2 раза в год')), (3.0, _(u'3 раза в год')),
(4.0, _(u'4 раза в год')), (5.0, _(u'5 раз в год')), (0.5, _(u'Раз в 2 года')),(0.33, _(u'Раз в 3 года')),
(0.25, _(u'Раз в 4 года')), (0.2, _(u'Раз в 5 лет')))
public = [(i, i) for i in TargetAudience.objects.all().values_list('title', flat=True)]
currencies = [(item, item) for item in CURRENCY]
data_begin = forms.DateField(label=_(u'Дата начала'), input_formats=['%Y-%m-%d', '%d.%m.%Y'])
data_end = forms.DateField(label=_(u'Дата окончания'), input_formats=['%Y-%m-%d', '%d.%m.%Y'])
logo = forms.ImageField(label=_('Logo'), required=False)
#organiser = forms.MultipleChoiceField(label=u'Организаторы', required=False,
# choices=[(item.id, item.name) for item in Organiser.objects.language().all()])
org = forms.CharField(required=False, label=_(u'Организатор'))
#company = forms.MultipleChoiceField(label=u'Компании', required=False,
# choices=[(item.id, item.name) for item in Company.objects.language().all()] )
country = forms.ChoiceField(label=_(u'Страна'), choices=[(c.id, c.name) for c in Country.objects.language().all()])
theme = forms.MultipleChoiceField(
label=_(u'Тематики'),
choices=[(item.id, item.name) for item in Theme.objects.language().filter(types=Theme.types.exposition)])
place = forms.ChoiceField(label=_(u'Место проведения'), required=False,
choices=places)
place_alt = forms.CharField(required=False, label=_(u'Альтернативное место'))
#creates select input with empty choices cause it will be filled with ajax
city = forms.CharField(label=_(u'Город'), widget=forms.HiddenInput())
tag = forms.CharField(label=_(u'Теги'), widget=forms.HiddenInput(), required=False)
periodic = forms.ChoiceField(label=_(u'Периодичность'), choices=PERIODIC, required=False)
audience = forms.MultipleChoiceField(label=_(u'Аудитория'), choices=public, initial='', required=False)
web_page = forms.CharField(label=_(u'Веб страница'), required=False)
registration_link = forms.CharField(label=_(u'Ссылка на регистрацию'), required=False)
foundation_year = forms.CharField(label=_(u'Год основания'), required=False)
members = forms.CharField(label=_(u'Участники'), required=False)
visitors = forms.CharField(label=_(u'Посетители'), required=False)
min_area = forms.CharField(label=_(u'Минимальная площадь'), required=False)
discount = forms.CharField(label=_(u'Cкидка(%)'), required=False)
area = forms.CharField(label=_(u'Площадь'), required=False)
quality_label = forms.MultipleChoiceField(label=_(u'Метки'), required=False,
choices=[('ufi', 'UFI'), ('rsva', 'РСВЯ'), ('exporating', 'ExpoRating')],
widget=forms.CheckboxSelectMultiple())
#
currency = forms.ChoiceField(label=_(u'Валюта'), choices=currencies, required=False)
application_deadline = forms.DateField(label=_(u'Срок подачи стенда'),input_formats=['%Y-%m-%d', '%d.%m.%Y'], required=False)
min_stand_size = forms.CharField(label=_(u'Минимальный размер стенда'), required=False)
price_catalog = forms.CharField(label=_(u'Цена за каталог'), required=False)
tax = forms.BooleanField(label=_(u'Налог включен'), initial=True, required=False)
min_closed_area = forms.CharField(label=_(u'Минимальная цена закрытой НЕ оборудованной площади'), required=False)
max_closed_area = forms.CharField(label=_(u'Максимальная цена закрытой НЕ оборудованной площади'), required=False)
min_closed_equipped_area = forms.CharField(label=_(u'Минимальная цена закрытой оборудованной площади'), required=False)
max_closed_equipped_area = forms.CharField(label=_(u'Максимальная цена закрытой оборудованной площади'), required=False)
min_open_area = forms.CharField(label=_(u'Минимальная цена открытой площади'), required=False)
max_open_area = forms.CharField(label=_(u'Максимальная цена открытой площади'), required=False)
registration_payment = forms.CharField(label=_(u'Регистрационны взнос'), required=False)
expohit = forms.BooleanField(label=_(u'Expohit'), required=False)
canceled = forms.BooleanField(label=_(u'Отменена'), required=False)
moved = forms.BooleanField(label=_(u'Перенесена'), required=False)
#field for comparing tmp files
key = forms.CharField(required=False, widget=forms.HiddenInput())
#
exposition_id = forms.CharField(required=False, widget=forms.HiddenInput())
def __init__(self, *args, **kwargs):
"""
create dynamical translated fields fields
"""
super(ExpositionCreateForm, self).__init__(*args, **kwargs)
#creates translated forms example: name_ru, name_en
# len(10) is a hack for detect if settings.LANGUAGES is not configured it return all langs
if len(settings.LANGUAGES) in range(10):
for lid, (code, name) in enumerate(settings.LANGUAGES):
# uses enumerate for detect iteration number
# first iteration is a default lang so it required fields
required = True if lid == 0 else False
self.fields['name_%s' % code] = forms.CharField(label=_(u'Название'), required=required,
widget=forms.TextInput(attrs={'style':'width: 550px'}))
self.fields['main_title_%s' % code] = forms.CharField(label=_(u'Краткое описание'),
required=False, widget=CKEditorWidget)
self.fields['description_%s' % code] = forms.CharField(label=_(u'Описание'),
required=False, widget=CKEditorWidget)
self.fields['time_%s' % code] = forms.CharField(label=_(u'Время работы'),
required=False, widget=CKEditorWidget)
self.fields['price_day_%s' % code] = forms.CharField(label=_(u'Стоимость билета 1 день'), required=False,
widget=forms.TextInput(attrs={'style':'width: 550px'}))
self.fields['price_all_%s' % code] = forms.CharField(label=_(u'Стоимость билета все дни'), required=False,
widget=forms.TextInput(attrs={'style':'width: 550px'}))
self.fields['price_day_bar_%s' % code] = forms.CharField(label=_(u'Стоимость на стойке 1 день'), required=False,
widget=forms.TextInput(attrs={'style':'width: 550px'}))
self.fields['price_all_bar_%s' % code] = forms.CharField(label=_(u'Стоимость на стойке все дни'), required=False,
widget=forms.TextInput(attrs={'style':'width: 550px'}))
self.fields['products_%s' % code] = forms.CharField(label=_(u'Экспонируемые продукты'),
required=False, widget=CKEditorWidget)
self.fields['discount_description_%s' % code] = forms.CharField(label=_(u'Описание скидки'),
required=False, widget=CKEditorWidget)
self.fields['stat_countries_%s' % code] = forms.CharField(label=_(u'Участвующие страны'),
required=False, widget=CKEditorWidget)
self.fields['pre_condition_%s' % code] = forms.CharField(label=_(u'Условия предварительной регистрации'),required=False,
widget=forms.TextInput(attrs={'style':'width: 550px'}))
self.fields['stand_condition_%s' % code] = forms.CharField(label=_(u'Условия регистрации на стойке'),required=False,
widget=forms.TextInput(attrs={'style':'width: 550px'}))
self.fields['visit_note_%s' % code] = forms.CharField(label=_(u'Примечание по посещению'),required=False,
widget=forms.TextInput(attrs={'style':'width: 550px'}))
self.fields['participation_note_%s' % code] = forms.CharField(label=_(u'Примечание по участии'),required=False,
widget=forms.TextInput(attrs={'style':'width: 550px'}))
#meta data
self.fields['title_%s' % code] = forms.CharField(label=_(u'Meta title'), required=False, max_length=255,
widget=forms.TextInput(attrs={'style':'width: 550px'}))
self.fields['keywords_%s' % code] = forms.CharField(label=_(u'Meta keywords'), required=False, max_length=255,
widget=forms.TextInput(attrs={'style':'width: 550px'}))
self.fields['descriptions_%s' % code] = forms.CharField(label=_(u'Meta description'), required=False, max_length=255,
widget=forms.TextInput(attrs={'style':'width: 550px'}))
def save(self, obj=None):
"""
change Exposition model object with id = id
N/A add new Exposition model object
usage: form.save(obj) - if change exposition
form.save() - if add exposition
"""
data = self.cleaned_data
if not obj:
exposition = Exposition()
else:
exposition = obj
exposition.theme.clear()
exposition.organiser.clear()
if data.get('tag'):
exposition.tag.clear()
#simple fields
if not getattr(exposition, 'url'):
exposition.url = translit_with_separator(data['name_ru'].strip()).lower()
if data.get('logo'):
exposition.logo = data['logo']
exposition.org = data['org']
exposition.data_begin = data['data_begin']
exposition.data_end = data['data_end']
exposition.periodic = data['periodic']
exposition.web_page= data['web_page']
exposition.registration_link = data['registration_link']
exposition.foundation_year = data['foundation_year']
exposition.members = data['members']
exposition.visitors = data['visitors']
exposition.area = data['area']
exposition.min_area = data['min_area']
exposition.currency = data['currency']
exposition.application_deadline = data['application_deadline']
exposition.min_stand_size = data['min_stand_size']
exposition.price_catalog = data['price_catalog']
exposition.tax = data['tax']
exposition.min_closed_area = data['min_closed_area']
exposition.max_closed_area = data['max_closed_area']
exposition.min_closed_equipped_area = data['min_closed_equipped_area']
exposition.max_closed_equipped_area = data['max_closed_equipped_area']
exposition.min_open_area = data['min_open_area']
exposition.max_open_area = data['max_open_area']
exposition.registration_payment = data['registration_payment']
exposition.discount = data['discount']
exposition.expohit = data['expohit']
exposition.canceled = data['canceled']
exposition.moved = data['moved']
# generates bitfield
quality = 0
if data['quality_label']:
quality = reduce(lambda x,y: x|y, (getattr(Exposition.quality_label, item) for item in data['quality_label']))
exposition.quality_label = quality
exposition.country = Country.objects.get(id=data['country'])
exposition.city = City.objects.get(id=data['city'])
if data.get('place'):
exposition.place = PlaceExposition.objects.get(id=data['place'])
else:
exposition.place = None
exposition.place_alt = data['place_alt']
# fill translated fields and save object
fill_with_signal(Exposition, exposition, data)
#fill manytomany fields
exposition.theme.add(*data['theme'])
exposition.tag.add(*Tag.objects.filter(id__in=data['tag']))
exposition.organiser.add(*Organiser.objects.filter(id__in=data.get('organiser', [])))
exposition.audience.add(*data['audience'])
#exposition.company.add(*Company.objects.filter(id__in=data.get('company', [])))
exposition.save()
return exposition
def clean(self):
id = self.cleaned_data.get('exposition_id')
name_ru = self.cleaned_data.get('name_ru')
exposition = Exposition.objects.filter(url=translit_with_separator(name_ru))
if exposition and str(exposition[0].id) != id:
msg = _(u'Выставка с таким названием уже существует')
self._errors['name_ru'] = ErrorList([msg])
del self.cleaned_data['name_ru']
return self.cleaned_data
def clean_tag(self):
tags = self.cleaned_data.get('tag')
if tags:
res = []
for id in tags.split(','):
try:
res.append(int(id))
except:
continue
return res
else:
return []
def clean_web_page(self):
"""
checking web_page
"""
cleaned_data = super(ExpositionCreateForm, self).clean()
web_page = cleaned_data.get('web_page')
if not web_page:
return ''
validate = URLValidator()
try:
validate(web_page)
except(forms.ValidationError),e:
raise forms.ValidationError(e.messages[0])
return web_page
def clean_registration_link(self):
"""
checking web_page
"""
cleaned_data = super(ExpositionCreateForm, self).clean()
registration_link = cleaned_data.get('registration_link')
if not registration_link:
return ''
validate = URLValidator()
try:
validate(registration_link)
except(forms.ValidationError),e:
raise forms.ValidationError(e.messages[0])
return registration_link
def clean_area(self):
"""
checking foundation_year
"""
cleaned_data = super(ExpositionCreateForm, self).clean()
area = cleaned_data.get('area').strip()
return is_positive_integer(area)
def clean_foundation_year(self):
"""
checking foundation_year
"""
cleaned_data = super(ExpositionCreateForm, self).clean()
foundation_year = cleaned_data.get('foundation_year').strip()
return is_positive_integer(foundation_year)
def clean_price_day(self):
"""
checking price_day
"""
cleaned_data = super(ExpositionCreateForm, self).clean()
price_day = cleaned_data.get('price_day').strip()
return is_positive_integer(price_day)
def clean_price_all(self):
"""
checking price_all
"""
cleaned_data = super(ExpositionCreateForm, self).clean()
price_all = cleaned_data.get('price_all').strip()
return is_positive_integer(price_all)
def clean_price_day_bar(self):
"""
checking price_day_bar
"""
cleaned_data = super(ExpositionCreateForm, self).clean()
price_day_bar = cleaned_data.get('price_day_bar').strip()
return is_positive_integer(price_day_bar)
def clean_price_all_bar(self):
"""
checking price_all_bar
"""
cleaned_data = super(ExpositionCreateForm, self).clean()
price_all_bar = cleaned_data.get('price_all_bar').strip()
return is_positive_integer(price_all_bar)
def clean_min_stand_size(self):
"""
checking min_stand_size
"""
cleaned_data = super(ExpositionCreateForm, self).clean()
min_stand_size = cleaned_data.get('min_stand_size').strip()
return is_positive_integer(min_stand_size)
def clean_price_catalog(self):
"""
checking price_catalog
"""
cleaned_data = super(ExpositionCreateForm, self).clean()
price_catalog = cleaned_data.get('price_catalog').strip()
return is_positive_integer(price_catalog)
def clean_visitors(self):
"""
checking visitors
"""
cleaned_data = super(ExpositionCreateForm, self).clean()
visitors = cleaned_data.get('visitors').strip()
return is_positive_integer(visitors)
def clean_members(self):
"""
checking members
"""
cleaned_data = super(ExpositionCreateForm, self).clean()
members = cleaned_data.get('members').strip()
return is_positive_integer(members)
def clean_min_area(self):
"""
checking min_area
"""
cleaned_data = super(ExpositionCreateForm, self).clean()
min_area = cleaned_data.get('min_area').strip()
return is_positive_integer(min_area)
def clean_min_closed_area(self):
"""
checking min_closed_area
"""
cleaned_data = super(ExpositionCreateForm, self).clean()
min_closed_area = cleaned_data.get('min_closed_area').strip()
return is_positive_integer(min_closed_area)
#
def clean_max_closed_area(self):
"""
checking max_closed_area
"""
cleaned_data = super(ExpositionCreateForm, self).clean()
max_closed_area = cleaned_data.get('max_closed_area').strip()
return is_positive_integer(max_closed_area)
def clean_min_closed_equipped_area(self):
"""
checking min_closed_equipped_area
"""
cleaned_data = super(ExpositionCreateForm, self).clean()
min_closed_equipped_area = cleaned_data.get('min_closed_equipped_area').strip()
return is_positive_integer(min_closed_equipped_area)
def clean_max_closed_equipped_area(self):
"""
checking max_closed_equipped_area
"""
cleaned_data = super(ExpositionCreateForm, self).clean()
max_closed_equipped_area = cleaned_data.get('max_closed_equipped_area').strip()
return is_positive_integer(max_closed_equipped_area)
def clean_min_open_area(self):
"""
checking min_open_area
"""
cleaned_data = super(ExpositionCreateForm, self).clean()
min_open_area = cleaned_data.get('min_open_area').strip()
return is_positive_integer(min_open_area)
def clean_max_open_area(self):
"""
checking max_open_area
"""
cleaned_data = super(ExpositionCreateForm, self).clean()
max_open_area = cleaned_data.get('max_open_area').strip()
return is_positive_integer(max_open_area)
def clean_registration_payment(self):
"""
checking registration_payment
"""
cleaned_data = super(ExpositionCreateForm, self).clean()
registration_payment = cleaned_data.get('registration_payment').strip()
return is_positive_integer(registration_payment)
def clean_discount(self):
"""
checking discount
"""
cleaned_data = super(ExpositionCreateForm, self).clean()
discount = cleaned_data.get('discount').strip()
return is_positive_integer(discount)
class ExpositionDeleteForm(forms.ModelForm):
url = forms.CharField(widget=forms.HiddenInput())
class Meta:
model = Exposition
fields = ('url',)
class StatisticForm(forms.Form):
year = forms.CharField(widget=forms.TextInput(attrs={'style': 'width:70px'}), label=_(u'Год'))
visitors = forms.CharField(widget=forms.TextInput(attrs={'style': 'width:70px'}), required=False, label=_(u'Посетители'))
members = forms.CharField(widget=forms.TextInput(attrs={'style': 'width:70px'}), required=False, label=_(u'Участники'))
area = forms.CharField(widget=forms.TextInput(attrs={'style': 'width:70px'}), required=False, label=_(u'Площадь'))
countries_number = forms.CharField(widget=forms.TextInput(attrs={'style': 'width:70px'}), required=False, label=_(u'Число стран'))
def __init__(self, *args, **kwargs):
"""
create dynamical translated fields fields
"""
super(StatisticForm, self).__init__(*args, **kwargs)
#creates translated forms example: name_ru, name_en
# len(10) is a hack for detect if settings.LANGUAGES is not configured it return all langs
if len(settings.LANGUAGES) in range(10):
for lid, (code, name) in enumerate(settings.LANGUAGES):
# uses enumerate for detect iteration number
# first iteration is a default lang so it required fields
required = True if lid == 0 else False
self.fields['countries_%s' % code] = forms.CharField(label=_(u'Участвующие страны'),
required=False,
widget=forms.TextInput(attrs={'style':'width: 250px'}))
def save(self, exposition=None):
data = self.cleaned_data
if not exposition:
return None
else:
stat = Statistic()
# simple fields
stat.exposition = exposition
stat.year = data['year']
stat.visitors = data.get('visitors')
stat.members = data.get('members')
stat.area = data.get('area')
stat.countries_number = data.get('countries_number')
fill_with_signal(Statistic, stat, data)
return stat
def clean_year(self):
cleaned_data = super(StatisticForm, self).clean()
year = cleaned_data.get('year').strip()
return is_positive_integer(year)
def clean_members(self):
cleaned_data = super(StatisticForm, self).clean()
members = cleaned_data.get('members').strip()
return is_positive_integer(members)
def clean_visitors(self):
cleaned_data = super(StatisticForm, self).clean()
visitors = cleaned_data.get('visitors').strip()
return is_positive_integer(visitors)
def clean_countries_number(self):
cleaned_data = super(StatisticForm, self).clean()
countries_number = cleaned_data.get('countries_number').strip()
return is_positive_integer(countries_number)
from functions.files import check_tmp_timetables
class TimeTableForm(forms.Form):
begin = forms.DateTimeField(label=_(u'Время начала'), input_formats=date_formats,
widget=forms.TextInput(attrs={'style':'width: 150px'}))
end = forms.DateTimeField(label=_(u'Время окончания'), input_formats=date_formats,
widget=forms.TextInput(attrs={'style':'width: 150px'}))
timetable_organiser = forms.ChoiceField(label=_(u'Организатор'), required=False,
choices=[(item.id, item.name) for item in Organiser.objects.language().all()])
def __init__(self, *args, **kwargs):
"""
create dynamical translated fields fields
and fills select fields
"""
super(TimeTableForm, self).__init__(*args, **kwargs)
#creates translated forms example: name_ru, name_en
# len(10) is a hack for detect if settings.LANGUAGES is not configured it return all langs
if len(settings.LANGUAGES) in range(10):
for lid, (code, name) in enumerate(settings.LANGUAGES):
# uses enumerate for detect iteration number
# first iteration is a default lang so it required fields
required = True if lid == 0 else False
self.fields['name_%s' % code] = forms.CharField(label=_(u'Название программы'), required=required,
widget=forms.TextInput(attrs={'style':'width: 550px'}))
self.fields['programe_%s' % code] = forms.CharField(label=_(u'Программа'), required=False,
widget=CKEditorWidget)
self.fields['speaker_%s' % code] = forms.CharField(label=_(u'Организатор'), required=False,
widget=forms.TextInput(attrs={'style':'width: 550px'}))
self.fields['place_%s' % code] = forms.CharField(label=_(u'Место проведения'), required=False,
widget=forms.TextInput(attrs={'style':'width: 550px'}))
def save(self,exposition=None):
data = self.cleaned_data
if not exposition:
return None
else:
timetable = TimeTable()
# simple fields
if data.get('timetable_organiser'):
timetable.timetable_organiser_id = data['timetable_organiser']
timetable.exposition = exposition
timetable.begin = data.get('begin')
timetable.end = data.get('end')
if not exposition:
fill_with_signal(TmpTimeTable, timetable, data)
else:
fill_with_signal(TimeTable, timetable, data)
return timetable
monthes = [('', ''),
(1, _(u'Январь')), (2, _(u'Февраль')), (3, _(u'Март')), (4, _(u'Апрель')),
(5, _(u'Май')), (6, _(u'Июнь')), (7, _(u'Июль')), (8, _(u'Август')),
(9, _(u'Сентябрь')), (10, _(u'Октябрь')), (11, _(u'Ноябрь')), (12, _(u'Декабрь'))]
class ExpositionFilterForm(EventsAdminFilterFormMixin, AdminFilterForm):
model = Exposition
country = forms.MultipleChoiceField(label=_(u'Страна'), choices=[(c.id, c.name) for c in Country.objects.language().all()],
required=False)
#city = forms.CharField(label=u'Город', widget=forms.HiddenInput(), required=False)
year = forms.CharField(label=_(u'Год'), required=False)
month = forms.ChoiceField(label=_(u'Месяц'),choices=[(item[0], item[1]) for item in monthes], required=False)
def filter(self):
data = self.cleaned_data
qs = super(ExpositionFilterForm, self).filter()
exact_name = data['exact_name']
if exact_name:
return self.model.objects.filter(translations__name=exact_name).distinct()
country = data['country']
# city = data['city']
year = data['year']
month = data['month']
if country:
qs = qs.filter(country__in=country)
# if city:
# qs = qs.filter(city__in=city)
if year:
qs = qs.filter(data_begin__year=year)
if month:
qs = qs.filter(data_begin__month=month)
return qs