Help us understand the problem. What is going on with this article?

Vue.Draggable の奇妙な動きを対症療法でなんとかする

初投稿です。よろしくお願いします。

1.環境

Vue.js:2.6.11
Vue.Draggable:2.23.2
Google Chrome

2.問題

趣味でなんとなく Vue.js で Webアプリを作っています。

ドラッグ&ドロップで要素をぴょこぴょこ移動させる機能を作りたいな~と思ってたら、Vue.Draggable というなんとも便利なものが存在しているではありませんか。

さっそくインストールして実装。

なかなかいい感じになってきたな、と思ってたらふと妙な動きをしていることに気付きました。

まずは動画を見てください。

※Google Chrome の場合

test1.gif

下のエリアの要素を少し動かしただけなのに、左上のエリアがなにやら蠢いています。
よくみると、下のエリアの要素を動かしはじめた一瞬、その要素が左上のエリアにワープしています。

なんじゃぁこれは、と公式のサイトを見てみたのですが、公式のサイトのデモアプリでも同じような動きをします。
あ~じゃあダメだな、と思いつつ諦めきれず英語のサイトや中国語のサイトをあさりましたが解決せず…

3.対症療法

ぼ~っとしながら奇妙な動きをするドラッグ&ドロップの操作を繰り返してると、ふと対症療法が浮かんできました。

色々試して気が付いたのは、この現象はcloneイベントの直後に発生しているということです。
そこで、cloneイベントのイベントハンドラに以下の記述を追加しました。

<draggable tag="ul" v-model="left" :group=state @clone="onClone">
    <li v-for="l in left" :key="l.content">
        <div>{{ l.content }}</div>
    </li>
</draggable>
<!-- あと右上エリアの分と下エリアの分-->

data() {
    return {
        state: undefined,
        left: [
            {content: "task1"},
            {content: "task2"},
            {content: "task3"},
            {content: "task4"}
        ],
        //あと右上エリアの分と下エリアの分
    }
},
methods: {
    onClone: function () {
        this.state = null
        setTimeout(this.setGroup, 100)
    },
    setGroup: function () {
        this.state = "move"
    }
}

cloneイベントが発生したらgroup 属性を null にして group 間の移動ができないようにします。
0.1秒くらい待って、group 属性に値をセットしてgroup 間の移動を可能にします。

すると以下の動画のようになります。

test2.gif

奇妙な動きはなくなりました。

また、同一エリア内での要素の移動に関して、動かした要素の二行上の要素が一瞬動くという奇妙な動きをすることもあります。

それもこの対症療法で対応できる気がします。

an_riri88
ゴリゴリのSIerが仕事以外で一人でどこまでWebサービス的なものを作れるか実験中
admin-guild
「Webサービスの運営に必要なあらゆる知見」を共有できる場として作られた、運営者のためのコミュニティです。
https://admin-guild.slack.com
Why not register and get more from Qiita?
  1. We will deliver articles that match you
    By following users and tags, you can catch up information on technical fields that you are interested in as a whole
  2. you can read useful information later efficiently
    By "stocking" the articles you like, you can search right away