Гость
Целевая тема:
Создать новую тему:
Автор:
Форумы / HTML, JavaScript, VBScript, CSS [игнор отключен] [закрыт для гостей] / Как правильно подключать Яндекс-Карты и Гугл-Карты? / 16 сообщений из 16, страница 1 из 1
17.01.2018, 14:54
    #39585860
Alibek B
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Как правильно подключать Яндекс-Карты и Гугл-Карты?
Мне нужно на одной странице использовать обе карты.
По отдельности все работает, вместе не получается.
В конце страницы указываю так:
Код: javascript
1.
2.
3.
4.
<script src="jquery.min.js"></script>
<script async src="https://api-maps.yandex.ru/2.1/?lang=ru_RU"></script>
<script async src="https://maps.googleapis.com/maps/api/js?key=...&callback=initMap"></script>
<script defer src="maps.js"></script>


В скрипте maps.js указан необходимый код, а также инициализация (в функции initMap инициализируются обе карты).
Для Яндекс-Карт используется такой код:
Код: javascript
1.
ymaps.ready(initMap);


Для Гугл-Карт достаточно указанного в параметрах callback=initMap.
Пробовал сделать так:
Код: javascript
1.
2.
3.
$(document).ready(function() {
	ymaps.ready(initMap);
});


Но так не работают Яндекс-Карты, на момент события ready скрипт еще не загружен.
...
Рейтинг: 0 / 0
17.01.2018, 14:58
    #39585861
Areostar
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Как правильно подключать Яндекс-Карты и Гугл-Карты?
Код: javascript
1.
2.
3.
4.
<script src="jquery.min.js"></script>
<script async src="https://api-maps.yandex.ru/2.1/?lang=ru_RU"></script>
<script async src="https://maps.googleapis.com/maps/api/js?key=...&callback=initMap"></script>
<script defer src="maps.js"></script>



Неподелитесь мануалом по яндекс картам?
...
Рейтинг: 0 / 0
17.01.2018, 14:59
    #39585863
Amiri
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Как правильно подключать Яндекс-Карты и Гугл-Карты?
...
Рейтинг: 0 / 0
17.01.2018, 15:02
    #39585864
Amiri
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Как правильно подключать Яндекс-Карты и Гугл-Карты?
Alibek B.,

Для того, чтобы этого избежать.
Напишите код создания карт в одном обработчике.
...
Рейтинг: 0 / 0
17.01.2018, 15:22
    #39585891
Alibek B
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Как правильно подключать Яндекс-Карты и Гугл-Карты?
А когда именно это нужно делать?
Функция initMap как раз и является таким обработчиком, в котором инициализируются обе карты.
Если initMap вызывать по событию ready, то Яндекс-Карты не работают — видимо к моменту построения DOM скрипты еще не инициализированы.
А если вызывать ymaps.ready(initMap), то карты Яндекс работают, но не работают карты Google, видимо из-за асинхронной загрузки скриптов.
...
Рейтинг: 0 / 0
17.01.2018, 15:24
    #39585894
Areostar
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Как правильно подключать Яндекс-Карты и Гугл-Карты?
Areostar,

Спасибо за ссылки!
...
Рейтинг: 0 / 0
17.01.2018, 16:37
    #39585953
Alibek B
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Как правильно подключать Яндекс-Карты и Гугл-Карты?
Вначале у меня был один контейнер для всех карт, в скрипте я при переключении карт его очищал и заново инициализировал. Но в таком способе оказалось несколько затруднений. Поэтому я сделал отдельные контейнеры для каждой карты и переключаю их видимость скриптом:
Код: html
1.
2.
<div id="map-frame-google" class="hidden" style="width: 100%; height: 450px;"></div>
<div id="map-frame-yandex" class="hidden" style="width: 100%; height: 450px;"></div>


