<commit_before>"""
Form components for working with trees.
"""
from django import forms
from django.forms.forms import NON_FIELD_ERRORS
from django.forms.util import ErrorList
from django.utils.encoding import smart_unicode
from django.utils.html import conditional_escape, mark_safe
from django.utils.translation import ugettext_lazy as _

from mptt.exceptions import InvalidMove

__all__ = ('TreeNodeChoiceField', 'TreeNodeMultipleChoiceField', 'TreeNodePositionField', 'MoveNodeForm')

# Fields ######################################################################

class TreeNodeChoiceField(forms.ModelChoiceField):
    """A ModelChoiceField for tree nodes."""
    def __init__(self, queryset, *args, **kwargs):
        self.level_indicator = kwargs.pop('level_indicator', u'---')
        if kwargs.get('required', True) and not 'empty_label' in kwargs:
            kwargs['empty_label'] = None

        # if a queryset is supplied, enforce ordering
        if hasattr(queryset, 'model'):
            mptt_opts = queryset.model._mptt_meta
            queryset = queryset.order_by(mptt_opts.tree_id_attr, mptt_opts.left_attr)

        super(TreeNodeChoiceField, self).__init__(queryset, *args, **kwargs)

    def label_from_instance(self, obj):
        """
        Creates labels which represent the tree level of each node when
        generating option labels.
        """
        level = getattr(obj, obj._mptt_meta.level_attr)
        level_indicator = mark_safe(conditional_escape(self.level_indicator) * level)
        return mark_safe(u'%s %s' % (level_indicator, conditional_escape(smart_unicode(obj))))

class TreeNodeMultipleChoiceField(TreeNodeChoiceField, forms.ModelMultipleChoiceField):
    """A ModelMultipleChoiceField for tree nodes."""<commit_msg>make label_from_instance more overridable for TreeNodeChoiceField, fixes #124<commit_after>"""
Form components for working with trees.
"""
from django import forms
from django.forms.forms import NON_FIELD_ERRORS
from django.forms.util import ErrorList
from django.utils.encoding import smart_unicode
from django.utils.html import conditional_escape, mark_safe
from django.utils.translation import ugettext_lazy as _

from mptt.exceptions import InvalidMove

__all__ = ('TreeNodeChoiceField', 'TreeNodeMultipleChoiceField', 'TreeNodePositionField', 'MoveNodeForm')

# Fields ######################################################################

class TreeNodeChoiceField(forms.ModelChoiceField):
    """A ModelChoiceField for tree nodes."""
    def __init__(self, queryset, *args, **kwargs):
        self.level_indicator = kwargs.pop('level_indicator', u'---')
        if kwargs.get('required', True) and not 'empty_label' in kwargs:
            kwargs['empty_label'] = None

        # if a queryset is supplied, enforce ordering
        if hasattr(queryset, 'model'):
            mptt_opts = queryset.model._mptt_meta
            queryset = queryset.order_by(mptt_opts.tree_id_attr, mptt_opts.left_attr)

        super(TreeNodeChoiceField, self).__init__(queryset, *args, **kwargs)
    
    def _get_level_indicator(self, obj):
        level = getattr(obj, obj._mptt_meta.level_attr)
        return mark_safe(conditional_escape(self.level_indicator) * level)
        
    def label_from_instance(self, obj):
        """
        Creates labels which represent the tree level of each node when
        generating option labels.
        """
        level_indicator = self._get_level_indicator(obj)
        return mark_safe(u'%s %s' % (level_indicator, conditional_escape(smart_unicode(obj))))

class TreeNodeMultipleChoiceField(TreeNodeChoiceField, forms.ModelMultipleChoiceField):
    """A ModelMultipleChoiceField for tree nodes."""
{'fraction_non_alphanumeric': 0.12830902215018908, 'fraction_numerical': 0.0008103727714748784, 'mean_word_length': 4.358900144717801, 'pattern_counts': {'":': 0, '<': 3, '<?xml version=': 0, '>': 3, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '2522050', 'n_tokens_mistral': 1042, 'n_tokens_neox': 1017, 'n_words': 257}