xkjyeah / vue-google-maps

Google maps component for vue with 2-way data binding
https://xkjyeah.github.io/vue-google-maps/
1.88k stars 475 forks source link

Customizing markers with custom icon #38

Open sway opened 7 years ago

sway commented 7 years ago

I'm trying to create markers with custom icons, and as my icons are not so standard I need to specify the size, scaledSize, anchor and origin properties as well.

All of those require the use of new google.maps.Size or new google.maps.Point which are not available as the component is isolated from the actual script being loaded on runtime.

Is there any way you could expose the additional properties for the icon or include those additional classes in vue-google-maps as well?

Thanks a lot!

xkjyeah commented 7 years ago

Hi,

That is a common annoyance, and suggestions are welcome on how to fix that. The only worry is that it introduces a layer of complexity into this library.

One workaround I'm using is (when using webpack) to have:

mapSettings.js

import {loaded} from 'vue2-google-maps';

var settings = new Vue({
    data: {
        defaultIconSettings: {},
        defaultMapOptions: {},
    }
})
export default settings;

loaded.then(() => {
    /* google.maps.Size is now available! */
    settings.defaultIconSettings = /* Do something with google.maps.Size */
})

your-app.vue

<template>
<gmap-map :options="mapSettings.defaultMapSettings">
    <gmap-marker :icon="mapSettings.defaultIconSettings"></gmap-marker>
</gmap-map>
</template>

<script>
import mapSettings from './mapSettings';

export default {
    data() {
        return { mapSettings }
    }
}
</script>

While it's verbose it's actually a lot neater than having all your map options cluttering up the rest of your app logic, especially if you have more than one map in your app. For example, I found the following map options pretty useful:

          defaultMapOptions: {
            clickableIcons: false,
            streetViewControl: false,
            panControlOptions: false,
            gestureHandling: 'greedy'
          }

I'll leave this issue open, because it's true that setting icon sizes is far too annoying, but you might want to consider this workaround for now.

sway commented 7 years ago

@xkjyeah Wow, thanks a lot for the solution, this works like a charm! And I agree, it is not so bad to separate the configuration from the component itself.

awitherow commented 7 years ago

@xkjyeah is there a way that we could implement this as default functionality in the application, or would it be better to simply update the documentation to provide a way to show how to set this up?

xkjyeah commented 7 years ago

@awitherow that's a good idea. Would you like to make a PR?

xkjyeah commented 7 years ago

@awitherow What do you mean by "default functionality" in the application? I am quite sure many people will have different settings for their own apps.

awitherow commented 7 years ago

@xkjyeah now that I understand what is going on here, the above comment I made about "default functionality" does not make much sense. The way you provided is great.

davodaslanifakor commented 7 years ago

I cant use this :icon="{path:'https://www.google.dk/images/branding/googlelogo/1x/googlelogo_color_272x92dp.png'}" this is my cod


  <div class="map">

                     <gmap-map
                     :center="{lat:item.latitude, lng:item.longtitude}"
                     :zoom="17"
                     :icon="{path:'https://www.google.dk/images/branding/googlelogo/1x/googlelogo_color_272x92dp.png'}"
                     >
                     <gmap-marker  :position="{lat:item.latitude, lng:item.longtitude}"   >

                 </gmap-marker>
             </gmap-map>
         </div>

and result

map

how change icon marker ? how fix?? i use :icon in gmap-marker again for slove but has err

First instruction in path must be "moveto". )

awitherow commented 7 years ago

@davodaslanifakor I am not sure if path works with a web link.

zashton commented 7 years ago

@davodaslanifakor does it work if you change to this ?

    icon="https://www.google.dk/images/branding/googlelogo/1x/googlelogo_color_272x92dp.png"
davodaslanifakor commented 7 years ago

@awitherow I think you are truthful @ashtonzheng i test this url but dont work


<div class="map">

            <gmap-map
            :center="{lat:clinic.latitude, lng:clinic.longtitude}"
            :zoom="16"
            :icon="https://www.google.dk/images/branding/googlelogo/1x/googlelogo_color_272x92dp.png">
            <gmap-marker  :position="{lat:clinic.latitude, lng:clinic.longtitude}"  ></gmap-marker>
        </gmap-map>

err

this is err


`  - invalid expression: :icon="https://www.google.dk/images/branding/googlelogo/1x/googlelogo_color_272x92dp.png"
`
davodaslanifakor commented 7 years ago

@xkjyeah Are you can help me how change marker icon to some pic??

awitherow commented 7 years ago

@davodaslanifakor try actually saving this image and putting it into you project build.

davodaslanifakor commented 7 years ago

