Создание карты на сайте с адресами магазинов, с использованием API Яндекс.Карт версии 2.х – продолжение

Не так давно я публиковал на своем блоге заметку «Создание карты на сайте с адресами магазинов, с использованием API Яндекс.Карт версии 2.х».

С момента публикации в API Яндекс.Карт появился метод getBounds для автоматического позиционирования карты по коллекции геообъектов.

Мне также задавали вопрос о том, как удалить метки с карты при выборе нового города.

Я подготовил новую версию кода примера вывода адресов магазинов на карту.

Посмотреть пример в работе

Что же нового в коде примера.

В API Яндекс.Карт появился метод getBounds и теперь нет необходимости использовать дополнительный скрипт bounds-collection.js

Удаляем весь код для его использования, строки

$.getScript('bounds-collection.js', function () {
collection = new GeoCollectionBounds();

collection.events.add('boundschange', function (e) {
            map.setBounds(e.get('bounds'));
});

collection.add(placemark);

А ткже не нужные закрывающие скобки }); после строки $(‘#shops’).html(src_res);

Глобальную переменную collection называем myCollection.

Сразу после добавления на карту элементов управления вставляем строку кода

myCollection = new ymaps.GeoObjectCollection();

Создаем новую коллекцию геообъектов.

После создания метки нужно добавить ее в коллекцию.

Для этого в функцию do_search перед строкой

src_res=src_res+'<p>'+sch+'. '+'<a href="#" onClick="return go_to('+json[i].lat+', '+json[i].lon+",'"+json[i].address+"');"+'">'+json[i].address+'</a></p>';

добавляем код

myCollection.add(placemark);

А после добавления всех меток, нужно добавить коллекцию на карту и устанавливаем центр и масштаб карты так, чтобы охватить коллекцию целиком.

За это отвечают строчки

map.geoObjects.add(myCollection);
map.setBounds(myCollection.getBounds());

Нужно также заменить название коллекции в строке

collection.each(function (item) {

в функции go_to на myCollection

myCollection.each(function (item) {

Для того, чтобы удалить предыдущие результаты поиска из нашей коллекции добавляем строку кода

myCollection.removeAll();

сразу после строки

var src_res="<p><strong>результаты поиска: </strong></p>";

Код файла map.html, выводящий карту будет иметь вид:

<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head>
    <title>Магазины М.Видео на карте - API Яндекс.Карт версии 2.х Новая версия</title>
    <meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
 
<script src="http://yandex.st/jquery/1.6.4/jquery.min.js" type="text/javascript"></script>
<script src="http://api-maps.yandex.ru/2.0/?load=package.full&lang=ru-RU" type="text/javascript"></script>
<style>
#shopconteyner{
width: 100%;
}
 
#shops{ float:left;
width: 30%;
}
 
#YMapsID{
margin-left: 40%;
width: 60%;
height: 600px;
}
</style>    
 
<script type="text/javascript">	
	var map;
 
	var myCollection;
 
	ymaps.ready(function () {
    map = new ymaps.Map('YMapsID', {
        center: [56.326944, 44.0075],
        zoom: 15,
        type: 'yandex#map',
        behaviors: ['default', 'scrollZoom']
    });
 
	//Добавляем элементы управления
	 map.controls                
            .add('zoomControl')                
            .add('typeSelector')                
            .add('mapTools');
 
	myCollection = new ymaps.GeoObjectCollection();			
 
	$("select").change(function () {			
	var town = $("#selecttown :selected").val();	
	do_search(town);			
	})
    .change();			
	})
 
function do_search(town){
 
$('#shops').html('');
 
$.getJSON("searcheshop.php", {town: town}, function(json){ 
var src_res="<p><strong>результаты поиска: </strong></p>";
 
myCollection.removeAll();
 
src_res=src_res+'<p><strong>Найдено объектов: '+json.length+'</strong></p>';
 
for (i = 0; i < json.length; i++) {
var sch = i+1;
var placemark = new ymaps.Placemark([json[i].lon,json[i].lat], {
	iconContent: sch,
    balloonContentHeader: '<div style="color:#ff0303;font-weight:bold">'+json[i].address+'</div>',
    balloonContentBody: '<div style="font-size:13px;"><div><strong>Адрес:</strong> '+json[i].address+'<br>'+'<strong>Режим работы:</strong> '+json[i].rrab+'<br></div></div>'   
        }, {
        // Опции
        preset: 'twirl#nightStretchyIcon' // иконка растягивается под контент
        });
myCollection.add(placemark);
src_res=src_res+'<p>'+sch+'. '+'<a href="#" onClick="return go_to('+json[i].lat+', '+json[i].lon+",'"+json[i].address+"');"+'">'+json[i].address+'</a></p>';
}
map.geoObjects.add(myCollection);
map.setBounds(myCollection.getBounds());
 
$('#shops').html(src_res);
 
});
}
 
function go_to(lat,lon,address){
map.setCenter([lon, lat], 16);
 
myCollection.each(function (item) {
    if (item.properties.get('balloonContentHeader') == '<div style="color:#ff0303;font-weight:bold">'+address+'</div>') {
        item.balloon.open();
     }
	});
return false;
}		
 
 
</script>
 
</head>
<body>
<div id="searchform">
<select id="selecttown">
<option value="Екатеринбург">Екатеринбург</option>
<option value="Казань">Казань</option>
<option value="Нижний Новгород">Нижний Новгород</option>
<option value="Пермь">Пермь</option>
<option value="Самара">Самара</option>
<option value="Санкт-Петербург">Санкт-Петербург</option>
</select>
</div>
 
<div id="shopconteyner">
<div id="shops"></div>
<div id="YMapsID"></div>
</div>
</body>
</html>

А остальные файлы мы будем использовать без изменений.

Аналогичным образом изменяем файл примера, использующего ссылки вместо select для выбора городов.

Посмотреть пример в действии

Загрузить архив с новыми файлами примеров

  • Гость: Добрый! Подскажите пожалуйста, есть ли у яндекса или гугла функции определения кратчайшие n расстояниq, между одним адресом и списком адресов. заранее благодарю за ответ.
  • Гость: А если я не выбираю город, а получаю его другим способом как мне изменить конструкцию: $("select").change(function () { var town = $("#selecttown :selected").val(); do_search(town); }) .change();
  • Гость: Разобрался)) удалите...
  • Гость: Подскажите плиз почему не работает следующее: Пытаюсь вывести список предприятий из joomla. Вот ваш измененый скрипт: var map; var myCollection; ymaps.ready(function () { map = new ymaps.Map('YMapsID', { center: [55.43099,37.54541], zoom: 14, type: 'yandex#map', behaviors: ['default', 'scrollZoom'] }); //Добавляем элементы управления map.controls .add('zoomControl') .add('typeSelector') .add('mapTools'); myCollection = new ymaps.GeoObjectCollection(); do_search(); }) function do_search(){ $('#shops').html(''); $.getJSON("searcheshop.php", function(json){ var src_res="<strong>результаты поиска: </strong>"; myCollection.removeAll(); src_res=src_res+'<strong>Найдено объектов: '+json.length+'</strong>'; for (i = 0; i &lt; json.length; i++) { var sch = i+1; var placemark = new ymaps.Placemark([json[i].lon,json[i].lat], { iconContent: sch, balloonContentHeader: &#039;'+json[i].address+'', balloonContentBody: '<strong>Адрес:</strong> '+json[i].address+''+'<strong>Режим работы:</strong> '+json[i].rrab+'' }, { // Опции preset: 'twirl#nightStretchyIcon' // иконка растягивается под контент }); myCollection.add(placemark); src_res=src_res+''+sch+'. '+'<a href="#" rel="nofollow">'+json[i].address+'</a>'; } map.geoObjects.add(myCollection); map.setBounds(myCollection.getBounds()); $('#shops').html(src_res); }); } Вот searcheshop.php: ?php $cat = JRequest::getInt( 'sid' ); //запрос на текущую категорию $query = "select pod_sobipro_object.id, pod_sobipro_object.name, pod_sobipro_field_geo.latitude, pod_sobipro_field_geo.longitude FROM pod_sobipro_object LEFT JOIN pod_sobipro_field_geo ON pod_sobipro_field_geo.sid = pod_sobipro_object.id WHERE pod_sobipro_object.parent = '$cat' ORDER BY name"; $db =&amp; JFactory::getDBO(); $db-&gt;setQuery($query); //$result1 = $db-&gt;query($query); $result1 = $db-&gt;loadAssocList(); if($result1){ foreach ( $result1 as $par1 ) { $addressshop[] = array("id"=&gt;$par1['id'], "name" =&gt; $par1['name'], "lat" =&gt; $par1['longitude'], "lon" =&gt; $par1['latitude']); } } $json = json_encode($addressshop); echo $json; ?&gt; Запрос отрабатывается нормально. Вот такой json получается: [{"id":"1398","name":"BP u041fu043eu0434u043eu043bu044cu0441u043a (u0411u0438 u041fu0438)","lat":"37.555555","lon":"55.428373"},{"id":"694","name":"u0418u043du0442u043eu043f","lat":"37.560691","lon":"55.406048"},{"id":"2359","name":"u041cu043eu0440u0438u043eu043d u0445u043eu043bu0434u0438u043du0433","lat":"37.528109","lon":"55.424843"},{"id":"2358","name":"u041cu043eu0441u0430u0432u0442u043eu0433u0430u0437 u0410u0413u041du041au0421 u0413u0423u041f","lat":"37.542392","lon":"55.40182"}] Но на карту ничего не выводится! Более того даже "найдено объектов" не пишет..
  • Гость: И еще - как сделать название метки ссылкой на запись так, чтобы при нажатии шел переход на соответствующий элемент в каталоге sobi?
  • Гость: Подскажите пожалуйста, вот есть установленный компонент и плагин версии 2. Как применить ваше исправление (дополнение), чтобы указывать корректно адреса? Я в не ламер, но из вашего примера так и непонял ((( что и куда вставлять/удалять. Вот есть скачанные файлы примера, есть установленный компанент-плагин, что дальше? Расскажите немного подробнее. Спасибо.
  • Гость: Дело в том, что для добавления примера в Joomla нужно использовать специальный плагин для вставки кода, см. <a href="http://webmap-blog.ru/yandex-maps/api-yandeks-kart-i-joomla" title="API Яндекс.Карт и Joomla" target="_blank" rel="nofollow">новую заметку</a>
  • Гость: Здравствуйте! Подскажите, пожалуйста, как вместо базы использовать текстовый файл? Спасибо.
  • Гость: Можно исходные данные хранить в виде набора текстовых файлов в формате JSON, подгружать необходимый из них для определенного города. Скоро напишу заметку об этом.
  • Гость: проблема с масштабом карты, когда например по отдельному городу один магазин сделать то объект выводится а карта не видна ибо масштаб очень большой
  • Гость: В API существует параметр для отслеживания доступного уровня масштаба в данной точке - <a href="http://api.yandex.ru/maps/doc/jsapi/2.x/ref/reference/Map.xml#zoomRange" title="zoomRange" target="_blank" rel="nofollow">zoomRange</a>
  • Гость: Добрый день! Подскажите, как можно каждому городу сделать "свой" цвет меток?
  • Гость: Скажите, пожалуйста, как сделать карту 100% по высоте и ширине?
  • Гость: Прописать CSS стили для страницы с картой: html, body { height: 100%; margin: 0; padding: 0; } #map { height: 100%; width: 100%; }
  • Гость: Сделал используя этот код аналогичную карту с гораздо большим кол-вом объектов и вот что заметил: в Опере и Гуглхром все работает как по маслу, и двигается плавно и открываеются балуны коректно а вот в Интернет Эксплорере все работает но очень сильно тормозит и балуны открываются долго, можете объяснить нормально это или есть причина?
  • Гость: Получается много объектов в DOM из-за этого Эсплорер тормозит, в этом случае лучше использовать YMapsML или активные области.
  • Гость: Помогите пожалуйста, что мне нужно сделать, чтобы я мог использовать иконку метки свою вместо яндексовской. к примеру меня есть картинка тут : http://site.ru/icon.png, что изменить в коде, чтобы использовалась моя иконка для метки?
  • Гость: Смотрите примеры из документации: <a href="http://api.yandex.ru/maps/doc/jsapi/2.x/examples/markericonlayout.html" title="Использование собственного значка метки без контента" target="_blank" rel="nofollow">первый</a> и <a href="http://api.yandex.ru/maps/doc/jsapi/2.x/examples/markerlayout-with-content.html" title="Использование собственного значка метки с заданным контентом" target="_blank" rel="nofollow">второй</a>
  • Сергей Угольников: Чтобы использовать свои значки для меток нужно прописать код для своей метки: var myPlacemark = new ymaps.Placemark([55.76, 37.56], {}, { iconImageHref: 'http://site.ru/icon.png', iconImageSize: [30, 42], iconImageOffset: [-3, -42] }); В опции iconImageHref указать URL графического файла значка. При необходимости можно указать опции iconImageSize и iconImageOffset — размер изображения и его сдвиг относительно точки привязки соответственно. Т.е часть кода: var placemark = new ymaps.Placemark([json[i].lon,json[i].lat], { iconContent: sch, balloonContentHeader: '<div style="color:#ff0303;font-weight:bold">'+json[i].address+'</div>', balloonContentBody: '<div style="font-size:13px;"><div><strong>Адрес:</strong> '+json[i].address+'<br>'+'<strong>Режим работы:</strong> '+json[i].rrab+'<br></div></div>' }, { // Опции preset: 'twirl#nightStretchyIcon' // иконка растягивается под контент }); будет иметь вид: var placemark = new ymaps.Placemark([json[i].lon,json[i].lat], { iconContent: sch, balloonContentHeader: '<div style="color:#ff0303;font-weight:bold">'+json[i].address+'</div>', balloonContentBody: '<div style="font-size:13px;"><div><strong>Адрес:</strong> '+json[i].address+'<br>'+'<strong>Режим работы:</strong> '+json[i].rrab+'<br></div></div>' }, { iconImageHref: 'http://site.ru/icon.png', iconImageSize: [30, 42], iconImageOffset: [-3, -42] });
  • Гость: Здравствуйте! Я подумываю поставить карту на сайт, такую же как у Вас на скриншоте. Но практически нет времени разбираться. Вы бы не могли помочь в ее создании за денюжку, или подсказать человека, который сможет? Все аналогично тому, как у Вас показано на скриншоте, только количество меток и групп отличается (100/20) Спасибо!
  • Гость: Сейчас занят к сожалению, напишите мне через недельку подробнее обсудим.
  • Гость: А не подскажите, если не сложно, куда нужно добавлять эти файлы. Сайт на joomla 2.5. 1.Я экспортировал mvideo_shops.sql в БД сайта. 2.В bd.php прописал параметры доступа к БД. 3.Затем, через плагин Sourcerer добавил все файлы из архива и код карты с вашего урока. После сохранения страница, где должна публиковаться карта, становится белой и выводит такую ошибку: Разбор ошибки : Parse error: syntax error, unexpected '&lt;&#039; in /home/webost/kino-v-seti.ru/plugins/system/sourcerer/helper.php(450) : runtime-created function on line 28 Fatal error: Function name must be a string in /home/webost/kino-v-seti.ru/plugins/system/sourcerer/helper.php on line 454
  • Гость: При использовании библиотеки jQuery в Joomla возникает конфликт со встроенной библиотекой mootools, см <a href="http://webmap-blog.ru/yandex-maps/api-yandeks-kart-i-joomla" title="API Яндекс.Карт и Joomla" target="_blank" rel="nofollow">заметку</a> Чуть позже напишу пример использования карты с адресами магазинов для Joomla
  • Nina Sanabria: А когда будет пример для joomla? Ошибок не выводит, но и базу, судя по всему не цепляет. Тк нет меток и при смене города ничего не происходит.
  • Гость: Добрый день, подскажите плз, а как в существующий пример добавить возможность добавлять кривые и области
  • Гость: Залил на хостинг. БД залил, подключил, все правильно, но ничего не выводится на странице: карта грузится, список выпадающий есть, а из базы ничего не выгружается. Залита отдельным html в папку, сайт основной на WP - не может быть конфликта?
  • Гость: Подскажите как сделать что бы город выбирался не из списка фильтра, а автоматически показывалась карта города с магазинами по определению местоположения. В яндексе функция опред-ния местоположения есть. Что бы если пользователь зашел с Казани - видел карту магазинов Казани, пользователь с Самары - карта магазинов Самары, и т.д. Очень нужно!!! Заранее спасибо.
  • Гость: Присоединяюсь к вопросу Евгения. Аналогичная проблема...(
  • Гость: Ни как не могу решить проблему с масштабированием, когда в городе один магазин. здесь уже был ответ что нужно использовать zoomRange, пожалуйста опишите как? Спасибо.
  • Гость: Отвечаю на свой вопрос... думаю люди сталкиваются с этим: Где, map = new ymaps.Map('YMapsID', { center: [55.755773, 37.617761], zoom: 11, type: 'yandex#map', behaviors: ['default', 'scrollZoom'] }); добавить checkZoomRange: true,
  • Гость: &gt;Воффка Не работает у меня checkZoomRange: true, Код: map = new ymaps.Map('YMapsID', { center: [55.7336,37.581559], zoom: 15, type: 'yandex#map', behaviors: ['default', 'scrollZoom'], checkZoomRange: true });
  • Гость: &gt; Igor, вот как у меня map = new ymaps.Map('YMapsID', { center: [55.755773, 37.617761], zoom: 11, type: 'yandex#map', checkZoomRange: true, behaviors: ['default', 'scrollZoom']
  • Гость: Так не работает. Нужно передавать параметр checkZoomRange непосредственно в map.setbounds(). Т.е. строку: map.setBounds(myCollection.getBounds()); заменить на: map.setBounds(myCollection.getBounds(), {checkZoomRange: true});
  • Евгений Попов: Локоничный пример. Но возникла проблема в организации поиска по меткам. Неподскажите как его реализовать?
  • Nina Sanabria: Добрый вечер! Как можно прикрутить доп. селект со станциями метро? в базу добавлено как metro.
  • Alex Erm: а как такие же баблы сделать на google maps?
  • Гость: ААА черт не работает пример ваш!