Так же я убрал асинхронную загрузку:
Код: html
1.
2.
3.
4.
<script src="https://code.jquery.com/jquery-3.2.1.min.js"></script>
<script src="https://api-maps.yandex.ru/2.1/?lang=ru_RU"></script>
<script src="https://maps.googleapis.com/maps/api/js?key=key"></script>
<script src="maps.js"></script>


Файл maps.js выглядит так (все лишнее убрал):
Код: javascript
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
18.
19.
20.
21.
22.
23.
24.
25.
26.
27.
28.
29.
30.
31.
32.
33.
34.
35.
36.
37.
38.
39.
40.
41.
42.
43.
44.
45.
46.
47.
48.
49.
50.
51.
52.
53.
54.
55.
56.
57.
58.
59.
60.
61.
62.
63.
64.
65.
66.
67.
68.
69.
70.
71.
72.
73.
74.
var maps = {google:null, yandex:null};

function initMap() {
	var $mode = <выясняется текущий режим, google или yandex>;
	$('[id|="map-frame"]').addClass('hidden');
	$('#map-frame-'+$mode).removeClass('hidden');
	switch ($mode)
	{
	case 'google':
		initMapGoogle();
		break;
	case 'yandex':
		ymaps.ready(initMapYandex);
		break;
	}
}

function initMapGoogle() {
	return; // сейчас инициализация карт Google отключена
	if (!maps.google) {
		maps.google = google.maps.Map(document.getElementById('map-frame-google'), {center: {lat:20, lng:30}, zoom: 10});
		setMapGoogle('село Кукуево');
	}
}

function initMapYandex() {
	if (!maps.yandex) {
		maps.yandex = new ymaps.Map('map-frame-yandex', {center: [20, 30], zoom: 10});
		setMapYandex('село Кукуево');
	}
}

function setMap(source) {
	var $mode = <выясняется текущий режим, google или yandex>;
	switch ($mode)
	{
	case 'google':
		setMapGoogle(source);
		break;
	case 'yandex':
		setMapYandex(source);
		break;
	}
}

function setMapGoogle(source) {
}

function setMapYandex(source) {
	maps.yandex.geoObjects.removeAll();
	maps.yandex.geoObjects.add(maps['yandex-base']);
	var multiRoute = new ymaps.multiRouter.MultiRoute({referencePoints: [source, 'Москва']}, {boundsAutoApply:true});
	maps.yandex.geoObjects.add(multiRoute);
	multiRoute.events.once('update', function () {
		var routes = multiRoute.getRoutes();
		for (var i = 0, l = routes.getLength(); i < l; i++) {
			var route = routes.get(i);
			if (!route.properties.get('blocked')) {
				multiRoute.setActiveRoute(route);
				route.balloon.open();
				break;
			}
		}
	});
}

$('#map-citylist a').on('click', function(event){
	event.preventDefault();
	setMap($(this).text());
});

$(document).ready(function() {
	initMap();
});



В таком варианты Яндекс-Карты работают нормально — успешно инициализируются и работает построение маршрута.
Но как только я убираю заглушку-return из функции initMapGoogle, как получаю ошибку jQuery.Deferred exception.

Если поменять порядок подключения скриптов (вначале maps.js, затем Карту Google) и добавить в подключаемый скрипт Гугл-Карт параметр callback=initMap, то получаю другую ошибку: Uncaught TypeError: this.setValues is not a function.

Не подскажите, как сделать правильно?
...
Рейтинг: 0 / 0
17.01.2018, 16:43
    #39585961
Amiri
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Как правильно подключать Яндекс-Карты и Гугл-Карты?
Alibek B.,

я думаю у вас где-то дублируются переменные типа map или иное. проблем быть не должно.
...
Рейтинг: 0 / 0
17.01.2018, 17:07
    #39585971
Alibek B
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Как правильно подключать Яндекс-Карты и Гугл-Карты?
Да, maps используется где-то в коде гугловских карт.
Переименовал maps в maplist, также добавил new при создании карты (new google.maps.Map). И еще убрал опцию map для маркера.
Теперь ошибок в консоли нет, но на карте отсутствует изображение, есть только серый фон и логотип Google.
Из-за чего такое может быть?

