angular-ymaps
Advanced tools
Comparing version 0.0.5 to 0.1.1
@@ -68,7 +68,12 @@ /*global angular*/ | ||
mapBehaviors: ['default'], | ||
mapControls: ['default'], | ||
markerOptions: { | ||
preset: 'islands#darkgreenIcon' | ||
}, | ||
clusterOptions: { | ||
preset: 'islands#darkGreenClusterIcons' | ||
}, | ||
fitMarkers: true, | ||
forMarkersZoomMargin: 40, | ||
fitMarkersZoomMargin: 40, | ||
clusterize: false | ||
}) | ||
@@ -121,8 +126,15 @@ //brought from underscore http://underscorejs.org/#debounce | ||
zoom : $scope.zoom || 0, | ||
behaviors: config.mapBehaviors | ||
behaviors: config.mapBehaviors, | ||
controls: config.mapControls | ||
}); | ||
$scope.markers = new ymaps.GeoObjectCollection({}, config.markerOptions); | ||
self.map.geoObjects.add($scope.markers); | ||
var collection = new ymaps.GeoObjectCollection({}, config.markerOptions); | ||
if(config.clusterize) { | ||
$scope.markers = new ymaps.Clusterer(config.clusterOptions); | ||
collection.add($scope.markers); | ||
} else { | ||
$scope.markers = collection; | ||
} | ||
self.map.geoObjects.add(collection); | ||
if(config.fitMarkers) { | ||
initAutoFit(self.map, $scope.markers, ymaps); | ||
initAutoFit(self.map, collection, ymaps); | ||
} | ||
@@ -191,3 +203,3 @@ var updatingBounds, moving; | ||
}, | ||
link : function ($scope, elm, attr, mapCtrl) { | ||
link: function ($scope, elm, attr, mapCtrl) { | ||
var marker; | ||
@@ -200,7 +212,5 @@ function pickMarker() { | ||
if (marker) { | ||
marker.geometry.setCoordinates(coord); | ||
mapCtrl.removeMarker(marker); | ||
} | ||
else { | ||
marker = mapCtrl.addMarker(coord, angular.extend({iconContent: $scope.index}, $scope.properties), $scope.options); | ||
} | ||
marker = mapCtrl.addMarker(coord, angular.extend({iconContent: $scope.index}, $scope.properties), $scope.options); | ||
} | ||
@@ -207,0 +217,0 @@ |
{ | ||
"name": "angular-ymaps", | ||
"main": "angular-ymaps.js", | ||
"version": "0.0.5", | ||
"version": "0.1.1", | ||
"homepage": "https://github.com/just-boris/angular-ymaps", | ||
@@ -6,0 +6,0 @@ "authors": [ |
@@ -1,2 +0,4 @@ | ||
angular.module('YmapsDemo', ['ymaps']).controller('MapCtrl', function ($scope) { | ||
angular.module('YmapsDemo', ['ymaps']).config(function(ymapsConfig) { | ||
ymapsConfig.clusterize = true; | ||
}).controller('MapCtrl', function ($scope) { | ||
function generateMarkers(tlCorner, brCorner, count) { | ||
@@ -31,2 +33,2 @@ var deltaLat = tlCorner[0] - brCorner[0], | ||
$scope.markers = generateMarkers([57.18, 35.55], [52.43, 40.23], 10); | ||
}); | ||
}); |
@@ -24,3 +24,5 @@ module.exports = function (grunt) { | ||
'color-marker', | ||
'controls', | ||
'markers-array', | ||
'clusterize', | ||
'markers-text', | ||
@@ -129,2 +131,2 @@ 'balloons', | ||
return grunt; | ||
}; | ||
}; |
@@ -5,6 +5,7 @@ { | ||
"scripts": { | ||
"prepublish": "bower install", | ||
"prepare": "bower install", | ||
"dev": "karma start --no-single-run", | ||
"test": "grunt" | ||
}, | ||
"version": "0.0.5", | ||
"version": "0.1.1", | ||
"repository": "git@github.com:just-boris/angular-ymaps.git", | ||
@@ -14,21 +15,20 @@ "dependencies": {}, | ||
"bower": "^1.4.1", | ||
"grunt": "^0.4.5", | ||
"grunt-build-control": "^0.5.0", | ||
"grunt-cli": "^0.1.13", | ||
"grunt-contrib-concat": "^0.5.1", | ||
"grunt-contrib-copy": "^0.8.0", | ||
"grunt-contrib-jshint": "^0.11.2", | ||
"grunt-contrib-uglify": "^0.9.1", | ||
"grunt-karma": "^0.12.0", | ||
"grunt": "^1.0.1", | ||
"grunt-build-control": "^0.7.1", | ||
"grunt-cli": "^1.2.0", | ||
"grunt-contrib-concat": "^1.0.1", | ||
"grunt-contrib-copy": "^1.0.0", | ||
"grunt-contrib-jshint": "^1.1.0", | ||
"grunt-contrib-uglify": "^3.1.0", | ||
"grunt-karma": "^2.0.0", | ||
"jasmine-core": "^2.3.4", | ||
"karma": "^0.13.2", | ||
"karma-chrome-launcher": "^0.2.0", | ||
"karma-firefox-launcher": "^0.1.6", | ||
"karma-html2js-preprocessor": "^0.1.0", | ||
"karma-jasmine": "^0.3.6", | ||
"karma-phantomjs-launcher": "^0.2.0", | ||
"karma": "^1.7.1", | ||
"karma-chrome-launcher": "^2.2.0", | ||
"karma-firefox-launcher": "^1.0.1", | ||
"karma-html2js-preprocessor": "^1.1.0", | ||
"karma-jasmine": "^1.1.0", | ||
"node-markdown": "^0.1.1", | ||
"phantomjs": "^1.9.17", | ||
"phantomjs-prebuilt": "^2.1.15", | ||
"underscore": "^1.8.3" | ||
} | ||
} |
[Angular JS]: http://angularjs.org | ||
[ymaps.GeoObject]: http://api.yandex.ru/maps/doc/jsapi/2.x/ref/reference/GeoObject.xml | ||
[ymaps.GeoObject]: https://tech.yandex.ru/maps/doc/jsapi/2.0/ref/reference/GeoObject-docpage/ | ||
[ymaps.Clusterer]: https://tech.yandex.ru/maps/doc/jsapi/2.0/ref/reference/Clusterer-docpage/ | ||
Angular-ymaps [](https://travis-ci.org/just-boris/angular-ymaps) | ||
@@ -57,9 +59,16 @@ ============= | ||
* **apiUrl**(String) - ссылка для загрузки API карт. Может переопределяться для загрузки другой версии. | ||
По умолчанию загружается `2.0-stable` | ||
* **mapBehaviors**(Array) - возможные поведения карты, массив ключей, которые принимает [ymaps.map.behavior.Manager](http://api.yandex.ru/maps/doc/jsapi/2.x/ref/reference/map.behavior.Manager.xml). | ||
* **apiUrl** (String) - ссылка для загрузки API карт. Может переопределяться для загрузки другой версии. | ||
По умолчанию загружается `2.1-stable` | ||
* **mapBehaviors** (Array) - возможные поведения карты, массив ключей, которые принимает [ymaps.map.behavior.Manager](http://api.yandex.ru/maps/doc/jsapi/2.x/ref/reference/map.behavior.Manager.xml). | ||
Стандартное значение: *['default']* | ||
* **markerOptions**(Object) - опции, передаваемые [ymaps.GeoObject], то есть настройки внешнего вида и поведения маркеров | ||
на карте. Стандартное значение: *{preset: 'twirl#darkgreenIcon'}* | ||
* **fitMarkers**(Boolean) - автоматически подстраивать видимую область и масштаб карты, чтобы было видно все точки на | ||
* **mapControls** (Array) - возможные элементы управления карты, массив ключей, которые принимает [ymaps.map.control.Manager](http://api.yandex.ru/maps/doc/jsapi/2.x/ref/reference/map.control.Manager.xml). | ||
Стандартное значение: *['default']* | ||
* **markerOptions** (Object) - опции, передаваемые [ymaps.GeoObject], то есть настройки внешнего вида и поведения маркеров | ||
на карте. Стандартное значение: *{preset: 'islands#darkgreenIcon'}* | ||
* **clusterize** (Boolean) – объединять ли маркеры в кластеры. По умолчанию *false* | ||
* **clusterOptions** (Object) - опции кластера [ymaps.Clusterer], применяются если включена кластеризация. Стандартное | ||
значение: *{preset: 'islands#darkGreenClusterIcons'}* | ||
* **fitMarkers** (Boolean) - автоматически подстраивать видимую область и масштаб карты, чтобы было видно все точки на | ||
карте. Стандартное значение: *true* | ||
* **fitMarkersZoomMargin** (Boolean) – отступ от границ карты при подстраивании масштаба под маркеры. Стандартное | ||
значение: *40* (px) |
@@ -34,4 +34,3 @@ /*globals jasmine, describe, beforeEach, it, afterEach, expect, angular, module, inject */ | ||
describe('ymap-directive', function() { | ||
var $rootScope, $compile, | ||
scope, ymapsMock, mapMock, geoObjectsMock, placemarkMock; | ||
var scope, ymapsMock, mapMock, geoObjectsMock, placemarkMock; | ||
@@ -83,118 +82,167 @@ function YaEvent(data) { | ||
})); | ||
beforeEach(inject(function(_$rootScope_, _$compile_) { | ||
$rootScope = _$rootScope_; | ||
$compile = _$compile_; | ||
})); | ||
function createElement(html, scopeVal) { | ||
var element = angular.element(html); | ||
scope = $rootScope.$new(); | ||
angular.extend(scope, scopeVal); | ||
$compile(element)(scope); | ||
scope.$apply(); | ||
} | ||
describe('default', function() { | ||
var $rootScope, $compile; | ||
beforeEach(inject(function(_$rootScope_, _$compile_) { | ||
$rootScope = _$rootScope_; | ||
$compile = _$compile_; | ||
})); | ||
function createMap() { | ||
createElement('<yandex-map center="center" zoom="zoom"></yandex-map>', {center: [55.23, 30.22], zoom: 10}); | ||
mapMock.deferred.resolve(); | ||
mapMock.panTo.calls.reset(); | ||
scope.$apply(); | ||
} | ||
function createElement(html, scopeVal) { | ||
var element = angular.element(html); | ||
scope = $rootScope.$new(); | ||
angular.extend(scope, scopeVal); | ||
$compile(element)(scope); | ||
scope.$apply(); | ||
} | ||
it('should create empty map with default center and zoom', function() { | ||
createElement('<yandex-map center="center" zoom="zoom"></yandex-map>'); | ||
var mapConfig = ymapsMock.Map.calls.argsFor(0)[1]; | ||
expect(mapConfig.center).toEqual([0, 0]); | ||
expect(mapConfig.zoom).toBe(0); | ||
}); | ||
function createMap() { | ||
createElement('<yandex-map center="center" zoom="zoom"></yandex-map>', {center: [55.23, 30.22], zoom: 10}); | ||
mapMock.deferred.resolve(); | ||
mapMock.panTo.calls.reset(); | ||
scope.$apply(); | ||
} | ||
//fix issue #4 | ||
it('should work with spaces inside', function() { | ||
createElement('<yandex-map center="center" zoom="zoom"> </yandex-map>'); | ||
}); | ||
it('should create empty map with default center and zoom', function() { | ||
createElement('<yandex-map center="center" zoom="zoom"></yandex-map>'); | ||
var mapConfig = ymapsMock.Map.calls.argsFor(0)[1]; | ||
expect(mapConfig.center).toEqual([0, 0]); | ||
expect(mapConfig.zoom).toBe(0); | ||
}); | ||
it('should create empty map with selected center and zoom', function() { | ||
createMap(); | ||
var mapConfig = ymapsMock.Map.calls.argsFor(0)[1]; | ||
expect(mapConfig.center).toEqual([55.23, 30.22]); | ||
expect(mapConfig.zoom).toBe(10); | ||
}); | ||
//fix issue #4 | ||
it('should work with spaces inside', function() { | ||
createElement('<yandex-map center="center" zoom="zoom"> </yandex-map>'); | ||
}); | ||
it('should change map center when attribute has changed', function() { | ||
createMap(); | ||
mapMock.panTo.calls.reset(); | ||
scope.$apply('center=[54.45, 31.16]'); | ||
expect(mapMock.panTo).toHaveBeenCalledWith([54.45, 31.16]); | ||
}); | ||
it('should create empty map with selected center and zoom', function() { | ||
createMap(); | ||
var mapConfig = ymapsMock.Map.calls.argsFor(0)[1]; | ||
expect(mapConfig.center).toEqual([55.23, 30.22]); | ||
expect(mapConfig.zoom).toBe(10); | ||
}); | ||
it('should change map zoom when attribute has changed', function() { | ||
createMap(); | ||
mapMock.setZoom.calls.reset(); | ||
scope.$apply('zoom=12'); | ||
expect(mapMock.setZoom).toHaveBeenCalledWith(12, {checkZoomRange: true}); | ||
}); | ||
it('should change map center when attribute has changed', function() { | ||
createMap(); | ||
mapMock.panTo.calls.reset(); | ||
scope.$apply('center=[54.45, 31.16]'); | ||
expect(mapMock.panTo).toHaveBeenCalledWith([54.45, 31.16]); | ||
}); | ||
it('should update model values of center and zoom', function() { | ||
createMap(); | ||
var callback = mapMock.events.add.calls.mostRecent().args[1]; | ||
callback(new YaEvent({newCenter: [62.16, 34.56], newZoom: 23})); | ||
expect(scope.center).toEqual([62.16, 34.56]); | ||
expect(scope.zoom).toEqual(23); | ||
}); | ||
it('should change map zoom when attribute has changed', function() { | ||
createMap(); | ||
mapMock.setZoom.calls.reset(); | ||
scope.$apply('zoom=12'); | ||
expect(mapMock.setZoom).toHaveBeenCalledWith(12, {checkZoomRange: true}); | ||
}); | ||
it('should ignore bounds change while center is moving', function() { | ||
createMap(); | ||
scope.center = [45.15, 34.47]; | ||
scope.$apply(); | ||
var callback = mapMock.events.add.calls.mostRecent().args[1]; | ||
callback(new YaEvent({newCenter: [62.16, 34.56], newZoom: 23})); | ||
expect(scope.center).toEqual([45.15, 34.47]); | ||
mapMock.deferred.resolve(); | ||
scope.$apply(); | ||
callback(new YaEvent({newCenter: [62.16, 34.56], newZoom: 23})); | ||
expect(scope.center).toEqual([62.16, 34.56]); | ||
}); | ||
it('should update model values of center and zoom', function() { | ||
createMap(); | ||
var callback = mapMock.events.add.calls.mostRecent().args[1]; | ||
callback(new YaEvent({newCenter: [62.16, 34.56], newZoom: 23})); | ||
expect(scope.center).toEqual([62.16, 34.56]); | ||
expect(scope.zoom).toEqual(23); | ||
}); | ||
it('should add nested markers to map', function() { | ||
createElement( | ||
'<yandex-map center="center" zoom="zoom">' + | ||
'<ymap-marker coordinates="marker1"></ymap-marker>'+ | ||
'<ymap-marker coordinates="marker2" options="options"></ymap-marker>'+ | ||
'</yandex-map>', | ||
{marker1: [55.23, 30.22], marker2: [45.15, 34.47], options: {preset: 'islands#icon', iconColor: '#a5260a'}} | ||
); | ||
expect(ymapsMock.Placemark.calls.argsFor(0)[0]).toEqual([55.23, 30.22]); | ||
expect(ymapsMock.Placemark.calls.argsFor(1)[0]).toEqual([45.15, 34.47]); | ||
expect(ymapsMock.Placemark.calls.argsFor(1)[2]).toEqual({preset: 'islands#icon', iconColor: '#a5260a'}); | ||
expect(geoObjectsMock.add.calls.count()).toBe(2); | ||
}); | ||
it('should ignore bounds change while center is moving', function() { | ||
createMap(); | ||
scope.center = [45.15, 34.47]; | ||
scope.$apply(); | ||
var callback = mapMock.events.add.calls.mostRecent().args[1]; | ||
callback(new YaEvent({newCenter: [62.16, 34.56], newZoom: 23})); | ||
expect(scope.center).toEqual([45.15, 34.47]); | ||
mapMock.deferred.resolve(); | ||
scope.$apply(); | ||
callback(new YaEvent({newCenter: [62.16, 34.56], newZoom: 23})); | ||
expect(scope.center).toEqual([62.16, 34.56]); | ||
}); | ||
describe('auto fit', function() { | ||
it('should listen collection bounds', function() { | ||
createMap(); | ||
expect(geoObjectsMock.events.add).toHaveBeenCalledWith('boundschange', jasmine.any(Function)); | ||
it('should add nested markers to map', function() { | ||
createElement( | ||
'<yandex-map center="center" zoom="zoom">' + | ||
'<ymap-marker coordinates="marker1"></ymap-marker>'+ | ||
'<ymap-marker coordinates="marker2" options="options"></ymap-marker>'+ | ||
'</yandex-map>', | ||
{marker1: [55.23, 30.22], marker2: [45.15, 34.47], options: {preset: 'islands#icon', iconColor: '#a5260a'}} | ||
); | ||
expect(ymapsMock.Placemark.calls.argsFor(0)[0]).toEqual([55.23, 30.22]); | ||
expect(ymapsMock.Placemark.calls.argsFor(1)[0]).toEqual([45.15, 34.47]); | ||
expect(ymapsMock.Placemark.calls.argsFor(1)[2]).toEqual({preset: 'islands#icon', iconColor: '#a5260a'}); | ||
expect(geoObjectsMock.add.calls.count()).toBe(2); | ||
}); | ||
it('should update map bounds after event', function() { | ||
createMap(); | ||
geoObjectsMock.getBounds.and.returnValue([[55.23, 30.22], [58.35, 36.18]]); | ||
var callback = geoObjectsMock.events.add.calls.argsFor(0)[1]; | ||
callback(); | ||
expect(mapMock.setBounds).toHaveBeenCalled(); | ||
describe('auto fit', function() { | ||
it('should listen collection bounds', function() { | ||
createMap(); | ||
expect(geoObjectsMock.events.add).toHaveBeenCalledWith('boundschange', jasmine.any(Function)); | ||
}); | ||
it('should update map bounds after event', function() { | ||
createMap(); | ||
geoObjectsMock.getBounds.and.returnValue([[55.23, 30.22], [58.35, 36.18]]); | ||
var callback = geoObjectsMock.events.add.calls.argsFor(0)[1]; | ||
callback(); | ||
expect(mapMock.setBounds).toHaveBeenCalledWith([[ 55.23, 30.22 ], [ 58.35, 36.18 ]], { checkZoomRange: true, zoomMargin: 40 }); | ||
}); | ||
it('should not update map bounds when collection is empty', function() { | ||
createMap(); | ||
geoObjectsMock.getLength.and.returnValue(0); | ||
var callback = geoObjectsMock.events.add.calls.argsFor(0)[1]; | ||
callback(new YaEvent({ | ||
newBounds: [[55.23, 30.22], [58.35, 36.18]] | ||
})); | ||
expect(mapMock.setBounds).not.toHaveBeenCalled(); | ||
}); | ||
}); | ||
it('should not update map bounds when collection is empty', function() { | ||
createMap(); | ||
geoObjectsMock.getLength.and.returnValue(0); | ||
var callback = geoObjectsMock.events.add.calls.argsFor(0)[1]; | ||
callback(new YaEvent({ | ||
newBounds: [[55.23, 30.22], [58.35, 36.18]] | ||
})); | ||
expect(mapMock.setBounds).not.toHaveBeenCalled(); | ||
describe('with ngRepeat', function() { | ||
beforeEach(function() { | ||
createElement( | ||
'<yandex-map center="center" zoom="zoom">' + | ||
'<ymap-marker coordinates="marker" index="$index+1" ng-repeat="marker in markers"></ymap-marker>'+ | ||
'</yandex-map>', | ||
{markers: [[55.23, 30.22], [45.15, 34.47]]} | ||
); | ||
}); | ||
it('should add array of markers', function() { | ||
expect(geoObjectsMock.add.calls.count()).toBe(2); | ||
expect(ymapsMock.Placemark).toHaveBeenCalledWith([55.23, 30.22], jasmine.any(Object), undefined); | ||
expect(ymapsMock.Placemark).toHaveBeenCalledWith([45.15, 34.47], jasmine.any(Object), undefined); | ||
}); | ||
it('should add new markers', function() { | ||
scope.markers.push([40.42, 45.30]); | ||
scope.$apply(); | ||
expect(geoObjectsMock.add.calls.count()).toBe(3); | ||
expect(ymapsMock.Placemark).toHaveBeenCalledWith([40.42, 45.30], jasmine.any(Object), undefined); | ||
}); | ||
it('should remove markers and update indexes', function() { | ||
scope.markers.splice(0, 1); | ||
scope.$apply(); | ||
expect(geoObjectsMock.remove.calls.count()).toBe(1); | ||
expect(placemarkMock.properties.set.calls.count()).toBe(1); | ||
expect(placemarkMock.properties.set).toHaveBeenCalledWith('iconContent', 1); | ||
}); | ||
}); | ||
}); | ||
}) | ||
describe('with ngRepeat', function() { | ||
beforeEach(function() { | ||
createElement( | ||
describe('clusterize', function() { | ||
beforeEach(module(function(ymapsConfig) { | ||
ymapsConfig.clusterize = true; | ||
})); | ||
beforeEach(inject(function($compile, $rootScope, ymapsLoader) { | ||
this.cluserer = jasmine.createSpyObj('clusterer', ['add', 'remove']) | ||
ymapsMock.Clusterer = jasmine.createSpy('Clusterer').and.returnValue(this.cluserer); | ||
this.createElement = function(html, scopeVal) { | ||
var element = angular.element(html); | ||
scope = $rootScope.$new(); | ||
angular.extend(scope, scopeVal); | ||
$compile(element)(scope); | ||
scope.$apply(); | ||
return scope; | ||
}; | ||
this.createElement( | ||
'<yandex-map center="center" zoom="zoom">' + | ||
@@ -205,26 +253,9 @@ '<ymap-marker coordinates="marker" index="$index+1" ng-repeat="marker in markers"></ymap-marker>'+ | ||
); | ||
}); | ||
})); | ||
it('should add array of markers', function() { | ||
expect(geoObjectsMock.add.calls.count()).toBe(2); | ||
expect(ymapsMock.Placemark).toHaveBeenCalledWith([55.23, 30.22], jasmine.any(Object), undefined); | ||
expect(ymapsMock.Placemark).toHaveBeenCalledWith([45.15, 34.47], jasmine.any(Object), undefined); | ||
it('should instantiate cluster instance', function() { | ||
expect(ymapsMock.Clusterer).toHaveBeenCalled(); | ||
}); | ||
it('should add new markers', function() { | ||
scope.markers.push([40.42, 45.30]); | ||
scope.$apply(); | ||
expect(geoObjectsMock.add.calls.count()).toBe(3); | ||
expect(ymapsMock.Placemark).toHaveBeenCalledWith([40.42, 45.30], jasmine.any(Object), undefined); | ||
}); | ||
it('should remove markers and update indexes', function() { | ||
scope.markers.splice(0, 1); | ||
scope.$apply(); | ||
expect(geoObjectsMock.remove.calls.count()).toBe(1); | ||
expect(placemarkMock.properties.set.calls.count()).toBe(1); | ||
expect(placemarkMock.properties.set).toHaveBeenCalledWith('iconContent', 1); | ||
}); | ||
}); | ||
}); | ||
}); |
Sorry, the diff of this file is not supported yet
64309
18
46
1026
74