2017-04-18 20 views
1

私はかなり新しいdjangoだし、google appsスクリプト(GAS)webappをdjangoに移行しようとしています。django modelformを使って画像をコピー/ペーストする方法は?

私がGoogleのウェブサイトに持っていた機能の1つは、クリップボードからペーストしたイメージをキャプチャしてフォームに送信することでした。これは、フォームで隠しフィールドを介して行われました:

<input type="hidden" name="summaryImage" id='summaryImage' value=''> 

、その後、私は、この非表示のフォームフィールドを移入するために、pasteイベントをキャプチャ

/* Handle paste events */ 
function pasteHandler(e) { 
   if (e.clipboardData) { 
      // Get the items from the clipboard 
      var items = e.clipboardData.items; 
      if (items) { 
         // Loop through all items, looking for any kind of image 
         for (var i = 0; i < items.length; i++) { 
            if (items[i].type.indexOf("image") !== -1) { 
               // We need to represent the image as a file, 
               var blob = items[i].getAsFile(); 
               var URLObj = window.URL || window.webkitURL; 
               var source = URLObj.createObjectURL(blob); 
       var reader = new FileReader(); 
       reader.onload = function(e) { 
       document.getElementById("summaryImage").value= reader.result; 
       } 
       reader.readAsDataURL(blob); 
            } 
      } 
    } 
   } 
} 

上記のフォームをグーグルを通じて提出する際、上に解析することができますサーバー側のGoogleは以下のように、フォームでsummaryImageフィールドからスクリプト(GAS)のアプリ:

var splitBase = form.summaryImage.split(','), 
var type = splitBase[0].split(';')[0].replace('data:',''); 
var byteCharacters = Utilities.base64Decode(splitBase[1]); 
var blob = Utilities.newBlob(byteCharacters, type); 

、ジャンゴでは、私はこれを複製する問題を抱えています。 forms.py

class MyForm(forms.ModelForm): 

    class Meta: 
     model = myModel 
     fields = '__all__' 
     widgets = { 
      'image': forms.HiddenInput() 
     } 
    ... 

... 
image = models.ImageField(blank=True, null=True, verbose_name='Image') 
... 

とHiddenInput(にウィジェットを設定する)とにもペーストを撮影したときに、私はそれを設定します。私はmodels.pyでのImageFieldでモデルを作成しましたこの隠されたイメージフィールド:

document.getElementById("id_image").value= reader.result; 

しかし、私はエラーメッセージ取得し、フォームを送信できませんでした:

(非表示フィールド画像)ファイルが送信されませんでした。フォームの のエンコードタイプを確認してください。

かなり検索しましたが、djangoのクリップボードから貼り付けた画像をキャプチャすることについて何も言及していませんでした。これも実行可能ですか?

+2

htmlには、入力タイプが隠されていてイメージではありません。 Djangoフォームには、貼り付けられたデータを受け入れるためのCharFieldが必要です。フォームのクリーンアンドセーブメソッドでは、その文字列データをファイルオブジェクトに変換し、それを使用してImageFieldにデータを取り込みます。 – allcaps

+0

@allcapsありがとう!!それは動作するように見え、データを文字列としてキャプチャします。 base64で、iVBORw0KGgoAAAANSUhEUgAAABUAAAAWCAYAAAAvg9c4AAAAMUlEQVRIDWP8 //// fwYqAyYqmwc2btRQ6ofqaJiOhimVQ2A0SVE5QBkYGEbDdIiEKQC6hwQozNWIkwAAAABJRU5ErkJggg == –

+0

@allcapsを、私は、画像を保持するために大きなフィールドが必要になります推測し、CharFieldですがMAXLENGTHは十分ではありません。画像/ PNG:データ:これは、このようになります。私はテキストエリアを試してみる。このデータをキャプチャするためのより良い方法/フィールドタイプがありますか? –

答えて

1

@ allcapsの提案のおかげで、私は解決策を見つけました。

は基本的に私は私のモデルでのImageField(画像)を保持し、IDのみid_imageでそれを表示するカスタムウィジェットを割り当てられました。次に、非表示の入力フィールドimage_containerをフォームに追加して貼り付けたデータを受け取ります。フォームの保存機能は、ファイルを作成してImageFieldに保存するためにオーバーライドされます。

class PictureWidget(forms.widgets.Widget): 
    def render(self, name, value, attrs=None): 
     if str(value) == '': 
      html1 = "<img id='id_image' style='display:block' class='rounded float-left d-block'/>" 
     else: 
      html1 = "<img id='id_image' style='display:block' class='rounded float-left d-block' src='" + settings.MEDIA_URL + str(value) + "'/>" 
     return mark_safe(html1) 

class MyForm(forms.ModelForm): 

    image_container = forms.CharField(required=False, widget=forms.HiddenInput()) 
    class Meta: 
     model = MYMODEL 
     fields = '__all__' 
     widgets = { 
      'image': PictureWidget(), 
     } 
    def save(self, commit=True): 
     # check image_container data 
     self.instance.image.delete(False) 
     imgdata = self.cleaned_data['image_container'].split(',') 
     try: 
      ftype = imgdata[0].split(';')[0].split('/')[1] 
      fname = slugify(self.instance.title) 
      self.instance.image.save('path/%s.%s' % (fname, ftype), ContentFile(imgdata[1].decode("base64"))) 
     except: 
      pass 
     return super(MyForm, self).save(commit=commit) 
関連する問題