В настройках ключа API я указывал адрес сайта, на котором эти карты используются.
И на всякий случай я вообще убрал эти ограничения, но не помогло.
...
Рейтинг: 0 / 0
17.01.2018, 17:28
    #39585990
Alibek B
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Как правильно подключать Яндекс-Карты и Гугл-Карты?
Как-то себя странно Гугл-Карты ведут.
На мобильном устройстве карта рисуется, правда долго.
А десктопе вместо карты серый экран. Но как только включаю панель разработчика, на карте прорисовывается изображение. Правда позиция не такая, какую я указываю в скрипте инициализации, но недалеко от этого места.
Когда я делал встраиваемую карту, проблем не было. На JS я перешел для того, чтобы ускорить отрисовку маршрута при смене пункта отправления (при использовании встраиваемой карты iframe загружался заново), но что-то вообще не работает.
...
Рейтинг: 0 / 0
17.01.2018, 17:36
    #39585993
Amiri
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Как правильно подключать Яндекс-Карты и Гугл-Карты?
Alibek B.,

может кешируется криво.
...
Рейтинг: 0 / 0
17.01.2018, 20:36
    #39586074
Alibek B
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Как правильно подключать Яндекс-Карты и Гугл-Карты?
Есть такой список:
Код: javascript
1.
2.
3.
4.
cities = [
	{'Москва': [55.751574, 37.573856]},
	...
];


На основании этого списка добавляю на карту выпадающих список:
Код: javascript
1.
2.
3.
4.
5.
6.
items = cities.map(function(item, index, list){
	key = Object.keys(item)[0];
	obj = new ymaps.control.ListBoxItem({data: {content: key, center: item[key]}});
	return obj;
});
var lst = new ymaps.control.ListBox({data:{content:'Выбрать город'}, items:items});


Но почему-то в obj оказывается скаляр (значение), а не объект.
Хотя такой код работает нормально:
Код: javascript
1.
2.
3.
4.
items = [
	new ymaps.control.ListBoxItem({data: {content: 'Москва', center: [55.751574, 37.573856]}}),
	...
];


Как нужно правильно использовать ymaps.control.ListBoxItem ?
...
Рейтинг: 0 / 0
17.01.2018, 23:50
    #39586122
