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

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

ただいまの
回答率

87.59%

UIをドラッグする方法について。

解決済

回答 1

投稿

  • 評価
  • クリップ 1
  • VIEW 4,849

score 352

 前提・実現したいこと

UIのドラッグを実装する方法は何が最適でしょうか?
また、Event SystemとEvent Triggerはそれぞれ別の実装方法なのでしょうか?

 試したこと

Event Systemに関しては、このようなサイトを見つけました。

using UnityEngine.EventSystems;
public class TestDrag : MonoBehaviour, IBeginDragHandler, IDragHandler, IEndDragHandler
{


このように、using UnityEngine.EventSystems;を宣言して、IBeginDragHandler, IDragHandler, IEndDragHandler
を継承しなければならないと認識しています。

Event Triggerに関しては、このようなサイトを見つけました。
このサイトを見る限り、特にusing宣言や継承するクラスはなさそうなのですが、
Event Triggerに関して、別のサイトを見てみると、
using UnityEngine.EventSystems;を宣言して、EventTriggerクラスを継承しています。

いろいろやり方があって、差異は何なのか?(それとも旧式と新方式の違いなのか?)、メリット、デメリット等あるのか、
わからない状態です。

わからないことをまとめると、

・そもそもEvent SystemとEvent Triggerは別の実装法かどうか?
・Event Triggerで実装する場合、EventTriggerクラスを継承しなきゃいけないのかどうか?
・UIのドラッグの最適(簡単)な実装はどれか?
・Event SystemとEvent Triggerを比較した場合、それぞれのメリット、デメリットは何なのか?


等です。
ご教授のほどお願いします。

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

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

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

    クリップを取り消します

  • 良い質問の評価を上げる

    以下のような質問は評価を上げましょう

    • 質問内容が明確
    • 自分も答えを知りたい
    • 質問者以外のユーザにも役立つ

    評価が高い質問は、TOPページの「注目」タブのフィードに表示されやすくなります。

    質問の評価を上げたことを取り消します

  • 評価を下げられる数の上限に達しました

    評価を下げることができません

    • 1日5回まで評価を下げられます
    • 1日に1ユーザに対して2回まで評価を下げられます

    質問の評価を下げる

    teratailでは下記のような質問を「具体的に困っていることがない質問」、「サイトポリシーに違反する質問」と定義し、推奨していません。

    • プログラミングに関係のない質問
    • やってほしいことだけを記載した丸投げの質問
    • 問題・課題が含まれていない質問
    • 意図的に内容が抹消された質問
    • 過去に投稿した質問と同じ内容の質問
    • 広告と受け取られるような投稿

    評価が下がると、TOPページの「アクティブ」「注目」タブのフィードに表示されにくくなります。

    質問の評価を下げたことを取り消します

    この機能は開放されていません

    評価を下げる条件を満たしてません

    評価を下げる理由を選択してください

    詳細な説明はこちら

    上記に当てはまらず、質問内容が明確になっていない質問には「情報の追加・修正依頼」機能からコメントをしてください。

    質問の評価を下げる機能の利用条件

    この機能を利用するためには、以下の事項を行う必要があります。

回答 1

checkベストアンサー

+1

機能説明

Event System
ユーザーの入力を監視しイベントを伝える役割を果たします。

Event Trigger
Inspector上からアタッチできるコンポーネントです。Event Systemの様々なイベントを受け取る受信機の役割を果たします。Hierarchy上から手動でイベントをアタッチする他にスクリプト上からEvent Triggerを参照し実装することもできます。

IxxxxHandler
クリックやドラッグなど様々なインターフェイスが存在します。スクリプトから実装することで動作します。この場合Event Triggerは必要ありません。

Event Systemのイベントを受け取る為の条件

[送信側]
・Hierarchy上にEvent Systemがある。
・uGUI以外で使いたい場合はPhysics Raycasterをカメラにアタッチする。2Dと3Dがあるので注意

[受信側]
・uGUIの場合、Raycast TargetがオンになったuGUIオブジェクト(Image、Textなど)
・uGUI以外の場合、Clliderがアタッチされている。

Event Trigger、IxxxxHandlerの選び方

スクリプトで書きたい派の方はIxxxxHandlerを。Inspector上から手動でアタッチしたい派の方はEvent Triggerをアタッチし該当スクリプトをアタッチすると良いと思います。それ以外に、ひとつのオブジェクトに対してイベントを動的に切り替えたい時などはEvent Triggerをアタッチし、スクリプトで切り替えるといいと思います。

IxxxxHandlerをuGUIのImageに対して実装するサンプル

Imageをドラッグする最小コードです。下記のコードをAssets以下に保存してuGUIのImageにアタッチすることで動作します。

using UnityEngine;
using UnityEngine.UI;
using UnityEngine.EventSystems;

[RequireComponent(typeof(Image))]
public class DraggableImg : MonoBehaviour, IDragHandler
{
    RectTransform Tr;

