2013-08-25 134 views
0

我有一個模型與許多字段,它通過一個表與布爾值鏈接的字段。Django ManyToMany字段使用通過關係值

我在不同的場景中得到了這個,讓用戶作爲主要模型,興趣作爲多對多的字段和user_interest模型作爲貫穿模型,在user_interest內部我有一個布爾字段,我希望用戶在選擇每個字段時指定他的許多很多值,

目前我堅持試圖找到一個適當的表單接口,以滿足我的需要,目前我正在使用MultipleSelect小部件,它只顯示感興趣的選擇,是否有任何示例字段控制會允許我選擇興趣並指定布爾字段的值?如果不是,我的情況下最佳做法是什麼?

最好的問候,用代碼樣本

class Interest(models.Model): 
    name = models.CharField(_('Name'), max_length=200,) 


class UserInterest(models.Model): 
    interest = models.ForeignKey(Interest,) 
    user = models.ForeignKey(getattr(settings, 'AUTH_USER_MODEL'),) 
    join_mail_list = models.BooleanField(default=False) 

class User(models.Model): 
    name = models.CharField(max_length=100) 
    interest = models.ManyToManyField(Interest, through='UserInterest', related_name='user_interest') 

現在基於上述模型

更新的問題,當我嘗試創建用戶模型的ModelForm,我會得到利益多選場是完全正確。但是,就我而言,如果希望爲特定的興趣join_mail_list,我希望表單爲每個興趣收集用戶興趣+。請指教?

回答

0

這個問題是一種普遍的,但我會說,因爲它是一個布爾字段,而不是一個多選字段,所以對於「我感興趣的東西......」(真)和一個是因爲「我對...沒有興趣......」(錯誤)。這兩個字段都會從相同的項目列表中多選,但分離允許用戶應用布爾字段而不會發現。另外,我強烈推薦jQuery UI自動完成,看起來就像這裏的最佳選擇。

更新答案:

所以看到你的代碼可以幫助清楚一些事情。我會這樣做的方式就像我首先建議的那樣,但是稍微調整一下。

爲每個'興趣'設置一個時事通訊複選框是笨拙的,因爲它需要用戶兩次檢查'興趣' - 一次是因爲他對它感興趣,一次是因爲他想收到關於它的電子郵件。因此,您必須自動假定用戶想讓收到他感興趣的主題的電子郵件,但是如果他們願意,可以讓他們阻止它。考慮到這一點,您需要構建兩個長文本輸入,並使用標記系統(here's a good one,這裏是some more)實現這兩個輸入。第一個輸入是「我感興趣」,第二個輸入是「我想收到關於...的電子郵件」。然後你用jQuery添加一個事件列表器,確保添加到第一個輸入的每個標記都會自動添加到第二個標記中。然後,如果用戶不想爲特定主題(或全部主題)獲取電子郵件,他可以輕鬆將其從第二個輸入中取出(這對第一個輸入沒有任何影響)。

舉一個例子,here's a jsfiddle顯示瞭如何使用選擇的jQuery庫進行操作。我使用了國家和航運,因爲我在所選圖書館網站上有一個預先製作的清單,所以我只是從那裏複製它。正如你所看到的,這是一個非常簡單的jQuery代碼,您可以輕鬆地applicate任何其他標記系統(和許多感謝精細勞爾·華雷斯誰helped me work that out自己):

$(".chosen-select").chosen({disable_search_threshold: 10}); 
$('#countries').on('change', function(e) { 
    var selected = $(this).val(); 
    $.each(selected, function(index, value) { 
     $('#shipping option[value="'+value+'"]:first').prop('selected',true); 
    }); 
    $(".chosen-select").trigger('chosen:updated'); 
}); 
+0

我剛剛更新了我的問題與示例代碼,我希望它會進一步澄清我的問題 –

+0

更新我的答案,希望它有幫助。如果你想要的代碼示例只是要求=] – yuvi

0

我就假設你想要一個旁邊有一個複選框的所有興趣列表。

假設這些模型:

class Ressource(models.Model): 
    name = models.CharField(max_length=255) 

class Ressource2Village(models.Model): 
    ressource = models.ForeignKey(Ressource) 
    village = models.ForeignKey(Village) 
    amount = models.FloatField() 

class Village(MapObject): 
    name = models.CharField(max_length=255) 

這種形式:

class Ressoure2VilllageForm(forms.Form): 
    name = forms.CharField() 
    # you would use a BooleanField 
    value = forms.IntegerField() 

現在,您可以創建一個表單集(https://docs.djangoproject.com/en/1.5/topics/forms/formsets/):

from django.forms.formsets import formset_factory 
r2v_formset = formset_factory(Ressoure2VilllageForm) 

# use boolean for your case, if you want to edit these values later use n2m to initialize value 
# [{'name': r2v.ressource.name, 'value': r2v.value} for r2v in your_village.ressource2village.all()] 
init_values = [{'name': r.name, 'value': 0} for r in Ressource.objects.all()] 
r2v_formset = r2v_formset(initial=init_values) 

哪個在你的模板會給你:

<label for="id_form-0-name">Name:</label><input type="text" name="form-0-name" value="Kohle" id="id_form-0-name"> 
<label for="id_form-0-value">Value:</label><input type="text" name="form-0-value" value="0" id="id_form-0-value"> 
<label for="id_form-1-name">Name:</label><input type="text" name="form-1-name" value="Eisenerz" id="id_form-1-name"> 
<label for="id_form-1-value">Value:</label><input type="text" name="form-1-value" value="0" id="id_form-1-value"> 
<label for="id_form-2-name">Name:</label><input type="text" name="form-2-name" value="Golderz" id="id_form-2-name"> 
[...] 

與特定用戶的關聯可以在處理過程中考慮到他的身份驗證細節。

顯示,驗證和處理這應該是非常簡單的,隨時提出後續問題。