From 0cbdece48359d080bbd345f5270020b71dc193b2 Mon Sep 17 00:00:00 2001 From: Dmitriy Shesterkin Date: Tue, 9 May 2017 20:27:06 +0300 Subject: [PATCH] autocomplete plaseholder --- src/customer/!!!del__forms.py | 486 ------------------ src/customer/consts.py | 1 - src/customer/context_processors.py | 2 +- src/customer/views/bank_accounts.py | 4 +- src/customer/views/profile_ajax.py | 8 +- src/docs/autocomplete_light_registry.py | 51 +- src/docs/forms/base_forms.py | 4 +- src/docs/forms/invoice.py | 2 - src/docs/models/base_models.py | 3 +- .../static/js/lib/jquery.formset.js | 12 +- .../templates/docs/!!del__stub_js.html | 133 ----- .../templates/docs/_base/base_list.html | 14 +- .../templates/docs/parts/form_tbl_items.html | 8 - 13 files changed, 59 insertions(+), 669 deletions(-) delete mode 100644 src/customer/!!!del__forms.py delete mode 100644 src/dokumentor/templates/docs/!!del__stub_js.html diff --git a/src/customer/!!!del__forms.py b/src/customer/!!!del__forms.py deleted file mode 100644 index 25684a8..0000000 --- a/src/customer/!!!del__forms.py +++ /dev/null @@ -1,486 +0,0 @@ -# -*- coding: utf-8 -*- -from django import forms -from django.utils.encoding import force_unicode -from django.utils.safestring import mark_safe -from django.conf import settings - -from yandex_money.forms import PaymentForm -from commons.forms import MyBaseModelForm, set_field_error - -from . import consts, models - - -FILE_UPLOAD_MAX_MEMORY_SIZE = getattr(settings, 'FILE_UPLOAD_MAX_MEMORY_SIZE ', 2621440) # default 2.5Mb - - -def get_profile_form_class(profile_type): - """Возвращает класс формы редактирования профиля пользователя.""" - if profile_type == consts.IP_PROFILE: - return IpUserProfileForm - elif profile_type == consts.ORG_PROFILE: - return OrgUserProfileForm - return None - - -def get_profile_filters_form_class(profile_type): - """Возвращает класс формы фильтрации профиля пользователя.""" - if profile_type == consts.IP_PROFILE: - return IpUserProfileFiltersForm - elif profile_type == consts.ORG_PROFILE: - return OrgUserProfileFiltersForm - return None - - -### - -def _numeric(field): - real_maxlength = field.widget.attrs['maxlength'] - return { - 'maxlength': int(real_maxlength)*3, # set fake maxlength. otherwise browser would cut pasted values too early - 'data-type': 'number', # used by jquery selector - 'data-maxlength': real_maxlength, # save real maxlength - } - -# ----------------------------------------------------------------------------- - - -class UserProfileForm(MyBaseModelForm): - """Общая форма редактирования профиля пользователя. - - Специализированные формы для редактирования профилей ИП и Организаций - - ищи ниже в классах IpUserProfileForm и OrgUserProfileForm соответственно. - - Форму для админки ищи ниже в классе UserProfileAdminForm. - """ - tmb_logo = forms.CharField(required=False, widget=forms.HiddenInput) - tmb_boss_sign = forms.CharField(required=False, widget=forms.HiddenInput) - tmb_glavbuh_sign = forms.CharField(required=False, widget=forms.HiddenInput) - tmb_stamp = forms.CharField(required=False, widget=forms.HiddenInput) - - class Meta: - model = models.UserProfile - - def __init__(self, *args, **kwargs): - super(UserProfileForm, self).__init__(*args, **kwargs) - if 'ip_reg_date' in self.fields: - self.fields['ip_reg_date'].widget.attrs['class'] = 'has-datepicker' - # - self.fields['inn'].widget.attrs.update(_numeric(self.fields['inn'])) - self.fields['ogrn'].widget.attrs.update(_numeric(self.fields['ogrn'])) - self.fields['okpo'].widget.attrs.update(_numeric(self.fields['okpo'])) - if 'kpp' in self.fields: - self.fields['kpp'].widget.attrs.update(_numeric(self.fields['kpp'])) - - def _check_file_size(self, image): - """Ограничить максимальный размер загружаемого файла.""" - if image and image.size > FILE_UPLOAD_MAX_MEMORY_SIZE: - raise forms.ValidationError( - u'Размер изображения превышает %i Мб' % (FILE_UPLOAD_MAX_MEMORY_SIZE / (1024*1024))) - return image - - def clean_boss_sign(self): - image = self.cleaned_data.get('boss_sign') - return self._check_file_size(image) - - def clean_glavbuh_sign(self): - image = self.cleaned_data.get('glavbuh_sign') - return self._check_file_size(image) - - def clean_stamp(self): - image = self.cleaned_data.get('stamp') - return self._check_file_size(image) - - def clean_logo(self): - image = self.cleaned_data.get('logo') - return self._check_file_size(image) - - -class IpUserProfileForm(UserProfileForm): - """Форма редактирования профиля - ИП.""" - change_labels = {'ogrn': u'ОГРНИП'} - - class Meta(UserProfileForm.Meta): - fields = ( - # фио ип - 'boss_surname', 'boss_name', 'boss_midname', - # инн, огрнип, окпо - 'inn', 'ogrn', 'okpo', - # свид-во гос. регистрации и дата - 'svid_gos_reg', 'ip_reg_date', - # фио главбуха - 'glavbuh_surname', 'glavbuh_name', 'glavbuh_midname', - # контактная информация - адреса, телефон, факс, почта, сайт - 'address', 'jur_address', 'real_address', 'phone_code', 'phone', 'fax_code', 'fax', 'email', 'site', - # подписи, печать и логотип - 'boss_sign', 'glavbuh_sign', 'stamp', 'logo', - 'tmb_logo', 'tmb_boss_sign', 'tmb_glavbuh_sign', 'tmb_stamp', - ) - - -class OrgUserProfileForm(UserProfileForm): - """Форма редактирования профиля - Организация.""" - unset_required = {'ogrn': u'ОГРН'} - change_labels = {'ogrn': u'ОГРН'} - - class Meta(UserProfileForm.Meta): - fields = ( - # краткое и полное названия организации - 'name', 'full_name', - # инн, кпп, огрн, окпо - 'inn', 'kpp', 'ogrn', 'okpo', - # должность руководителя, его фио и на каком основании он действует - 'boss_title', 'boss_surname', 'boss_name', 'boss_midname', 'na_osnovanii', - # фио главбуха - 'glavbuh_surname', 'glavbuh_name', 'glavbuh_midname', - # контактная информация - адреса, телефон, факс, почта, сайт - 'address', 'jur_address', 'real_address', 'phone_code', 'phone', 'fax_code', 'fax', 'email', 'site', - # подписи, печать и логотип - 'boss_sign', 'glavbuh_sign', 'stamp', 'logo', - 'tmb_logo', 'tmb_boss_sign', 'tmb_glavbuh_sign', 'tmb_stamp', - ) - - -class UserProfileAdminForm(UserProfileForm): - """Форма редактирования профиля - для админки.""" - - # условно-обязательные поля, проверять отдельно - могут быть обязательны в зависимости от типа профиля - unset_required = [ - # для ИП - 'kpp', 'name' - # для Организаций - ] - - def clean(self): - super(UserProfileAdminForm, self).clean() - - cleaned_data = self.cleaned_data - - # тип профиля - ИП или Организация - profile_type = cleaned_data.get('profile_type') - - if profile_type == consts.IP_PROFILE: # поля, обязательные для ИП - pass - - elif profile_type == consts.ORG_PROFILE: # поля, обязательные для Организаций - org_boss_name = cleaned_data.get('org_boss_name') - kpp = cleaned_data.get('kpp') - - if not org_boss_name: set_field_error(self, 'org_boss_name') - if not kpp: set_field_error(self, 'kpp') - - return cleaned_data - -# ----------------------------------------------------------------------------- - - -class BankAccountForm(forms.ModelForm): - """Форма редактирования расчетных счетов.""" - # search_bank = forms.CharField(label=u'Поиск банка', required=False, initial='') - class Meta: - model = models.BankAccount - # fields = ('search_bank', 'bik', 'name', 'short_name', 'korr_account', 'account', 'is_main', 'company') - fields = ('bik', 'name', 'short_name', 'korr_account', 'account', 'is_main', 'company') - _textarea = forms.Textarea(attrs={'cols': 80, 'rows': 3}) - widgets = { - 'bik': forms.HiddenInput(), - 'name': forms.HiddenInput(), - 'short_name': forms.HiddenInput(), - 'korr_account': forms.HiddenInput(), - 'company': forms.HiddenInput(), - } - - def __init__(self, *args, **kwargs): - super(BankAccountForm, self).__init__(*args, **kwargs) - # self.fields['bik'].widget.attrs.update(_numeric(self.fields['bik'])) - # self.fields['korr_account'].widget.attrs.update(_numeric(self.fields['korr_account'])) - self.fields['account'].widget.attrs.update(_numeric(self.fields['account'])) - # self.fields['search_bank'].widget.attrs['class'] = 'search-bank' - - -class BankAccountAdminForm(BankAccountForm): - """Форма редактирования расчетных счетов - для админки.""" - class Meta(BankAccountForm.Meta): - fields = None - exclude = ('address',) - - -class BankAccountListForm(forms.Form): - """Форма со списком всех расчетных счетов пользователя.""" - bank_account = forms.ModelChoiceField(queryset=models.BankAccount.objects.get_all(None), - empty_label=u'все контрагенты', required=False) - - def __init__(self, user, *args, **kwargs): - super(BankAccountListForm, self).__init__(*args, **kwargs) - self.fields['bank_account'].queryset = models.BankAccount.objects.get_all(user.profile) - -# ----------------------------------------------------------------------------- - - -class ClientForm(forms.ModelForm): - """Форма редактирования контрагентов.""" - class Meta: - model = models.Client - fields = ('name', 'inn', 'kpp', 'ogrn', 'okpo', 'address', - # банковские реквизиты - 'bank_bik', 'bank_name', 'bank_korr_account', 'bank_account', - # контакты - 'contact_name', 'contact_email', 'contact_phone', 'contact_skype', 'contact_other', - ) - _textarea = forms.Textarea(attrs={'cols': 80, 'rows': 3}) - widgets = { - 'bank_bik': forms.HiddenInput(), - 'bank_name': forms.HiddenInput(), - 'short_name': forms.HiddenInput(), - 'bank_korr_account': forms.HiddenInput(), - } - - def __init__(self, *args, **kwargs): - super(ClientForm, self).__init__(*args, **kwargs) - self.fields['inn'].widget.attrs.update(_numeric(self.fields['inn'])) - self.fields['kpp'].widget.attrs.update(_numeric(self.fields['kpp'])) - self.fields['ogrn'].widget.attrs.update(_numeric(self.fields['ogrn'])) - self.fields['okpo'].widget.attrs.update(_numeric(self.fields['okpo'])) - # self.fields['bank_bik'].widget.attrs.update(_numeric(self.fields['bank_bik'])) - # self.fields['bank_korr_account'].widget.attrs.update(_numeric(self.fields['bank_korr_account'])) - # self.fields['bank_account'].widget.attrs.update(_numeric(self.fields['bank_account'])) - - -class ClientAdminForm(ClientForm): - """Форма редактирования контрагентов - для админки.""" - class Meta(ClientForm.Meta): - fields = None - exclude = ('bank_address',) - - -class ClientsListForm(forms.Form): - """Форма со списком всех контрагентов пользователя.""" - client = forms.ModelChoiceField(queryset=models.Client.objects.get_all(None), empty_label=u'все контрагенты', - required=False) - - def __init__(self, user, *args, **kwargs): - super(ClientsListForm, self).__init__(*args, **kwargs) - self.fields['client'].queryset = models.Client.objects.get_all(user.profile) - -# ----------------------------------------------------------------------------- - - -class UserProfileFiltersForm(MyBaseModelForm): - """Общая форма фильтрации реквизитов.""" - _profile_type = None # задать в наследнике! - - _is_admin = False - _user = None - - class Meta: - model = models.UserProfileFilters - widgets = { - 'bank_account': forms.RadioSelect(), - } - - def __init__(self, profile=None, accounts=None, *args, **kwargs): - instance = kwargs.get('instance') - initial = kwargs.get('initial') - - new_initial = { - # всегда включены - 'show_ip_boss_fio': True, - 'show_name': True, - } - - # TODO 1. переписать проверки в стиле new_initial['show_inn'] = bool(profile.inn) - # TODO 2. загнать условия в словарь вида {'show_inn': 'inn'}. потом в цикле обработать - if profile: - # сбросить чекбоксы, если не заполнены определенные поля в профиле или нет расчетных счетов - if instance: - new_initial['show_inn'] = bool(profile.inn) - new_initial['show_ogrn'] = bool(profile.ogrn) - new_initial['show_okpo'] = bool(profile.okpo) - new_initial['show_glavbuh'] = bool(profile.get_glavbuh_fio()) - new_initial['show_address'] = bool(profile.address) - new_initial['show_jur_address'] = bool(profile.jur_address) - new_initial['show_real_address'] = bool(profile.real_address) - new_initial['show_phone'] = bool(profile.get_full_phone()) - new_initial['show_fax'] = bool(profile.get_full_fax()) - new_initial['show_email'] = bool(profile.email) - new_initial['show_site'] = bool(profile.site) - new_initial['show_bank_account'] = bool(accounts) - new_initial['show_logo'] = bool(profile.logo) - - if self._profile_type == consts.IP_PROFILE: - new_initial['show_svid_gos_reg'] = bool(profile.svid_gos_reg) - new_initial['show_ip_reg_date'] = bool(profile.ip_reg_date) - elif self._profile_type == consts.ORG_PROFILE: - new_initial['show_full_name'] = bool(profile.full_name) - new_initial['show_kpp'] = bool(profile.kpp) - new_initial['show_na_osnovanii'] = bool(profile.na_osnovanii) - else: - new_initial['show_inn'] = bool(profile.inn) - new_initial['show_ogrn'] = bool(profile.ogrn) - new_initial['show_okpo'] = bool(profile.okpo) - new_initial['show_glavbuh'] = bool(profile.get_glavbuh_fio()) - new_initial['show_address'] = bool(profile.address) - new_initial['show_jur_address'] = bool(profile.jur_address) - new_initial['show_real_address'] = bool(profile.real_address) - new_initial['show_phone'] = bool(profile.get_full_phone()) - new_initial['show_fax'] = bool(profile.get_full_fax()) - new_initial['show_email'] = bool(profile.email) - new_initial['show_site'] = bool(profile.site) - new_initial['show_bank_account'] = bool(accounts) - new_initial['show_logo'] = bool(profile.logo) - - if self._profile_type == consts.IP_PROFILE: - new_initial['show_svid_gos_reg'] = bool(profile.svid_gos_reg) - new_initial['show_ip_reg_date'] = bool(profile.ip_reg_date) - elif self._profile_type == consts.ORG_PROFILE: - new_initial['show_full_name'] = bool(profile.full_name) - new_initial['show_kpp'] = bool(profile.kpp) - new_initial['show_na_osnovanii'] = bool(profile.na_osnovanii) - - if initial: - initial.update(new_initial) - else: - kwargs['initial'] = new_initial - - super(UserProfileFiltersForm, self).__init__(*args, **kwargs) - - # для админки - if self._is_admin: - # попробовать взять user из kwargs['instance'], а потом из self.data - try: - self._user = getattr(kwargs.get('instance'), 'user') - except AttributeError: - self._user = self.data.get('user') - if not accounts: - accounts = models.BankAccount.objects.get_all(self._user.profile) - - f = self.fields - - # только расчетные счета пользователя - f_acc = f['bank_account'] # TODO вынести настройку расчетных счетов в mixin? - f_acc.queryset = accounts - f_acc.empty_label = None - f_acc.label_from_instance = lambda obj: mark_safe( - force_unicode('%s
%s' % (obj.account, obj.name,))) # исправить метку - - # заблокировать чекбоксы, если: не заполнены определенные поля в профиле или нет расчетных счетов - if profile: - if not profile.inn: f['show_inn'].widget.attrs['disabled'] = 'disabled' - if not profile.ogrn: f['show_ogrn'].widget.attrs['disabled'] = 'disabled' - if not profile.okpo: f['show_okpo'].widget.attrs['disabled'] = 'disabled' - if not profile.get_glavbuh_fio(): f['show_glavbuh'].widget.attrs['disabled'] = 'disabled' - if not profile.address: f['show_address'].widget.attrs['disabled'] = 'disabled' - if not profile.jur_address: f['show_jur_address'].widget.attrs['disabled'] = 'disabled' - if not profile.real_address: f['show_real_address'].widget.attrs['disabled'] = 'disabled' - if not profile.get_full_phone(): f['show_phone'].widget.attrs['disabled'] = 'disabled' - if not profile.get_full_fax(): f['show_fax'].widget.attrs['disabled'] = 'disabled' - if not profile.email: f['show_email'].widget.attrs['disabled'] = 'disabled' - if not profile.site: f['show_site'].widget.attrs['disabled'] = 'disabled' - if not profile.logo: f['show_logo'].widget.attrs['disabled'] = 'disabled' - if not accounts: f['show_bank_account'].widget.attrs['disabled'] = 'disabled' - - if self._profile_type == consts.IP_PROFILE: - if not profile.svid_gos_reg: f['show_svid_gos_reg'].widget.attrs['disabled'] = 'disabled' - if not profile.ip_reg_date: f['show_ip_reg_date'].widget.attrs['disabled'] = 'disabled' - elif self._profile_type == consts.ORG_PROFILE: - if not profile.name: f['show_name'].widget.attrs['disabled'] = 'disabled' - if not profile.full_name: f['show_full_name'].widget.attrs['disabled'] = 'disabled' - if not profile.kpp: f['show_kpp'].widget.attrs['disabled'] = 'disabled' - if not profile.boss_title: f['show_org_boss_title_and_fio'].widget.attrs['disabled'] = 'disabled' - if not profile.na_osnovanii: f['show_na_osnovanii'].widget.attrs['disabled'] = 'disabled' - - # блокировать чекбоксы, т.к.эти реквизиты юзеру выключать нельзя - if self._profile_type == consts.IP_PROFILE: - f['show_ip_boss_fio'].widget.attrs['disabled'] = 'disabled' - elif self._profile_type == consts.ORG_PROFILE: - f['show_name'].widget.attrs['disabled'] = 'disabled' - - -class IpUserProfileFiltersForm(UserProfileFiltersForm): - """Форма фильтрации реквизитов - для ИП.""" - _profile_type = consts.IP_PROFILE - - change_labels = { - 'show_profile_type': dict(consts.PROFILE_TYPES)[_profile_type], - 'show_ogrn': u'ОГРНИП', - } - - class Meta(UserProfileFiltersForm.Meta): - fields = ( - 'show_profile_type', - 'show_ip_boss_fio', - 'show_inn', - 'show_ogrn', - 'show_okpo', - 'show_svid_gos_reg', - 'show_ip_reg_date', - 'show_glavbuh', - 'show_bank_account', - 'bank_account', - 'show_contact_info', - 'show_address', - 'show_jur_address', - 'show_real_address', - 'show_phone', - 'show_fax', - 'show_email', - 'show_site', - 'show_logo', - ) - - -class OrgUserProfileFiltersForm(UserProfileFiltersForm): - """Форма фильтрации реквизитов - для Организаций.""" - _profile_type = consts.ORG_PROFILE - - change_labels = { - 'show_profile_type': dict(consts.PROFILE_TYPES)[_profile_type], - 'show_ogrn': u'ОГРН', - } - - class Meta(UserProfileFiltersForm.Meta): - fields = ( - 'show_profile_type', - 'show_name', - 'show_full_name', - 'show_inn', - 'show_kpp', - 'show_ogrn', - 'show_okpo', - 'show_org_boss_title_and_fio', - 'show_na_osnovanii', - 'show_glavbuh', - 'show_bank_account', - 'bank_account', - 'show_contact_info', - 'show_address', - 'show_jur_address', - 'show_real_address', - 'show_phone', - 'show_fax', - 'show_email', - 'show_site', - 'show_logo', - ) - -# ----------------------------------------------------------------------------- - - -class EmailProfileForm(forms.Form): - """Форма отправки реквизитов пользователя по email.""" - to = forms.EmailField(label=u'E-mail получателя') - body = forms.CharField(label=u'Текст сообщения', max_length=1000, required=False, - widget=forms.Textarea(attrs={'cols': 80, 'rows': 3})) - - -class LicenseForm(forms.Form): - """Форма продления лицензии - """ - term = forms.ModelChoiceField(queryset=models.LicensePrice.objects.all(), - widget=forms.RadioSelect, label=u'Срок лицензии', empty_label = None) - payform = forms.ChoiceField(choices=consts.PAYFORMS[1:], widget=forms.RadioSelect, - label=u'Форма оплаты') - - -class YaForm(PaymentForm): - def get_display_field_names(self): - return () diff --git a/src/customer/consts.py b/src/customer/consts.py index ed42452..6de6261 100644 --- a/src/customer/consts.py +++ b/src/customer/consts.py @@ -21,7 +21,6 @@ PAYFORMS = ( (-1, u'Бесплатно'), (0, u'Безналичный расчёт'), (1, u'Банковская карта'), -# (2, u'Квитанция Сбербанка'), ) TERMS = ( diff --git a/src/customer/context_processors.py b/src/customer/context_processors.py index 7872f64..45ffd37 100644 --- a/src/customer/context_processors.py +++ b/src/customer/context_processors.py @@ -1,7 +1,7 @@ # -*- coding: utf-8 -*- from datetime import datetime, timedelta from django.core.cache import cache -from .models import License +from customer.models import License def license_check_soon_ends(request): diff --git a/src/customer/views/bank_accounts.py b/src/customer/views/bank_accounts.py index 4d50f69..58c261d 100644 --- a/src/customer/views/bank_accounts.py +++ b/src/customer/views/bank_accounts.py @@ -7,7 +7,7 @@ from django.contrib.auth.decorators import login_required from commons.paginator import pagination, save_per_page_value from .. import models, forms -from ..decorators import license_required +from ..decorators import license_required from ..utils import raise_if_no_profile @@ -98,7 +98,7 @@ def bank_accounts_delete(request, id): """Удалить расчетный счет.""" raise_if_no_profile(request) - template_name='customer/bank_accounts/delete.html' + template_name = 'customer/bank_accounts/delete.html' success_url = 'customer_bank_accounts_list' referer = request.POST.get('referer') diff --git a/src/customer/views/profile_ajax.py b/src/customer/views/profile_ajax.py index 1c78ba0..0a9ba29 100644 --- a/src/customer/views/profile_ajax.py +++ b/src/customer/views/profile_ajax.py @@ -41,8 +41,8 @@ def profile_filters_edit_ajax(request): data = { 'success': form.is_valid(), - 'field_errors': form.errors, # ошибки полей - 'form_errors': non_field_errors, # ошибки формы + 'field_errors': form.errors, # ошибки полей + 'form_errors': non_field_errors, # ошибки формы } return HttpResponse(json.dumps(data), content_type='application/json') @@ -78,7 +78,7 @@ def profile_email_ajax(request): data = { 'success': form.is_valid(), - 'field_errors': form.errors, # ошибки полей - 'form_errors': non_field_errors, # ошибки формы + 'field_errors': form.errors, # ошибки полей + 'form_errors': non_field_errors, # ошибки формы } return HttpResponse(json.dumps(data), content_type='application/json') diff --git a/src/docs/autocomplete_light_registry.py b/src/docs/autocomplete_light_registry.py index c15768e..e6ec8b5 100644 --- a/src/docs/autocomplete_light_registry.py +++ b/src/docs/autocomplete_light_registry.py @@ -2,21 +2,25 @@ import autocomplete_light from django.db.models import Q -from docs.models import (Country, Currency, Measure) +from docs.models import Country, Currency, Measure from customer.models import Client class AutocompleteWithEmptyWidget(autocomplete_light.AutocompleteModelBase): - '''Автокомплит без текста подсказки - ''' - autocomplete_js_attributes = {'placeholder': u''} + """ + Автокомплит без текста подсказки + """ + autocomplete_js_attributes = {'placeholder': ''} class AutocompleteClient(autocomplete_light.AutocompleteModelBase): - '''Автокомплит клиента в зависимости от юзера - ''' - autocomplete_js_attributes = {'placeholder': u'Название из добавленных ранее'} - + """ + Автокомплит клиента в зависимости от юзера + """ + attrs = { + 'data-autcomplete-minimum-characters': 0, + 'placeholder': 'Название из добавленных ранее', + } def choices_for_request(self): q = self.request.GET.get('q', '') user_ = self.request.user @@ -30,24 +34,37 @@ class AutocompleteClient(autocomplete_light.AutocompleteModelBase): class AutocompleteCurrency(autocomplete_light.AutocompleteModelBase): - '''Автокомплит валют - ''' - autocomplete_js_attributes = {'placeholder': u'Название валюты'} + """ + Автокомплит валют + """ + attrs = { + 'data-autcomplete-minimum-characters': 0, + 'placeholder': 'Название валюты', + } search_fields = ('name', '^abc_code', '^code') class AutocompleteMeasure(autocomplete_light.AutocompleteModelTemplate): - '''Автокомплит ед. измерения - ''' - autocomplete_js_attributes = {'placeholder': u'Название ед. измерения'} + """ + Автокомплит ед. измерения + """ + attrs = { + 'data-autcomplete-minimum-characters': 0, + 'placeholder': '', + } + widget_attrs = {'data-widget-maximum-values': 3} search_fields = ('name', 'full_name', '^code') choice_template = 'autocomplete_light/docs_measure_choice.html' class AutocompleteCountry(autocomplete_light.AutocompleteModelTemplate): - '''Автокомплит стран - ''' - autocomplete_js_attributes = {'placeholder': u'Название страны'} + """ + Автокомплит стран + """ + attrs = { + 'data-autcomplete-minimum-characters': 0, + 'placeholder': 'Название страны', + } search_fields = ('name', 'full_name', '^code') choice_template = 'autocomplete_light/docs_country_choice.html' diff --git a/src/docs/forms/base_forms.py b/src/docs/forms/base_forms.py index 259170f..776172d 100644 --- a/src/docs/forms/base_forms.py +++ b/src/docs/forms/base_forms.py @@ -18,7 +18,7 @@ class BaseModelForm(MyBaseModelForm): # пользователя. Если же пользователь никак не был задан - селекты будут пустыми! Если в форме есть поле client, # то оно настраивается автоматически. client = ModelChoiceField(Client.objects.all(), label=u'клиент', required=True, - widget=autocomplete_light.ChoiceWidget('ACClient')) + widget=autocomplete_light.ChoiceWidget('ACClient')) adjust_client_fields = [] def __init__(self, user, *args, **kwargs): @@ -64,7 +64,7 @@ class BaseModelForm(MyBaseModelForm): self._adjust_clients() def _adjust_clients(self): - #"""Настраивает перечисленные в self.adjust_client_fields поля на модель Client.""" + # Настраивает перечисленные в self.adjust_client_fields поля на модель Client. if self.adjust_client_fields: user_clients = Client.objects.filter(company=self._user.profile) for key in self.adjust_client_fields: diff --git a/src/docs/forms/invoice.py b/src/docs/forms/invoice.py index bf3dac9..31701ad 100644 --- a/src/docs/forms/invoice.py +++ b/src/docs/forms/invoice.py @@ -54,8 +54,6 @@ class InvoiceItemForm(MyBaseModelForm): class Meta: model = InvoiceItem - # exclude = ('parent',) - # fields = ('name', 'qty', 'units', 'price', 'total_price', 'id',) fields = ('id', 'name', 'qty', 'units', 'price', 'total_price',) diff --git a/src/docs/models/base_models.py b/src/docs/models/base_models.py index 55ca019..6d6355c 100644 --- a/src/docs/models/base_models.py +++ b/src/docs/models/base_models.py @@ -109,5 +109,6 @@ class BaseItemInvoiceModel(BaseItemModel): return u'%s, %s %s * %s = %s %s' % (self.name[:30], self.qty, self.units, self.price, self.total_price, curr) def save(self, *args, **kwargs): - self.total_price = self.price * self.qty # пересчитать сумму + # пересчитать сумму + self.total_price = self.price * self.qty super(BaseItemInvoiceModel, self).save(*args, **kwargs) diff --git a/src/dokumentor/static/js/lib/jquery.formset.js b/src/dokumentor/static/js/lib/jquery.formset.js index 463bc44..9a63ae8 100644 --- a/src/dokumentor/static/js/lib/jquery.formset.js +++ b/src/dokumentor/static/js/lib/jquery.formset.js @@ -82,7 +82,7 @@ }, checkActionButtons = function() { var max_num = parseInt($('#id_' + options.prefix + '-MAX_NUM_FORMS').val()), - formCount = $$formsetContainer.find('.'+options.formCssClass).length + formCount = $$formsetContainer.find('.'+options.formCssClass).length; if (options.min_num > 0) { if (formCount <= options.min_num) { @@ -182,20 +182,20 @@ } return $$; - } + }; /* Setup plugin defaults */ var clearErrors = function(row) { $(row).find('.errorlist').remove(); - } + }; var calc_itogo = function(row) { window.calc_itogo(); - } + }; $.fn.formset.defaults = { prefix: 'form', // The form prefix for your django formset min_num: 0, // Minimum count rows formTemplate: null, // The jQuery selection cloned to generate new form instances - addText: 'Добавить строку', // Text for the add link + addText: 'Добавить позицию', // Text for the add link deleteText: '', // Text for the delete link addCssClass: 'add-row', // CSS class applied to the add link deleteCssClass: 'delete-row', // CSS class applied to the delete link @@ -206,4 +206,4 @@ beforeremove: null, // Function called each time before a new form is added removed: calc_itogo // Function called each time a form is deleted }; -})(jQuery) +})(jQuery); diff --git a/src/dokumentor/templates/docs/!!del__stub_js.html b/src/dokumentor/templates/docs/!!del__stub_js.html deleted file mode 100644 index 0393266..0000000 --- a/src/dokumentor/templates/docs/!!del__stub_js.html +++ /dev/null @@ -1,133 +0,0 @@ -{# заглушка js #} - diff --git a/src/dokumentor/templates/docs/_base/base_list.html b/src/dokumentor/templates/docs/_base/base_list.html index 3a4d762..b3c5b3c 100644 --- a/src/dokumentor/templates/docs/_base/base_list.html +++ b/src/dokumentor/templates/docs/_base/base_list.html @@ -1,5 +1,7 @@ {% extends "base.html" %} +{% load static %} + {% block title %}{{ padeji_mnoj.imenit|capfirst }}{% endblock %} {% block content %} @@ -73,7 +75,7 @@
@@ -139,10 +141,10 @@ CLIENT.get_url_pattern = "{% url 'customer_clients_get_ajax' 0 %}"; - - - - + + + + - + {% endblock %} diff --git a/src/dokumentor/templates/docs/parts/form_tbl_items.html b/src/dokumentor/templates/docs/parts/form_tbl_items.html index fc043dd..af210db 100644 --- a/src/dokumentor/templates/docs/parts/form_tbl_items.html +++ b/src/dokumentor/templates/docs/parts/form_tbl_items.html @@ -38,14 +38,6 @@ - {% comment %} - - - Без НДС - - - - {% endcomment %} {{ formset.management_form }}