change color image video field and place it in product varient model
This commit is contained in:
+43
-30
@@ -77,11 +77,24 @@ class AttributeValueAdmin(ModelAdmin, ImportExportModelAdmin):
|
||||
"widget": ArrayWidget,
|
||||
}
|
||||
}
|
||||
def get_form(self, request, obj=None, change=False, **kwargs):
|
||||
form = super().get_form(request, obj, change, **kwargs)
|
||||
form.base_fields["color"].widget = UnfoldAdminColorInputWidget()
|
||||
return form
|
||||
# def get_form(self, request, obj=None, change=False, **kwargs):
|
||||
# form = super().get_form(request, obj, change, **kwargs)
|
||||
# form.base_fields["color"].widget = UnfoldAdminColorInputWidget()
|
||||
# return form
|
||||
|
||||
@admin.register(ProductImageModel)
|
||||
class ProductImagesAdmin(ModelAdmin):
|
||||
import_form_class = ImportForm
|
||||
export_form_class = ExportForm
|
||||
search_fields = ['name']
|
||||
compressed_fields = True
|
||||
warn_unsaved_form = True
|
||||
|
||||
formfield_overrides = {
|
||||
ArrayField: {
|
||||
"widget": ArrayWidget,
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
@@ -92,14 +105,14 @@ class ProductVariantInLine(StackedInline):
|
||||
show_change_link = True
|
||||
tab = True
|
||||
min_num = 1
|
||||
autocomplete_fields = ['attributes']
|
||||
autocomplete_fields = ['attributes', 'in_pack_items', 'images']
|
||||
# search_fields = ['']
|
||||
|
||||
|
||||
def get_form(self, request, obj=None, change=False, **kwargs):
|
||||
form = super().get_form(request, obj, change, **kwargs)
|
||||
form.base_fields["color"].widget = UnfoldAdminColorInputWidget()
|
||||
return form
|
||||
def formfield_for_dbfield(self, db_field, request, **kwargs):
|
||||
if db_field.name == 'color':
|
||||
kwargs['widget'] = UnfoldAdminColorInputWidget()
|
||||
return super().formfield_for_dbfield(db_field, request, **kwargs)
|
||||
|
||||
|
||||
|
||||
@@ -138,15 +151,15 @@ class ProductModelAdmin(ModelAdmin, ImportExportModelAdmin):
|
||||
readonly_fields = ('slug', )
|
||||
search_fields = ['name', 'description', ]
|
||||
list_filter = ['show', 'category']
|
||||
autocomplete_fields = ['related_products', 'in_pack_items',]
|
||||
autocomplete_fields = ['related_products', ]
|
||||
# compressed_fields = True
|
||||
warn_unsaved_form = True
|
||||
list_display = ['display_image', 'display_price', 'view', 'show', 'rating', 'category', ]
|
||||
list_display = ['display_price', 'view', 'show', 'rating', 'category', ]
|
||||
fieldsets = (
|
||||
('فیلد های اصلی', {'fields': ('name', 'description', 'category', 'related_products', 'show',), "classes": ["tab"],}),
|
||||
('فیلد های سيو', {'fields': ('meta_description', 'meta_keywords', 'meta_rating', 'slug'), "classes": ["tab"],}),
|
||||
('فیلد های مربوط به کاربر', {'fields': ('rating', 'view',), "classes": ["tab"],}),
|
||||
('فیلد های ایتم های پک', {'fields': ('in_pack_items', ), "classes": ["tab"],})
|
||||
# ('فیلد های ایتم های پک', {'fields': ('in_pack_items', ), "classes": ["tab"],})
|
||||
|
||||
)
|
||||
formfield_overrides = {
|
||||
@@ -163,24 +176,24 @@ class ProductModelAdmin(ModelAdmin, ImportExportModelAdmin):
|
||||
return obj.get_toman_price()
|
||||
display_price.short_description = 'قیمت تومانی'
|
||||
|
||||
@display(description='محصول', header=True)
|
||||
def display_image(self, instance):
|
||||
if instance and instance.variants.first() and instance.variants.first().attributes.first():
|
||||
image = instance.variants.first().attributes.first().image.url if instance.variants.first().attributes.first().image else None
|
||||
else:
|
||||
image = None
|
||||
return [
|
||||
instance.name,
|
||||
None,
|
||||
None,
|
||||
{
|
||||
"path": image,
|
||||
"height": 30,
|
||||
"width": 30,
|
||||
"borderless": True,
|
||||
# "squared": True,
|
||||
},
|
||||
]
|
||||
# @display(description='محصول', header=True)
|
||||
# def display_image(self, instance):
|
||||
# if instance and instance.variants.first() and instance.variants.first().attributes.first():
|
||||
# image = instance.variants.first().attributes.first().image.url if instance.variants.first().attributes.first().image else None
|
||||
# else:
|
||||
# image = None
|
||||
# return [
|
||||
# instance.name,
|
||||
# None,
|
||||
# None,
|
||||
# {
|
||||
# "path": image,
|
||||
# "height": 30,
|
||||
# "width": 30,
|
||||
# "borderless": True,
|
||||
# # "squared": True,
|
||||
# },
|
||||
# ]
|
||||
# @display(
|
||||
# description=("نمایش در صفحه ی اصلی"),
|
||||
# label={
|
||||
|
||||
@@ -0,0 +1,22 @@
|
||||
# Generated by Django 5.1.2 on 2025-02-11 17:44
|
||||
|
||||
from django.db import migrations, models
|
||||
|
||||
|
||||
class Migration(migrations.Migration):
|
||||
|
||||
dependencies = [
|
||||
('product', '0020_productvariant_max_price_and_more'),
|
||||
]
|
||||
|
||||
operations = [
|
||||
migrations.RemoveField(
|
||||
model_name='productmodel',
|
||||
name='in_pack_items',
|
||||
),
|
||||
migrations.AddField(
|
||||
model_name='productvariant',
|
||||
name='in_pack_items',
|
||||
field=models.ManyToManyField(blank=True, to='product.inpackitems', verbose_name='ایتم های داخل پک'),
|
||||
),
|
||||
]
|
||||
+48
@@ -0,0 +1,48 @@
|
||||
# Generated by Django 5.1.2 on 2025-02-11 19:19
|
||||
|
||||
from django.db import migrations, models
|
||||
|
||||
|
||||
class Migration(migrations.Migration):
|
||||
|
||||
dependencies = [
|
||||
('product', '0021_remove_productmodel_in_pack_items_and_more'),
|
||||
]
|
||||
|
||||
operations = [
|
||||
migrations.CreateModel(
|
||||
name='ProductImageModel',
|
||||
fields=[
|
||||
('id', models.BigAutoField(auto_created=True, primary_key=True, serialize=False, verbose_name='ID')),
|
||||
('name', models.CharField(max_length=30, verbose_name='نام عکس')),
|
||||
('image', models.ImageField(upload_to='product_images/')),
|
||||
],
|
||||
),
|
||||
migrations.RemoveField(
|
||||
model_name='attributevalue',
|
||||
name='color',
|
||||
),
|
||||
migrations.RemoveField(
|
||||
model_name='attributevalue',
|
||||
name='image',
|
||||
),
|
||||
migrations.RemoveField(
|
||||
model_name='attributevalue',
|
||||
name='video',
|
||||
),
|
||||
migrations.AddField(
|
||||
model_name='productvariant',
|
||||
name='color',
|
||||
field=models.CharField(blank=True, max_length=7, null=True, verbose_name='رنک'),
|
||||
),
|
||||
migrations.AddField(
|
||||
model_name='productvariant',
|
||||
name='video',
|
||||
field=models.FileField(blank=True, null=True, upload_to='product_videos/', verbose_name='ویدیو'),
|
||||
),
|
||||
migrations.AddField(
|
||||
model_name='productvariant',
|
||||
name='images',
|
||||
field=models.ManyToManyField(to='product.productimagemodel', verbose_name='عکس ها'),
|
||||
),
|
||||
]
|
||||
@@ -111,7 +111,6 @@ class ProductModel(models.Model):
|
||||
created_at = models.DateTimeField(auto_now_add=True, verbose_name='زمان ثبت محصول')
|
||||
category = models.ForeignKey(SubCategoryModel, null=True, on_delete=models.SET_NULL, related_name='products', verbose_name='دسته بندی محصول')
|
||||
related_products = models.ManyToManyField('self', blank=True, verbose_name='محصولات مرتبط')
|
||||
in_pack_items = models.ManyToManyField(InPackItems, blank=True, verbose_name='ایتم های داخل پک')
|
||||
|
||||
|
||||
|
||||
@@ -198,15 +197,27 @@ class AttributeType(models.Model):
|
||||
class AttributeValue(models.Model):
|
||||
attribute_type = models.ForeignKey(AttributeType, on_delete=models.CASCADE, blank=True, null=True)
|
||||
value = models.CharField(verbose_name='مقدار نوع اتربیوت', max_length=100, blank=True, null=True)
|
||||
color = models.CharField(verbose_name='رنک', max_length=7, blank=True, null=True)
|
||||
image = models.ImageField(upload_to='product_images/')
|
||||
video = models.FileField(upload_to='product_videos/', blank=True, null=True, verbose_name='ویدیو')
|
||||
class Meta:
|
||||
unique_together = ('attribute_type', 'value')
|
||||
|
||||
def __str__(self):
|
||||
return f"{self.attribute_type.name}: {self.value}"
|
||||
|
||||
|
||||
class ProductImageModel(models.Model):
|
||||
name = models.CharField(max_length=30, verbose_name='نام عکس')
|
||||
image = models.ImageField(upload_to='product_images/')
|
||||
|
||||
def __str__(self):
|
||||
return self.name
|
||||
|
||||
class Meta:
|
||||
verbose_name = 'عکس محصولات'
|
||||
verbose_name_plural = 'عکس های محصولات'
|
||||
|
||||
|
||||
|
||||
|
||||
class ProductVariant(models.Model):
|
||||
product = models.ForeignKey(ProductModel, on_delete=models.CASCADE, related_name='variants', verbose_name='محصول')
|
||||
attributes = models.ManyToManyField(AttributeValue, verbose_name='ویژگیها', related_name='variant')
|
||||
@@ -219,9 +230,13 @@ class ProductVariant(models.Model):
|
||||
('toman', 'تومان'),
|
||||
('derham', 'درهم')
|
||||
)
|
||||
in_pack_items = models.ManyToManyField(InPackItems, blank=True, verbose_name='ایتم های داخل پک')
|
||||
sell = models.IntegerField(default=0, verbose_name='فروش')
|
||||
currency = models.CharField(verbose_name='نوع ارز', max_length=20, choices=currency_type)
|
||||
discount = models.SmallIntegerField(default=0, verbose_name='تخفیف')
|
||||
color = models.CharField(verbose_name='رنک', max_length=7, blank=True, null=True)
|
||||
images = models.ManyToManyField(ProductImageModel, verbose_name='عکس ها')
|
||||
video = models.FileField(upload_to='product_videos/', blank=True, null=True, verbose_name='ویدیو')
|
||||
class Meta:
|
||||
verbose_name = 'تنوع محصول'
|
||||
verbose_name_plural = 'تنوعهای محصول'
|
||||
|
||||
@@ -30,9 +30,24 @@ class AttributeValueSerialzier(serializers.ModelSerializer):
|
||||
model = AttributeValue
|
||||
fields = "__all__"
|
||||
|
||||
|
||||
class InPackItemsSerialzier(serializers.ModelSerializer):
|
||||
class Meta:
|
||||
model = InPackItems
|
||||
fields = '__all__'
|
||||
|
||||
class ProductImageSerailizer(serializers.ModelSerializer):
|
||||
class Meta:
|
||||
model = ProductImageModel
|
||||
fields = '__all__'
|
||||
|
||||
|
||||
|
||||
class ProductVariantSerialzier(serializers.ModelSerializer):
|
||||
attributes = AttributeValueSerialzier(many=True)
|
||||
price = serializers.SerializerMethodField()
|
||||
in_pack_items = InPackItemsSerialzier(many=True)
|
||||
images = ProductImageSerailizer(many=True)
|
||||
class Meta:
|
||||
model = ProductVariant
|
||||
exclude = ('min_price', 'max_price','sell', 'currency', 'product')
|
||||
@@ -42,6 +57,11 @@ class ProductVariantSerialzier(serializers.ModelSerializer):
|
||||
toman_price = obj.get_toman_price(dollor_price=dollor_price)
|
||||
return "{:,.0f} تومان".format(toman_price)
|
||||
|
||||
def __init__(self, *args, **kwargs):
|
||||
super().__init__(*args, **kwargs)
|
||||
view_type = self.context.get('view_type', None)
|
||||
if view_type == 'list':
|
||||
self.fields.pop('in_pack_items', None)
|
||||
|
||||
|
||||
|
||||
@@ -49,11 +69,12 @@ class ProductVariantSerialzier(serializers.ModelSerializer):
|
||||
|
||||
|
||||
class DynamicProductSerializer(serializers.ModelSerializer):
|
||||
variants = ProductVariantSerialzier(many=True)
|
||||
variants = serializers.SerializerMethodField()
|
||||
# variants_colors = serializers.SerializerMethodField()
|
||||
is_new = serializers.SerializerMethodField()
|
||||
related_products = serializers.SerializerMethodField()
|
||||
details = ProductDetailSerializer(many=True, read_only=True)
|
||||
|
||||
def __init__(self, *args, **kwargs):
|
||||
super().__init__(*args, **kwargs)
|
||||
view_type = self.context.get('view_type', 'all')
|
||||
@@ -75,6 +96,8 @@ class DynamicProductSerializer(serializers.ModelSerializer):
|
||||
'chat': ['name', 'description', 'variants']
|
||||
}
|
||||
|
||||
def get_variants(self, obj):
|
||||
return ProductVariantSerialzier(instance=obj.variants.all(), many=True, context=self.context).data
|
||||
|
||||
# def get_variants_colors(self, obj):
|
||||
# varients = obj.variants.all()
|
||||
|
||||
Reference in New Issue
Block a user