Alibek B
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Как правильно подключать Яндекс-Карты и Гугл-Карты?
С Яндексом разобрался.
С Гуглом частично, нужно было добавить триггер на resize ( https://stackoverflow.com/questions/42222130/google-maps-shows-gray-screen-instead-of-map).
...
Рейтинг: 0 / 0
18.01.2018, 00:43
    #39586129
Alibek B
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Как правильно подключать Яндекс-Карты и Гугл-Карты?
Триггер на resize частично помогает, но не всегда.
Карты Google глючат, если контейнер в момент инициализации еще не был виден.
При переключении карт помогает повторная инициализация с небольшой задержкой (400 мс).
Но при загрузке страницы этого недостаточно, потому что карта находится на скрываемой закладке и к моменту загрузки страницы контейнер не виден.

Подскажите, как отловить событие, когда DIV становится видимым?
Я нашел пример с IntersectionObserver, но это на многих браузерах не работает.
Нужно какое-то универсальное решение, которое будет учитывать в том числе и то, что родительский контейнер DIV с картой тоже может быть скрытым.
...
Рейтинг: 0 / 0
18.01.2018, 08:40
    #39586193
Alibek B
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Как правильно подключать Яндекс-Карты и Гугл-Карты?
Судя по всему, определение момента видимости элемента на JS задача нетривиальная.
Универсальный способ только в периодическом опросе по таймеру.
...
Рейтинг: 0 / 0
18.01.2018, 09:30
    #39586220
Alibek B
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Как правильно подключать Яндекс-Карты и Гугл-Карты?
Сделал так:
Код: javascript
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
18.
19.
20.
21.
22.
23.
24.
25.
26.
27.
28.
29.
30.
31.
32.
33.
34.
35.
36.
37.
38.
39.
40.
41.
42.
43.
44.
45.
46.
47.
48.
49.
50.
51.
52.
53.
54.
55.
56.
57.
58.
59.
60.
61.
62.
63.
64.
65.
66.
67.
68.
69.
70.
71.
72.
73.
74.
75.
76.
77.
78.
79.
80.
81.
82.
83.
84.
85.
86.
87.
88.
89.
90.
91.
92.
93.
94.
95.
96.
97.
98.
99.
100.
101.
102.
103.
104.
105.
106.
107.
108.
109.
110.
111.
112.
113.
114.
115.
116.
117.
118.
119.
120.
121.
122.
123.
124.
125.
126.
127.
128.
129.
130.
131.
132.
133.
134.
135.
136.
137.
138.
139.
140.
141.
142.
143.
144.
145.
146.
147.
148.
149.
150.
151.
152.
153.
154.
155.
156.
157.
158.
159.
160.
161.
162.
163.
164.
165.
166.
167.
168.
169.
170.
171.
var maplist = {google:null, yandex:null};
maplist.origins = [
	{'Москва': [50, 30], type: 'столица', area: 'РФ'},
	...
];

function initMap() {
	var $mode = $('#map-mode input:checked').attr('id');
	$mode = $mode.substr(9);
	maplist.mode = $mode;
	$('[id|="map-frame"]').addClass('hidden');
	$('#map-frame-'+$mode).removeClass('hidden');
	if (maplist[$mode]) maplist['refresh-'+$mode] = true;
	maplist['active-frame'] = $('#map-frame-'+maplist.mode);
	var checkRedraw = function (mode,frame) {
		if (frame.is(':visible')) {
			switch (mode)
			{
			case 'google':
				if (maplist.google) google.maps.event.trigger(maplist.google, 'resize');
				break;
			case 'yandex':
				if (maplist.yandex) maplist.yandex.redraw();
				break;
			}
		} else {
			setTimeout(checkRedraw(mode,frame), 250);
		}
	};
	if (maplist['refresh-google']) checkRedraw('google',$('#map-frame-google'));
	if (maplist['refresh-yandex']) checkRedraw('yandex',$('#map-frame-yandex'));
	switch ($mode)
	{
	case 'google':
		maplist['google-frame'] = $('#map-frame-google');
		var checkVisibility = function () {
			var state = maplist['google-frame'].is(':visible');
			if (state) {
				initMapGoogle();
			} else {
				setTimeout(checkVisibility, 250);
			}
		};
		if (!maplist.google) checkVisibility();
		break;
	case 'yandex':
		ymaps.ready(initMapYandex);
		break;
	}
}

function initMapGoogle() {
	if (maplist.google) return;
	var $center = new google.maps.LatLng(43.564393, 41.280583);
	var $options = {zoom: 10, center: $center, mapTypeId: google.maps.MapTypeId.ROADMAP};
	maplist.google = new google.maps.Map(document.getElementById('map-frame-google'), $options);
	searchMapGoogle('село Кукуево');
}

function initMapYandex() {
	if (maplist.yandex) return;
	var ctlControls = ['searchControl','geolocationControl','typeSelector','fullscreenControl','zoomControl'];
	maplist.yandex = new ymaps.Map('map-frame-yandex', {center: [43.564393, 41.280583], zoom: 10, controls: ctlControls});
	var search = maplist.yandex.controls.get('searchControl');
	search.options.set('provider', 'yandex#map');
	search.options.set('kind', 'locality');
	search.options.set('noSelect', false);
	search.options.set('noPlacemark', true);
	search.options.set('noCentering', true);
	search.options.set('placeholderContent', 'Поиск населенного пункта...');
	search.options.set('suppressYandexSearch', true);
	search.options.set('boundedBy', maplist.yandex.getBounds());
	search.events.add('resultselect', function (e) {
		var index = e.get('index');
		var result = search.getResultsArray()[index];
		search.hideResult();
		searchMapYandex(search.getRequestString(), result.geometry.getCoordinates());
	}, this);
	var lstOrigins = maplist.origins.map(function(item, index, list){
		var obj = new ymaps.control.ListBoxItem({options: {type: 'separator'}});
		if (item) {
			var key = Object.keys(item)[0];
			var obj = {content: key, center: item[key]};
			if (item.type) obj.content += ' ('+item.type+')';
			obj = new ymaps.control.ListBoxItem({data: obj, options: {selectOnClick:false}});
		}
		return obj;
	});
	var ctlOrigins = new ymaps.control.ListBox({data:{content:'Выбрать город'}, items:lstOrigins});
	ctlOrigins.events.add('click', function (e) {
		var item = e.get('target');
		if (item != ctlOrigins) {
			searchMapYandex(item.data.get('content'), item.data.get('center'));
			item.getParent().collapse();
		}
	});
	maplist.yandex.controls.add(ctlOrigins);
	searchMapYandex('село Кукуево');
}

function searchMapGoogle(origin, position) {
	var local;
	if (!position)
	{
		for (var i = 0, l = maplist.origins.length; i < l; i++) {
			var item = maplist.origins[i];
			if (!item) continue;
			var name = Object.keys(item)[0];
			if (name == origin)
			{
				position = item[name];
				local = item;
				if (!position)
				{
					if (!item.type) origin = item.type + ' ' + origin;
				}
				break;
			}
		}
	}
}

function searchMapYandex(origin, position) {
	var local;
	if (!position)
	{
		for (var i = 0, l = maplist.origins.length; i < l; i++) {
			var item = maplist.origins[i];
			if (!item) continue;
			var name = Object.keys(item)[0];
			if (name == origin)
			{
				position = item[name];
				local = item;
				if (!position)
				{
					if (!item.type) origin = item.type + ' ' + origin;
				}
				break;
			}
		}
	}
	maplist.yandex.geoObjects.removeAll();
	var multiRoute = new ymaps.multiRouter.MultiRoute({referencePoints: [(position ? position : origin), 'Москва']}, {boundsAutoApply:true});
	maplist.yandex.geoObjects.add(multiRoute);
	multiRoute.events.once('update', function () {
		var routes = multiRoute.getRoutes();
		for (var i = 0, l = routes.getLength(); i < l; i++) {
			var route = routes.get(i);
			if (!route.properties.get('blocked')) {
				multiRoute.setActiveRoute(route);
				route.balloon.open();
				break;
			}
		}
	});
}

// Карты переключаются по нажатию radio-кнопок
$('#map-mode input').on('change', function(event){
	initMap();
});

$(window).resize(function() {
	maplist['refresh-google'] = !$('#map-frame-google').is(':visible')
	maplist['refresh-yandex'] = !$('#map-frame-yandex').is(':visible')
});

$(document).ready(function() {
	initMap();
});


Насколько вижу, все работает во всех режимах (ресайз на скрытой вкладке, долгая загрузка и т.д.). К тому же загрузка скриптов теперь асинхронная.
Буду благодарен за советы по оптимизации и улучшению.
...
Рейтинг: 0 / 0
Форумы / HTML, JavaScript, VBScript, CSS [игнор отключен] [закрыт для гостей] / Как правильно подключать Яндекс-Карты и Гугл-Карты? / 16 сообщений из 16, страница 1 из 1
Найденые пользователи ...
Разблокировать пользователей ...
Читали форум (0):
Пользователи онлайн (0):
x
x
Закрыть


Просмотр
0 / 0
Close
Debug Console [Select Text]