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

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

ただいまの
回答率

89.13%

javascript 直近のクリックイベントの内容のみ反映したい

解決済

回答 2

投稿

  • 評価
  • クリップ 1
  • VIEW 223

t.togashi

score 22

前提・実現したいこと

ruby on railsのアプリにおいて、Google Maps APIを使用しています。
マップをクリックすると、クリックしたポイントの緯度・経度情報を取得した上で
・緯度経度情報を入力フォームの該当欄へ出力
・マップ上にマーカーが表示される
仕様を目指しています。

発生している問題・エラーメッセージ

マップ上にマーカーを表示することはできたのですが、クリックする毎にマーカーが生成され、複数のマーカーが表示される状態となってしまいます。
マップ上には、直近のクリックによるマーカー1つのみが表示されるようにしたいです。

該当のソースコード

new.html.slim

.page-title 被害の新規登録

= form_with model: @damage, local: true do |f|
  = render 'layouts/error_messages', model: f.object
  .form-group
  = f.label :title, '題名'
  = f.text_field :title, class: 'form-control'
  .form-group
  = f.label :place, '場所'
  = f.text_field :place, class: 'form-control'
  .form-group
  = f.label :latitude, '緯度'
  = f.text_field :latitude, class: 'form-control', id: 'latitude'
  .form-group
  = f.label :longitude, '経度'
  = f.text_field :longitude, class: 'form-control', id: 'longitude'
  button.mt-2.mr-3 onclick="geoFindMe()" type="button"  緯度・経度情報を取得
  = link_to 'Google Mapで探す', 'https://www.google.co.jp/maps', target: '_blank', class: 'googlemap'
  .form-group
  = f.label :description, '内容'
  = f.text_area :description, rows: 10, class: 'form-control'
  .form-group
  = f.label :amount, '被害額(円)'
  = f.text_field :amount, class: 'form-control'
  .form-group
  = f.label :image, '写真'
  = f.file_field :image, class: 'form-control'
  = f.submit class: 'btn btn-primary mt-3'


#map.mb-5.mt-5
javascript:
  // APIライブラリの読み込みが終わったら実行する関数を指定
  function initMap() {
  // idがmapのdiv要素オブジェクトを取得
    var target = document.getElementById('map');
    // 中央に表示する座標(羽黒町役場)
    var center = {lat: 38.719072,lng: 139.901329}

    // マップを描画
    map = new google.maps.Map(
      // 描画する領域のオブジェクトを指定
      target, {
      // 描画に関するオプション
      center: center,
      zoom: 13
      }
    );

    // クリックイベント
    map.addListener('click', function(e){
      getClickLatLng(e.latLng);
    });

    // イベントの内容
    function getClickLatLng(lat_lng){
      // 緯度・経度情報を取得
      var lat = lat_lng.lat();
      var lng = lat_lng.lng();

      // 緯度・経度情報を、views/damages/new.html.slimの緯度・経度欄へ入力
      document.getElementById( "latitude" ).value = lat ;
      document.getElementById( "longitude" ).value = lng ;

      // マーカーの設置
      marker = new google.maps.Marker({
        // 表示オプション
        position: new google.maps.LatLng(lat, lng),
        map: map,
        icon: "http://maps.google.com/mapfiles/ms/micons/blue-dot.png"
      });
    }
  }


script async="" defer="defer" src="https://maps.googleapis.com/maps/api/js?key=AIzaSyDD8_DF2AUAtXfZVcQYFUi3T3AslQKAXaw&callback=initMap"

試したこと・参考にした情報

http://seto-abe.hatenablog.com/entry/2017/01/07/015535
このサイトと同様のコードとしたつもりなのですが、挙動がサイトに掲載のものと異なっております。
この要因と、解決方法をご教示いただけますと助かります。

他に参考にした情報
http://www.webdesignleaves.com/pr/plugins/googlemap_01.html

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

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

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

    クリップを取り消します

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

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

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

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

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

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

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

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

    質問の評価を下げる

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

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

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

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

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

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

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

    詳細な説明はこちら

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

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

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

回答 2

check解決した方法

0

