🗒️

【Nuxt.js】$refsを使ってHTML要素の位置を取得する

2021/04/04に公開

HTML要素の情報を取得

template内で以下のように任意の名前でref属性を付与する。
script内でthis.$refs.<名前>とすることでHTML要素にアクセスできる。

<div ref="sample">
  サンプル
</div>

要素へのアクセスはDOMの生成が完了しているmounted内で行う。
(createdで参照してもundefinedになる。)

export default {
  mounted () {
    const rect = this.$refs.sample.getBoundingClientRect()
    ・・・
  }
}

HTML要素が持つプロパティ

this.$refs.〇〇.getBoundingClientRect()の戻り値は、DOMRectというオブジェクトで以下プロパティを持っています。

  • left
  • top
  • right
  • bottom
  • x
  • y
  • width
  • height

各プロパティに入る情報は以下の通りです。
外の四角はviewport(画面に表示されてる範囲)、中の四角がDOMRectとして取得した要素の範囲です。

スクロールを考慮した要素の位置取得

HTML要素が持つ位置情報はviewportの最上部、最左部からの距離なので、HTMLドキュメント全体の中での正確な位置を取得するためには、今のスクロール量を足して計算する必要があります。
縦方向のスクロール量はwindow.pageYOffset、横方向のスクロール量はwindow.pageXOffsetで取得します。

上記を考慮し、HTMLドキュメント内での要素の絶対位置は以下のように取得する。

const rect = this.$refs.sample.getBoundingClientRect()

// 最上部からの距離
const top = rect.top + window.pageYOffset

// 最左部からの距離
const left = rect.left + window.pageXOffset

HTMLドキュメントの右、下からの距離を取得

HTMLドキュメント全体の高さから、ドキュメント最上部から要素bottomまでの距離を引くことで、最下部から要素下辺までの距離、
HTMLドキュメント全体の幅から、ドキュメント最左部から要素rightまでの距離を引くことで、最右部からの要素右辺までの距離が導き出せる。

const rect = this.$refs.sample.getBoundingClientRect()

// 最下部からの距離
const bottom = document.body.clientHeight - (rect.bottom + window.pageYOffset)

// 最右部からの距離
const right = document.body.clientWidth - (rect.right + window.pageXOffset)

コンポーネントにref属性を付与する

コンポーネントに付与したrefからは、上記のようにHTML要素の情報が取得できません。
コンポーネント内部のタグがHTMLとして出力され、コンポーネントのタグが実際に生成されるわけではないためです。

<MyComponent ref="sample" />

以下のようにコンポーネントの外側にタグを追加して、そこにref属性を設定することで、コンポーネントのHTML要素にアクセスできます。

<div ref="sample">
  <MyComponent />
</div>

Discussion