アプリ版:「スタンプのみでお礼する」機能のリリースについて

住所から座標を取得し、マーカーを設置
情報ウインドウを設定したいのですが、想定している動きをしません
動かすと
1回目→3回目→1回目→3回目→2回目
といった順番でalertが表示されます
原因はclientGeocoder.getLatLng辺りじゃないかと思っているんですが、これを順番通りに動かすにはどのようにすればよいでしょうか

var map;
var shopName;
var address;
var tel;
function changeFont(input) {
if (GBrowserIsCompatible()) {
//住所名取得
var point = document.getElementById('{!$Component.top.ad}').value.split(',');
//地図を配置するオブジェクト取得
map = new GMap2(document.getElementById('map'));
//拡大・縮小を行えるようにする
map.enableScrollWheelZoom();
//ジオコード
var clientGeocoder = new GClientGeocoder();
//マーカー設定
for (var i = 0; i < point.length; i++) {
//shopName = shop[i];
address = point[i];
//tel = telpho[i];
alert("1回目 = " + address);
clientGeocoder.getLatLng(point[i], shoMap);
alert("3回目 = " + address);
}
}
}

function shoMap(point) {
//中心設定
map.setCenter(point, 8);
//マーカー
var marker = new GMarker(point);
map.addOverlay(marker);
alert("2回目 = " + address);
GEvent.addListener(marker, "click", function() {marker.openInfoWindowHtml("店名:" + shopName + "<br/>住所:" + address + "<br/>TEL:" + tel);});
}

A 回答 (4件)

こうすればうまくいきますね。

↓サンプルです。応用してね、、
※全角空白は半角空白にしてね...

<div id="map" style="width:800px;height:600px;border:2px solid black;"></div>
<script type="text/javascript">
var map;
window.onload = function () {
  if (GBrowserIsCompatible()) {
   map = new GMap2(document.getElementById("map"));
   map.setCenter(new GLatLng(35.83050952932199,139.7885262966156), 12);
   map.addControl(new GMapTypeControl());
  var custom_map = new GMapType([G_PHYSICAL_MAP.getTileLayers()[0],
               G_HYBRID_MAP.getTileLayers()[1]],
               G_NORMAL_MAP.getProjection(),
              "地図+地形");
   map.addMapType(custom_map);
   map.addControl(new GLargeMapControl());
   map.addControl(new GScaleControl(),new GControlPosition(G_ANCHOR_BOTTOM_RIGHT, new GSize(10,15)));
   new GKeyboardHandler(map);

   hoge();

  }
}
function hoge(){
 var clientGeocoder = new GClientGeocoder();
 var point = ["埼玉県大宮市","埼玉県所沢市","埼玉県春日部市"];
 var shopName = ["大宮店","所沢店","春日部店"];
 var address = [];
 var tel = ["110","119","105"];
 for (var i = 0; i < point.length; i++) {
  address[i] = point[i];
  clientGeocoder.getLatLng(point[i],(function(shopName,tel,address){
   return function(point){
   map.setCenter(point,8);
   var marker = new GMarker(point);
   map.addOverlay(marker);
   GEvent.addListener(marker,"click",function(){
    marker.openInfoWindowHtml("店名:"+shopName+"<br/>住所:"+address+"<br/>TEL:"+tel);
   });
   }
  })(shopName[i],tel[i],address[i]));
 }
}
</script>
    • good
    • 0
この回答へのお礼

回答が遅れました、申し訳ありません
ご提示いただいたソースを参考にしたところ、無事実装が完了しました
ありがとうございます

お礼日時:2010/11/15 09:22

情報ウインドウの内容が全て同じになってしまいます



=>全容が見えないので、function changeFont()がどのタイミングで実行されるのか
わからないので、あえて書きませんでしたが、提示されてる分のロジックは何か不足
してます。

var point = document.getElementById('{!$Component.top.ad}').value.split(',');
point配列にはそれぞれの住所が入るんですよね。

var shopName;
var address;
var tel;

 これらも、pointの要素に、対応する変数をどこかでセットしてるんですか?
さもなきゃ一緒になるのは当然です。
セットしてたとしても、コールバック関数には直接渡せないんで、クロージャ
みたいにすれば出来そう(検証してみます)ですが、
最初に書いたようにGClientGeocoder.getLatLng()はループ処理にはむいてません。
HTTPジオコーダー(RESTインターフェース:GET送信)を使った方がよいんですけど、javascriptからだと、クロスドメインアクセスの問題を解決する必要があります。

 ジオコーディングサービスはGoogleMapsAPI以外だと、YahooMapAPIが代表選手で、

http://developer.yahoo.co.jp/webapi/map/openloca …

 他に

http://newspat.csis.u-tokyo.ac.jp/geocode/

もあります。
    • good
    • 0
この回答へのお礼

>対応する変数をどこかでセットしてるんですか
↓ループ内でセットしています shopNameなどはテスト中の為コメントアウトしています
address = point[i];

>コールバック関数には直接渡せないんで
shoMapのことですよね?メンバ変数でも渡せないんでしょうか(引数でってことですかね?)

>最初に書いたようにGClientGeocoder.getLatLng()はループ処理にはむいてません。
HTTPジオコーダーだと制限はないんでしょうか?
補足ですがこのシステムが動作しているサーバーで、リクエスト数(?)を制限しているようです
yahooAPI等に連続で投げると10数回程度でエラーを確認しました

>http://newspat.csis.u-tokyo.ac.jp/geocode/
こちらのサイトに関しては使い方がよくわかりませんでした
一括変換出来れば非常に楽なんですけどね

お礼日時:2010/11/12 09:18

もう一点、気がついた点


ご提示のコードのように、ループ処理で連続して、
GClientGeocoder()を使うと、かなりの確立で失敗します。
2秒~3秒のインターバルで使うと、確実です。
(確か1日当たり数千件しか許されてなかったようです。)
(※有償サービスのAPIは大丈夫みたいです)

連続してジオコーディングすると、

 ステータスコード:620 G_GEO_TOO_MANY_QUERIES

が返され、pointはnullになります。検索不能の場合もふまえ
このへんのハンドリングも必要です。
    • good
    • 0
この回答へのお礼

>1日当たり数千件しか許されてなかったようです
それは知りませんでした
しかし今回のコレに関しては個人的なものですので問題ないと思います(公開予定もありません)
仮に公開する場合は有償APIというものを使用することになると思います

GClientGeocoder()などを使用せずに緯度経度を出せればよいんですが、Webサービスを使わない限り難しいと思いますし

お礼日時:2010/11/11 13:06

 clientGeocoder.getLatLng(point[i], shoMap);


の結果(shopMapの実行)は非同期にレスポンスされます。

 場所によって、検索結果を返す時間がことなるので当然です。

どうしても、順番にやりたかったら、一工夫する必要がありますが、
何故、順番にやる必要があるんでしょうか?
    • good
    • 0
この回答へのお礼

成程、こう書くと非同期になるんですね
>何故、順番にやる必要があるんでしょうか?
現状住所から座標を出して複数マーカーを設置したまでは良かったんですが
情報ウインドウの内容が全て同じになってしまいます

ですのでalertの順番通り動かせれば解決するものと考えていました

お礼日時:2010/11/11 12:01

お探しのQ&Aが見つからない時は、教えて!gooで質問しましょう!