#map.mb-5.mt-5
javascript:
  // APIライブラリの読み込みが終わったら実行する関数を指定
  function initMap() {
  // idがmapのdiv要素オブジェクトを取得
    var target = document.getElementById('map');
    // 中央に表示する座標
    var center = {lat: 38.719072,lng: 139.901329}

    // マップを描画
    map = new google.maps.Map(
      // 描画する領域のオブジェクトを指定
      target, {
      // 描画に関するオプション
      center: center,
      zoom: 13
      }
    );

    // マーカーの定義
    var marker = new google.maps.Marker({
      // 表示オプション(positionの中身は空)
      position: new google.maps.LatLng(),
      map: map,
      icon: "http://maps.google.com/mapfiles/ms/micons/blue-dot.png"
    });

    // クリックイベント
    map.addListener('click', function(e){
      getClickLatLng(e.latLng);
    });

    // イベントの内容
    function getClickLatLng(lat_lng){
      // 緯度・経度情報を取得
      var lat = lat_lng.lat();
      var lng = lat_lng.lng();

      // 緯度・経度情報を、views/damages/new.html.slimの緯度・経度欄へ入力
      document.getElementById( "latitude" ).value = lat ;
      document.getElementById( "longitude" ).value = lng ;

      // マーカーの表示の削除
      marker.setMap(null);

      // マーカーの位置情報を更新
      marker.position = new google.maps.LatLng(lat, lng);

      // マーカーの表示
      marker.setMap(map);

    }
  }

投稿

  • 回答の評価を上げる

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

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

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

  • 回答の評価を下げる

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

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

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

0

marker変数をグローバルな場所に取っておいて、
次のマーカーを追加する前に削除すれば良いのではないでしょうか?
https://www.javadrive.jp/google-maps-javascript/gmarker/index4.html

投稿

  • 回答の評価を上げる

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

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

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

  • 回答の評価を下げる

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

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

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

  • 2019/09/19 16:23

    ご教示くださりありがとうございます。
    ご紹介いただいたページを拝見し、以下のコードに修正したのですが、クリックしてもマーカーが表示されなくなりました。

    ```
    .page-title 被害の新規登録

    = form_with model: @damage, local: true do |f|
    = render 'layouts/error_messages', model: f.object
    .form-group
    = f.label :title, '題名'
    = f.text_field :title, class: 'form-control'
    .form-group
    = f.label :place, '場所'
    = f.text_field :place, class: 'form-control'
    .form-group
    = f.label :latitude, '緯度'
    = f.text_field :latitude, class: 'form-control', id: 'latitude'
    .form-group
    = f.label :longitude, '経度'
    = f.text_field :longitude, class: 'form-control', id: 'longitude'
    button.mt-2.mr-3 onclick="geoFindMe()" type="button" 緯度・経度情報を取得
    = link_to 'Google Mapで探す', 'https://www.google.co.jp/maps', target: '_blank', class: 'googlemap'
    .form-group
    = f.label :description, '内容'
    = f.text_area :description, rows: 10, class: 'form-control'
    .form-group
    = f.label :amount, '被害額(円)'
    = f.text_field :amount, class: 'form-control'
    .form-group
    = f.label :image, '写真'
    = f.file_field :image, class: 'form-control'
    = f.submit class: 'btn btn-primary mt-3'


    #map.mb-5.mt-5
    javascript:
    var marker;
    // APIライブラリの読み込みが終わったら実行する関数を指定
    function initMap() {
    // idがmapのdiv要素オブジェクトを取得
    var target = document.getElementById('map');
    // 中央に表示する座標(羽黒町役場)
    var center = {lat: 38.719072,lng: 139.901329}

    // マップを描画
    map = new google.maps.Map(
    // 描画する領域のオブジェクトを指定
    target, {
    // 描画に関するオプション
    center: center,
    zoom: 13
    }
    );

    // クリックイベント
    map.addListener('click', function(e){
    getClickLatLng(e.latLng);
    });

    // イベントの内容
    function getClickLatLng(lat_lng){
    // 緯度・経度情報を取得
    var lat = lat_lng.lat();
    var lng = lat_lng.lng();

    // 緯度・経度情報を、views/damages/new.html.slimの緯度・経度欄へ入力
    document.getElementById( "latitude" ).value = lat ;
    document.getElementById( "longitude" ).value = lng ;

    // マーカーの削除
    marker.setMap(null);

    // マーカーの作成
    var marker = new google.maps.Marker({
    // 表示オプション
    position: new google.maps.LatLng(lat, lng),
    map: map,
    icon: "http://maps.google.com/mapfiles/ms/micons/blue-dot.png"
    });
    marker.setMap(map);
    }
    }
    ```

    私の認識が誤っており、コードの修正方法が適切で無いのでしょうか。

    キャンセル

  • 2019/09/19 16:26

    var が要らないのではないでしょうか?

    var marker = new google.maps.Marker({

    marker = new google.maps.Marker({

    キャンセル

  • 2019/09/19 16:38

    varを削除したのですが、クリックしてもマーカーが表示されない状態です。

    キャンセル

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

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