2009-05-25 1 views
2

私はビューからフォームに初期値を設定する方法を知っています。しかし、ジェネリック・ビューにフォームに初期値を設定させるにはどうすればいいですか?私は、一般的なビューのラッパービューを書くことができますが、私はまだフォームオブジェクトのインスタンス化へのアクセス権がありません。Djangoの一般的なビューに初期値のフォームを使用させるには?

私が達成しようとしている具体的な目標は、create_objectジェネリックビューを使用して、ユーザーに新しいオブジェクトを作成させることです。しかし、オブジェクト 'user'のフィールドを現在ログインしているユーザーに設定したいのですが、これはrequest.userとしてしかアクセスできません。どのようにフォームはこのフィールドを持つように初期化できますか?

編集:私は__new__に出くわしました。これはデフォルトの引数で独自のコンストラクタを呼び出すことができますか?

多くのありがとうございます。

+0

私は本当にこの目的を理解していませんが、template_nameとextra_content変数を見ましたか? しかし、真剣にHTMLページ/フォームを書いて、これを行う一般的な方法について狂ったラウンドを考えようとしないでください。特定の値(ユーザーのような)をフォームに設定する必要がある場合は、すでに非常に特殊なケースについてプログラミングしています。 – drozzy

答えて

4

残念ながら、Djangoのcreate_object総称ビューではこの動作を達成できません。あなたは自分で書く必要があります。しかし、これはむしろ単純です。

オフを開始するには、次のような、新しいフォームクラスを作成する必要があります。

from django.shortcuts import render_to_response 
from django.template import RequestContext 
from django.http import HttpResponseRedirect 
from django.contrib.auth.decorators import login_required 

@login_required 
def create_mymodel(request): 
    if request.method == 'POST': 
     # Get data from form 
     form = MyForm(request.POST) 
     # If the form is valid, create a new object and redirect to it. 
     if form.is_valid(): 
      newObject = form.save() 
      return HttpResponseRedirect(newObject.get_absolute_url()) 
    else: 
     # Fill in the field with the current user by default 
     form = MyForm(initial={'user': request.user}) 
    # Render our template 
    return render_to_response('path/to/template.html', 
     {'form': form}, 
     context_instance=RequestContext(request)) 
+0

ありがとうございます。私はこれについてすでに知っていましたが、一般的なビューは初期値ではうまくいかないほど魅力的です。 –

+0

私は同意します:一般的なビューは素晴らしいですが、デフォルトを設定したい場合、それは悪夢です。私はCarl Meyerのポストに全面的に同意します。 –

3

はあなたがこれを行うことができます:

from django import forms 
class MyForm(forms.ModelForm): 
    class Meta: 
     model = MyModel # model has a user field 

は、その後、あなたは、このようなビューを作成することができるだろうフォームクラスを動的に構築して一般的なビューに渡すことによって一般的なビューラッパーを作成しますが、それはおそらく病気より悪いでしょう。あなた自身の見解を書いて、thisが着陸するのを熱心に待ってください。

0

汎用ビューのすべての機能を使用する場合は、オリジナルをテンプレートとして使用して新しい汎用ビューを作成できます。

例:

def create_object_with_initial(request, model=None, template_name=None, 
    template_loader=loader, extra_context=None, post_save_redirect=None, 
    login_required=False, context_processors=None, form_class=None, initial=None): 

if extra_context is None: extra_context = {} 
if login_required and not request.user.is_authenticated(): 
    return redirect_to_login(request.path) 

model, form_class = get_model_and_form_class(model, form_class) 
if request.method == 'POST': 
    form = form_class(request.POST, request.FILES) 
    if form.is_valid(): 
     new_object = form.save() 

     msg = ugettext("The %(verbose_name)s was created successfully.") %\ 
           {"verbose_name": model._meta.verbose_name} 
     messages.success(request, msg, fail_silently=True) 
     return redirect(post_save_redirect, new_object) 
else: 
    print "creating", form_class, " with initial data ", initial 
    form = form_class(initial=initial) 

# Create the template, context, response 
if not template_name: 
    template_name = "%s/%s_form.html" % (model._meta.app_label, model._meta.object_name.lower()) 
t = template_loader.get_template(template_name) 
c = RequestContext(request, { 
    'form': form, 
}, context_processors) 
apply_extra_context(extra_context, c) 
return HttpResponse(t.render(c)) 

これは、初期データを組み込むために変更ライン3と21のみで/site-packages/django/views/generic/create_update.pyからコピーされます。ご想像のとおり

そして、それを使用する:

object_info = { 
'model': YourModel, 
'initial': {'data' : 'Initial Value'}, 
'template_name': 'template.html' 
} 

url(r'^path/$', 
    login_required(create_object_with_initial), 
    object_info, 
    name='url_name'), 

動作する必要があること。

関連する問題