    void Awake()
    {
        Tr = GetComponent<RectTransform>();
    }

    public void OnDrag(PointerEventData eventData)
    {
        Move(eventData.position);
    }

    void Move(Vector3 pos)
    {
        Tr.position = pos;
    }
}

知っておくと便利なこと

Event SystemのDrag Threshold
どのタイミングからドラッグがスタートするかを決めることができます。ドラッグに対しての感度みたいなものです。数値が低いほど感度が高くなります。例えば、1つのボタンがクリックできる克つ移動できるとします。感度が高いほどドラッグとして見なされやすくなるので、ユーザーが少しもドラッグせずクリックしなければクリックイベントが発火しないなどの設定ができます。

オブジェクトの重なり順
Event Systemは重なり順を考慮してくれます。例えばuGUIのButtonより前にImageがある場合、Buttonにイベントが伝達されず反応しなくなります。これをうまく利用するとユーザーの動作をコントロールしやすくなります。

動くuGUI要素は結構な負荷に
Event Systemとは関係ないですが、uGUIのすべての要素は画面に対して相対的に配置されます。Imageなどを動かす場合すべての要素が再計算されるので結構な負荷になります。対策としてはCanvasをもう一つ用意しそこで動かす方法や、動くものはuGUIを使わないという選択肢もあります。内容にもよりますが重くて動きが悪い場合はご検討ください。

Unity上で使う座標の扱いを覚える
uGUIを扱う上で座標の種類を知っておくと便利です。

【Unity】【uGUI】Screenの座標とWorld(3D)座標の変換について
http://tsubakit1.hateblo.jp/entry/2016/03/01/020510

投稿

編集

  • 回答の評価を上げる

    以下のような回答は評価を上げましょう

    • 正しい回答
    • わかりやすい回答
    • ためになる回答

    評価が高い回答ほどページの上位に表示されます。

  • 回答の評価を下げる

    下記のような回答は推奨されていません。

    • 間違っている回答
    • 質問の回答になっていない投稿
    • スパムや攻撃的な表現を用いた投稿

    評価を下げる際はその理由を明確に伝え、適切な回答に修正してもらいましょう。

  • 2019/03/17 11:42

    ご回答ありがとうございます。
    なるほど、非推奨というわけではないのですね。

    ドラッグ処理のご提示ありがとうございます。
    勉強させていただきます。

    現在の疑問点が全て解決しました。
    大変遅くなってしまった返信にも関わらず、ご丁寧にご教示いただき、本当にありがとうございました。

    キャンセル

  • 2019/03/17 15:29

    解決できてよかったです。

    Unityはどんどん機能が新しくなります。
    改善が難しいものは新しく作り直すことも多いです。
    そのひとつがuGUIです。

    余談ですが、uGUIはNGUIというプラグインの作者との共同開発で完成しました。
    https://assetstore.unity.com/packages/tools/gui/ngui-next-gen-ui-2413

    そして、2018にはUIElementsがリリースされました。HTML+CSSのようなスクリプトからレイアウトできるものです。ランタイムで利用できるのはまだ先の話なので今は流し読み程度で良いと思いますが、その中で
    新しいクリックイベント「UnityEngine.UIElements.Button.clickable.clicked」が登場しました。

    https://docs.unity3d.com/2019.1/Documentation/ScriptReference/UIElements.Button.html

    UIElementsの開発がうまくいってメジャーバージョンがリリースされれば
    来年には上記 + UIElements系イベントを意識する必要が出てくると思います。

    参考
    https://qiita.com/enrike3/items/286977f46d842e4a90e5

    キャンセル

  • 2019/03/17 16:23

    ご回答ありがとうございます。
    UIElementsというものがリリースされていたのですね、知りませんでした。
    リンク先拝見しました。勉強になります。
    今後は、UIElementsの動向に関してもチェックしていきたいと思います。
    ありがとうございます。

    キャンセル

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

  • ただいまの回答率 87.59%
  • 質問をまとめることで、思考を整理して素早く解決
  • テンプレート機能で、簡単に質問をまとめられる

関連した質問

同じタグがついた質問を見る