knockout.google.maps example

by kougiland

HTML

<script src="http://maps.googleapis.com/maps/api/js?sensor=false&amp;extension=.js"></script>
<script src="https://rawgithub.com/manuel-guilbault/knockout.google.maps/master/dist/knockout.google.maps-0.1.0.debug.js"></script>
<div>
    <fieldset>
        <legend>Locations</legend>
        <button data-bind="click: newPin">New random location</button>
        <select size="1" data-bind="visible: pins().length, options: pins, optionsText: function(pin) { return '[' + pin.position().lat().toFixed(2) + ', ' + pin.position().lng().toFixed(2) + '] ' + pin.title(); }, value: selectedPin"></select>
        <div data-bind="with: selectedPin">
            <input type="text" data-bind="value: title, valueUpdate: 'afterkeydown'" />
            <button data-bind="click: function() { $parent.removePin($data); }">Remove</button>
        </div>
    </fieldset>
</div>
<div data-bind="map: $data" style="width:500px;height:300px;">
    <div data-bind="marker: currentLocation"></div>
    <div data-bind="mapItems: pins">
        <div data-bind="marker: $data">
            <div data-bind="infoWindow: { anchor: $marker, visible: hintVisible }">
                <p data-bind="text: title"></p>
            </div>
        </div>
    </div>
</div>
<div>
    <span>
        Center: [<span data-bind="text: center().lat().toFixed(4)"></span>, <span data-bind="text: center().lng().toFixed(4)"></span>]
    </span>
    <span>
        Zoom: <span data-bind="text: zoom"></span>
    </span>
    <span data-bind="if: bounds">
        Bounds: [<span data-bind="text: bounds().getSouthWest().lat().toFixed(4)"></span>, <span data-bind="text: bounds().getSouthWest().lng().toFixed(4)"></span>]
        to [<span data-bind="text: bounds().getNorthEast().lat().toFixed(4)"></span>, <span data-bind="text: bounds().getNorthEast().lng().toFixed(4)"></span>]
    </span>
    <span data-bind="with: currentLocation">
        <span data-bind="if: visible">
            Current location: [<span data-bind="text:...

CSS

.gm-style-iw p {
    margin:0;
}

JavaScript

function randomLatitude() {
    return Math.floor(Math.random() * 180) - 90;
}

function randomLongitude() {
    return Math.floor(Math.random() * 360) - 180;
}

function Pin(owner) {
    this.latitude = ko.observable(randomLatitude());
    this.longitude = ko.observable(randomLongitude());
    
    this.title = ko.observable('');
    this.animation = ko.observable(google.maps.Animation.DROP);
    this.clickable = ko.observable(true);
    this.cursor = ko.observable(null);
    this.icon = ko.observable(null);
    this.raiseOnDrag = ko.observable(true);
    this.shadow = ko.observable(null);
    this.draggable = ko.observable(true);
    this.flat = ko.observable(false);
    this.visible = ko.observable(true);
    
    this.position = ko.computed({
        read: function () {
            return new google.maps.LatLng(this.latitude(), this.longitude());
        },
        write: function (value) {
            this.latitude(value.lat());
            this.longitude(value.lng());
        },
        owner: this
    });
    
    this.hintVisible = ko.observable(false);
    this.click = function () {
        owner.selectedPin(this);
    }
}

function ViewModel() {
    
    function createCurrentLocation(owner) {
        var currentLocation = new Pin(owner);
        currentLocation.visible(false);
        currentLocation.title('Current location');
        currentLocation.draggable(false);
        currentLocation.clickable(false);
        currentLocation.icon('http://www.google.com/mapmaker/mapfiles/marker-k.png');
        return currentLocation;
    }
    
    this.center = ko.observable(new google.maps.LatLng(48.8567, 2.3508));
    this.panCenter = ko.observable(true);
    this.zoom = ko.observable(8);
    this.mapTypeId = ko.observable(google.maps.MapTypeId.ROADMAP);
    this.bounds = ko.observable();
    this.panBounds = ko.observable(true);
    
    this.pins = ko.observableArray([]);
    this.selectedPin = ko.observable(null);
    
    var pinIndex = 1;
   ...