简体   繁体   中英

Show tooltip on hover of custom marker

I have the following Google Map test: http://jsfiddle.net/gM6Z6/

As you can see it gets your position and then shows it on the map using three markers.

What I want to do is when a user hovers over any of the three markers, I want to show the following tooltip NEXT to the marker avatar:

var tooltipOptions={
    marker:marker,
    content: "You're here!",
    cssClass:'tooltip'
};
var tooltip = new Tooltip(tooltipOptions);

I'm not sure how to best do this, as I need this to work for all three markers, and be in the same position regardless of which marker was hovered. It should ALWAYS appear next to the avatar like in the foursquare screenshot below BUT should move to the left or right dependant on the position of the icon on screen to allow it to fit.

在此输入图像描述

Can anyone help? As the docs are a little vague for my liking on this... I can create the tooltip but I'm confused how best to show it for all three markers but in the same position and viewport aware.

Here you go:

http://jsfiddle.net/nickaknudson/KVa2d/

tooltip = new Tooltip("text");
...
tooltip.open(map, marker);

Customizable via CSS.

UPDATE

Commented code: http://jsfiddle.net/nickaknudson/KVa2d/12/

UPDATE 2

Removed unnecessary bits: http://jsfiddle.net/nickaknudson/KVa2d/14/

//========================
// Tooltip Class Definition
//   extends OverlayView:
//   https://developers.google.com/maps/documentation/javascript/reference#OverlayView
//========================
var Tooltip
Tooltip = function(tip) {
    this.tip = tip;
    this.buildDOM();
};

$.extend(Tooltip.prototype, google.maps.OverlayView.prototype, {

    // build the DOM
    buildDOM: function() {
        // Body DIV
        this.bdiv = $("<div></div>").addClass('WindowBody').html(this.tip);
        // Window DIV
        this.wdiv = $("<div></div>").addClass('Window').append(this.bdiv);
        // Shadow DIV
        this.sdiv = $("<div></div>").addClass('WindowShadow');
        // Start Closed
        this.close();
    },

    // API - onAdd
    onAdd: function() {
        $(this.getPanes().floatPane).append(this.wdiv);
        $(this.getPanes().floatShadow).append(this.sdiv);
    },

    // API - onRemove
    onRemove: function() {
        this.wdiv.detach();
        this.sdiv.detach();

    },

    // API - draw
    draw: function() {
        var pos, left, top;
        // projection is accessible?
        if (!this.getProjection()) return;
        // position is accessible?
        if (!this.get('position')) return;
        // convert projection
        pos = this.getProjection().fromLatLngToDivPixel(this.get('position'));
        // top offset
        top = pos.y - this.getAnchorHeight() / 2;
        // left offset
        if (this.getMap().getCenter().lng() > this.get('position').lng()) {
            left = pos.x + this.wdiv.width() * 0.5;
        } else {
            left = pos.x - this.wdiv.width() * 1.5;
        }
        // window position
        this.wdiv.css('top', top);
        this.wdiv.css('left', left);
        // shadow position
        this.sdiv.css('top', (top - this.getAnchorHeight() / 2));
        this.sdiv.css('left', left);
        // shadow size
        this.sdiv.width(this.wdiv.width());
        this.sdiv.height(this.wdiv.height());
    },

    // open Tooltip
    open: function(map, anchor) {
        // bind to map
        if (map) this.setMap(map);
        // bind to anchor
        if (anchor) {
            this.set('anchor', anchor);
            this.bindTo('anchorPoint', anchor);
            this.bindTo('position', anchor);
        }
        // need to force redraw otherwise it will decide to draw after we show the Tooltip                    
        this.draw();
        // show tooltip
        this.wdiv.show();
        this.sdiv.show();
        // set property
        this.isOpen = true;
    },

    // close Tooltip
    close: function() {
        // hide tooltip
        this.wdiv.hide();
        this.sdiv.hide();
        // set property
        this.isOpen = false;
    },

    // correctly get the anchorPoint height
    getAnchorHeight: function() {
        // See: https://developers.google.com/maps/documentation/javascript/reference#InfoWindow
        //   "The anchorPoint is the offset from the anchor's position to the tip of the InfoWindow."
        return -1 * this.get('anchorPoint').y;
    }
});

UPDATE 3

Better positioning using outerWidth() and outerHeight() to take borders etc into account. Removed shadow div.

http://jsfiddle.net/nickaknudson/KVa2d/16/

//========================
// Tooltip Class Definition
//   extends OverlayView:
//   https://developers.google.com/maps/documentation/javascript/reference#OverlayView
//========================
var Tooltip
Tooltip = function(tip) {
    this.tip = tip;
    this.buildDOM();
};

$.extend(Tooltip.prototype, google.maps.OverlayView.prototype, {

    // build the DOM
    buildDOM: function() {
        // Window DIV
        this.wdiv = $("<div></div>").addClass('Window').append(this.tip);
        // Start Closed
        this.close();
    },

    // API - onAdd
    onAdd: function() {
        $(this.getPanes().floatPane).append(this.wdiv);
    },

    // API - onRemove
    onRemove: function() {
        this.wdiv.detach();
    },

    // API - draw
    draw: function() {
        var pos, left, top;
        // projection is accessible?
        if (!this.getProjection()) return;
        // position is accessible?
        if (!this.get('position')) return;
        // convert projection
        pos = this.getProjection().fromLatLngToDivPixel(this.get('position'));
        // top offset
        top = pos.y - this.getAnchorHeight() / 2 - this.wdiv.outerHeight()/2;
        // left offset
        if (this.getMap().getCenter().lng() > this.get('position').lng()) {
            left = pos.x + this.wdiv.outerWidth() * 0.3;
        } else {
            left = pos.x - this.wdiv.outerWidth() * 1.3;
        }
        // window position
        this.wdiv.css('top', top);
        this.wdiv.css('left', left);
    },

    // open Tooltip
    open: function(map, anchor) {
        // bind to map
        if (map) this.setMap(map);
        // bind to anchor
        if (anchor) {
            this.set('anchor', anchor);
            this.bindTo('anchorPoint', anchor);
            this.bindTo('position', anchor);
        }
        // need to force redraw otherwise it will decide to draw after we show the Tooltip                    
        this.draw();
        // show tooltip
        this.wdiv.show();
        // set property
        this.isOpen = true;
    },

    // close Tooltip
    close: function() {
        // hide tooltip
        this.wdiv.hide();
        // set property
        this.isOpen = false;
    },

    // correctly get the anchorPoint height
    getAnchorHeight: function() {
        // See: https://developers.google.com/maps/documentation/javascript/reference#InfoWindow
        //   "The anchorPoint is the offset from the anchor's position to the tip of the InfoWindow."
        return -1 * this.get('anchorPoint').y;
    }
});​

RESOURCES

You can use the mouseover event to display your tooltip. (See events doc here ). You only need to show it for marker2 since it has the highest zIndex value.

google.maps.event.addListener(marker2, 'mouseout', function() {
});

Here's a jsFiddle displaying a tooltip using InfoWindow . You don't have the tooltip code in your example. Can you update your example using the tooltip you created?

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM