如何在Django表单中显示持仓对象的不可编辑买入价信息
在Django表单中显示不可编辑的股票买入价
下面提供几种实用方案,根据你的需求选择:
方案1:修改模型__str__方法,让下拉选项直接包含买入价
这是最快捷的方式,直接让下拉框的每个选项同时展示股票代码和买入价,不需要改动表单逻辑:
修改Holdings模型的__str__方法:
class Holdings(models.Model): student = models.ForeignKey(Student, on_delete=models.CASCADE) symbol = models.CharField(max_length=10) purchase_price = models.DecimalField(max_digits=10, decimal_places=2) class Meta: verbose_name_plural = "Holdings" ordering = ['symbol'] def __str__(self): return f"{self.symbol} (买入价: ${self.purchase_price})"
修改后,你的下拉选择框会自动显示类似AAPL (买入价: $150.00)的选项,用户提交表单时,后端拿到的依然是正确的Holdings对象,完全不影响原有逻辑。
方案2:添加只读字段单独显示买入价(结合前端JS)
如果希望买入价在下拉框外单独展示,且不可编辑,可以通过添加只读表单字段+前端联动实现:
步骤1:修改表单代码
添加只读的purchase_price字段,同时自定义下拉框Widget,给每个选项带上买入价的data属性:
from django import forms from .models import Holdings class SymbolSelectWidget(forms.Select): def create_option(self, name, value, label, selected, index, subindex=None, attrs=None): option = super().create_option(name, value, label, selected, index, subindex, attrs) # 给每个选项添加data-price属性存储买入价 if value: holding = Holdings.objects.get(pk=value) option['attrs']['data-price'] = holding.purchase_price return option class SellForm(forms.Form): symbol = forms.ModelChoiceField( queryset=None, widget=SymbolSelectWidget(attrs={ 'class': 'form-control', 'autofocus': 'autofocus', 'id': 'symbol-select' }) ) # 添加只读字段用于显示买入价 purchase_price = forms.CharField( widget=forms.TextInput(attrs={ 'class': 'form-control', 'readonly': 'readonly', 'id': 'purchase-price' }) ) def __init__(self, *args, **kwargs): self.request = kwargs.pop('request') super(SellForm, self).__init__(*args, **kwargs) self.fields['symbol'].queryset = Holdings.objects.filter(student=self.request.user.student) # 如果表单有初始选中值,自动填充买入价 if self.initial.get('symbol'): self.initial['purchase_price'] = self.initial['symbol'].purchase_price
步骤2:模板中添加JS联动
在渲染表单的模板里加入JS,让下拉框选中变化时自动更新只读字段的值:
<div class="form-group"> <label>股票代码</label> {{ form.symbol }} </div> <div class="form-group mt-2"> <label>买入价</label> {{ form.purchase_price }} </div> <script> const symbolSelect = document.getElementById('symbol-select'); const priceInput = document.getElementById('purchase-price'); // 初始化显示第一个选项的买入价 if (symbolSelect.options.length > 1) { priceInput.value = symbolSelect.options[1].dataset.price; } // 下拉框切换时更新价格 symbolSelect.addEventListener('change', function() { priceInput.value = this.options[this.selectedIndex].dataset.price; }); </script>
方案3:纯前端显示买入价(无需修改表单字段)
如果买入价仅用于展示,不需要提交到后端,可以直接在模板中通过JS渲染,无需添加额外表单字段:
步骤1:使用自定义Widget(同方案2的SymbolSelectWidget)
确保下拉框的每个选项都带有data-price属性。
步骤2:模板中添加展示区域和JS
<div class="form-group"> <label>股票代码</label> {{ form.symbol }} <div class="mt-2 text-muted"> 当前选中买入价: <span id="price-display"></span> </div> </div> <script> const symbolSelect = document.getElementById('id_symbol'); const priceDisplay = document.getElementById('price-display'); // 初始化显示 if (symbolSelect.options.length > 1) { priceDisplay.textContent = `$${symbolSelect.options[1].dataset.price}`; } // 切换选项时更新显示 symbolSelect.addEventListener('change', function() { priceDisplay.textContent = `$${this.options[this.selectedIndex].dataset.price}`; }); </script>
这种方式更轻量,适合仅需展示的场景。
内容的提问来源于stack exchange,提问作者Jordan Dovey
相关产品推荐
相关产品推荐

