【问题标题】:django-mptt: How to auto select children in admin when selecting parent?django-mptt:选择父级时如何在管理员中自动选择子级?
【发布时间】:2021-10-31 02:15:59
【问题描述】:

我在选择父母时遇到了一些麻烦 - 没有自动选择孩子。例如,当我选择 Cluster #2 时,它的子项(Store #1Store #2)未被选中:

我该如何解决这个问题?

这很重要,因为我只需要使用stores(带有叶子)创建多对多(Deviation-Orgunit)链接。

型号:

from django.db import models
from mptt.fields import TreeForeignKey
from mptt.models import MPTTModel


class Orgunit(MPTTModel):
    name = models.CharField(
        max_length=100
    )
    type = models.CharField(
        choices=[
            ('MACRO', 'Макро'),
            ('CLUSTER', 'Кластер'),
            ('KUST', 'Куст'),
            ('STORE', 'Магазин')
        ],
        max_length=100
    )
    parent = TreeForeignKey(
        'self',
        on_delete=models.CASCADE,
        null=True,
        blank=True,
        related_name='children'
    )

    def __str__(self):
        return self.name


class Deviation(models.Model):
    name = models.CharField(max_length=100)
    number = models.PositiveIntegerField(null=True)
    orgunits = models.ManyToManyField('orgunits.Orgunit')

    def __str__(self):
        return self.name

管理员:

from django.contrib import admin

from deviations.forms import MyForm
from deviations.models import Deviation


@admin.register(Deviation)
class DeviationAdmin(admin.ModelAdmin):
    form = MyForm

表格:

from django.forms import ModelForm, widgets
from mptt.forms import TreeNodeMultipleChoiceField

from orgunits.models import Orgunit


class MyForm(ModelForm):
    orgunits = TreeNodeMultipleChoiceField(queryset=Orgunit.objects.all(), widget=widgets.SelectMultiple())

    class Meta:
        model = Orgunit
        fields = '__all__'

【问题讨论】:

    标签: django django-forms django-mptt


    【解决方案1】:

    我以下面的代码为例:

     private void CheckAllChildNodes(TreeNode treeNode, bool nodeChecked)
        {
            foreach (TreeNode node in treeNode.Nodes)
            {
                node.Checked = nodeChecked;
                if (node.Nodes.Count > 0)
                {
                    this.CheckAllChildNodes(node, nodeChecked);
                }
            }
        }
        private void treeView_AfterCheck(object sender, TreeViewEventArgs e)
        {
            if (e.Action != TreeViewAction.Unknown)
            {
                if (e.Node.Nodes.Count > 0)
                {
                    if (!e.Node.Checked)
                    {
                        this.CheckAllChildNodes(e.Node, e.Node.Checked);
                    }
                }
            }
    
            if (e.Node.Parent != null)
            {
                TreeNode n = e.Node;
                while (n.Parent != null)
                {
                    if (n.Checked)
                    {
                        n.Parent.Checked = true;
                    }
                    n = n.Parent;
                }
            }
    
        }
    

    否则,有更多关于 AfterCheck 事件的文档可以做到这一点

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2011-03-01
      • 1970-01-01
      • 1970-01-01
      • 2015-04-16
      • 1970-01-01
      • 1970-01-01
      • 2023-04-04
      • 1970-01-01
      相关资源
      最近更新 更多