質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

新規登録して質問してみよう
ただいま回答率
85.48%
Vue.js

Vue.jsは、Webアプリケーションのインターフェースを構築するためのオープンソースJavaScriptフレームワークです。

HTML5

HTML5 (Hyper Text Markup Language、バージョン 5)は、マークアップ言語であるHTMLの第5版です。

Laravel

LaravelとはTaylor Otwellによって開発された、オープンソースなPHPフレームワークです。Laravelはシンプルで表現的なシンタックスを持ち合わせており、ウェブアプリケーション開発の手助けをしてくれます。

イベントハンドラ

マウスのクリックなどの特定の事象(イベント)が発生した時に実行される処理のことをイベントハンドラと呼びます。

Q&A

解決済

2回答

610閲覧

htmlをビューにappendする際に要素の中に@changeもしくはv-on:を追加したい。

tenlife

総合スコア70

Vue.js

Vue.jsは、Webアプリケーションのインターフェースを構築するためのオープンソースJavaScriptフレームワークです。

HTML5

HTML5 (Hyper Text Markup Language、バージョン 5)は、マークアップ言語であるHTMLの第5版です。

Laravel

LaravelとはTaylor Otwellによって開発された、オープンソースなPHPフレームワークです。Laravelはシンプルで表現的なシンタックスを持ち合わせており、ウェブアプリケーション開発の手助けをしてくれます。

イベントハンドラ

マウスのクリックなどの特定の事象(イベント)が発生した時に実行される処理のことをイベントハンドラと呼びます。

0グッド

0クリップ

投稿2020/07/06 22:11

laravelで画像の複数枚投稿を実装しています。

解決したいこと: 新しく作るhtml要素に@changeもしくはv-onをつける。

現状: html要素として表示されてしまう。発火しない。

現在は写真を追加した際に新しいinput要素を作るようにしています。
そのイベントの発火でvue.jsの@changeを使用しています。
しかし、新しく追加するinput要素に@change をうまく付与することが出来ません。
削除の部分も同様です。

<div class="form-group" id="image"> <label for="photo">写真</label> <input type="file" name="src" @change='onFile'> </div> <script src="https://code.jquery.com/jquery-3.5.1.js"></script> <script src="https://cdn.jsdelivr.net/npm/vue@2.6.11"></script> <script> new Vue({ el: '#image', data: { photos: [], fileIndex: [1,2,3] }, methods: { buildinput(index) { let html = `<div data-index="${index}" class="js-file_group"> <input type="file" name="src[${index}]" @change='onFile'> <div class="js-remove" @change='delete_image'>削除</div> </div>` return html; }, onFile(e) { this.photos = e.target.files $('#image').append(this.buildinput(this.fileIndex[0])) }, delete_image(){ console.log('テスト') } } }) </script>

書き方の問題な気がするのですが、正しい記述方法が見つけられませんでした。

どなたか知恵を貸していただけないでしょうか?
よろしくお願いします。

laravel6.18
vue 2.6.11

気になる質問をクリップする

クリップした質問は、後からいつでもMYページで確認できます。

またクリップした質問に回答があった際、通知やメールを受け取ることができます。

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

zushi0905

2020/07/07 02:11

$('#image').append(this.buildinput(this.fileIndex[0])) ↑この書き方ってjQueryじゃないですかね?
tenlife

2020/07/07 06:08 編集

ご指摘ありがとうございます。 templateで用意して、v-htmlで出すという流れで認識あっていますでしょか? https://qiita.com/Yorinton/items/a0144c34e4edb0777493#15props%E3%81%AB%E6%B8%A1%E3%81%95%E3%82%8C%E3%81%9F%E3%83%87%E3%83%BC%E3%82%BF%E3%82%92templatemethodsupdated%E7%AD%89%E3%81%A7%E4%BD%BF%E3%81%86 引数等は上記のサイトのようなイメージでしょうか? 引数等の渡し方で参考になるようなサイトをご存知であれば教えていただけますでしょうか?
zushi0905

2020/07/07 08:53

templateを用意してというか、html部分がもうtemplateなんで。。。 v-htmlというか双方向データバインディングでphotosをvueオブジェクトの中に持たせて、あとはレンダリングはライフサイクルに委ねてレンダリング走らせればいいだけです。 簡単にいうと、jQueryで実装する形だとデータを取得して整形して出力するのに対して、Vueは出力はもともと決めてあって、データを格納する変数に入れてあげるだけって感じです。 引数はjqueryと同じでイベントとして使っているメソッドは引数にイベントオブジェクトを渡され、普通のメソッドとして定義しているものはphpと同じような関数です。
tenlife

2020/07/08 02:34

返信ありがとうございます。 提示していただいたやり方と全く同じではないかもしれませんが、双方向データバインディング考え方参考にさせていただきました。 <div class="form-group"> <div> <h2>Select an image</h2> <input type="file" @change="onFileChange"> </div> <div v-if="images"> <ol> @{{images}} <li v-for="(image, index) in images"> <h5>@{{image.name}}</h5> <img :src="image.thumbnail" style="width: 100px; height: 100px;" /> <input type="hidden" v-model="image.name"> <div @click="edit(index)">Edit image</div> <div @click="remove(index)">Remove image</div> </li> </ol> </div> </div> data() { return { images: [] } }, methods: { onFileChange(e) { let files = e.target.files this.createImage(files[0]) }, createImage(file) { let obj = {}; const reader = new FileReader(); reader.onload = (e) => { obj.thumbnail = e.target.result; obj.name = file.name this.images.push(obj) };       reader.readAsDataURL(file); },
guest

回答2

0

vueとjQueryは共存させることは可能ですがこの書き方だとダメですね。
photos をv-forでループさせる形にしてjQueryを外すべきです。

投稿2020/07/07 13:44

mikkame

総合スコア5036

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

tenlife

2020/07/08 02:38

提示された方向で作成し直したところ、photosに格納することができました。 ありがとうございました!
guest

0

自己解決

下記のような流れでimagesに格納することができました。

photosからimagesに変更されています。

<div class="form-group"> <div> <h2>Select an image</h2> <input type="file" @change="onFileChange"> </div> <div v-if="images"> <ol> <li v-for="(image, index) in images"> <h5>@{{image.name}}</h5> <img :src="image.thumbnail" style="width: 100px; height: 100px;" /> <input type="hidden" v-model="image.name"> <div @click="edit(index)">Edit image</div> <div @click="remove(index)">Remove image</div> </li> </ol> </div> </div>
       data() { return { images: [] } }, methods: { onFileChange(e) { let files = e.target.files this.createImage(files[0]) }, createImage(file) { let obj = {}; const reader = new FileReader(); reader.onload = (e) => { obj.thumbnail = e.target.result; obj.name = file.name this.images.push(obj) }; reader.readAsDataURL(file); },

投稿2020/07/08 02:42

tenlife

総合スコア70

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

15分調べてもわからないことは
teratailで質問しよう!

ただいまの回答率
85.48%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問