@awitherow Test this Way but has same err

awitherow commented 7 years ago

Well by using :icon you are saying that it should reference some sort of data within the this context of vue. perhaps using only icon would work.

mojereliev commented 7 years ago

Try use icon object with svg path, its work for me: { path: 'M0,5a5,5 0 1,0 10,0a5,5 0 1,0 -10,0', fillColor: '#091cab', fillOpacity: 1, strokeWeight: 0, scale: 6 }

davodaslanifakor commented 7 years ago

i understand have another problem . for example i change :draggable="true" but when i lock the console vue this not change i don't know where is problem and how solve.

robhawkes commented 7 years ago

A workaround for the initial issue of not being able to access google.maps.Size() and the other methods is to fake their object structure. If you run new google.maps.Size(46, 46) in the console it spits out {width: 46, height: 46, f: "px", b: "px"} and if you use that format in your marker code then it works perfect and you don't need to faff around with the google global.

For example:

icon: {
    url: 'path-to-icon.png',
    size: {width: 46, height: 46, f: 'px', b: 'px'},
    scaledSize: {width: 23, height: 23, f: 'px', b: 'px'}
}
Rufio2031 commented 6 years ago

I used @robhawkes approach and it worked great; when draggable was set to true.

Setting draggable to false alters the style and everything seems to change. The size becomes different, and zooming in and out the icons don't resize accordingly. Anyone know what might be going on here?

kk3hi3123 commented 6 years ago

I set my marker icon according to the example from @robhawkes. But I still cannot get the icon store from asset folder.

userPositionIcon: {url: "../assets/static/image/userLocationMarker.png", size: {width: 46, height: 46, f: 'px', b: 'px'}, scaledSize: {width: 23, height: 23, f: 'px', b: 'px'} }

The image path should be right as I can use it in <img> tag. And it displays correctly when I use an image link in url. Do I miss some other setting?

Rufio2031 commented 6 years ago

Just taking a shot at it, try "./../assets/static/image/userLocationMarker.png".

cristijora commented 6 years ago

A more simple, "pure" Vue option

 import { loaded } from 'vue2-google-maps';
computed: {
    icon(){
     let baseIcon = {
       path: 'path-to-img',
     }
     if(this.googleMapsInitialized){
      // we have google maps in the window
      baseIcon.scaledSize = new window.google.maps.Size(30, 30)
     }
     return baseIcon;
   }
},
async mounted() {
   loaded.then(()=>{
     this.googleMapsInitialized = true; // define this property in data
   });
 },
rosstripi commented 6 years ago

@cristijora's solution worked for me.

lochawala commented 6 years ago

@Rufio2031 thanks for this solution it's work fine just marker display on slide different point please look below image

image

Rufio2031 commented 6 years ago

I think you may have to play around with the size and scaledSize properties. If that doesn't seem to work, then I'd double check your position.

lochawala commented 6 years ago

@Rufio2031 yes it's work perfect when i give size and scaledSize properties value same

gregevari commented 6 years ago

I have a stock vue-cli based app and I can't seem to get an icon stored in the /src/assets folder to show up. As for @Pratiklocho if I put the location in an tag it works.

Showing from a url works fine:

<GmapMarker
    :key="index"
    v-for="(m, index) in markers"
    :position="m.position"
    :clickable="true"
    :draggable="false"
    icon="https://www.google.dk/images/branding/googlelogo/1x/googlelogo_color_272x92dp.png"
    @click="center=m.position"
  />

But replacing icon with any of these doesn't work: icon='./../assets/truck.png' icon="{path:'./../assets/truck.png'}" icon="{url:'./../assets/truck.png'}" :icon="{'./../assets/truck.png'}" // errors - compilation :icon="{path:'./../assets/truck.png'}" // errors - invalid character '\' :icon="{url:'./../assets/truck.png'}"

And neither does as a property like @kk3hi3123:

:icon="m.icon"

{
  icon: {
    url: "./../assets/truck.png",
    size: { width: 46, height: 46, f: "px", b: "px" },
    scaledSize: { width: 23, height: 23, f: "px", b: "px" }
  }
}

Probably missing something silly, any ideas?

gregevari commented 6 years ago

Nevermind, solved with

:icon="{ url: require('../../assets/img/marker-a.png')}"

from https://stackoverflow.com/questions/51800404/custom-marker-for-vue2-google-maps

meastblue commented 5 years ago

@gregevari thx for the solution. Is it possible to custom width and height?

eregnier commented 5 years ago

This component should help do the trick https://github.com/eregnier/vue2-gmap-custom-marker

vallemar commented 4 years ago

Is it possible to set a rotation of the icon / image?