React-native-maps: Image component inside Custom Markers and Callouts in Android

Created on 12 Dec 2017  ·  340Comments  ·  Source: react-native-maps/react-native-maps

Image component inside Custom Markers and Callouts in Android not appearing or rendering.

Merging all issues to this.

Please, clone https://github.com/alvelig/react-native-maps-example and try if you can reproduce.

Mention your lib version, react-native version, Android version, and is it a device or emulator.

Android bug react-native

Most helpful comment

react-native-maps 0.22 fixes this :)

All 340 comments

Tested with:

  • react-native 0.50.4
  • react-native-maps 0.18.3
  • play-services-maps 10.2.4/11.0.4
  • compileSdkVersion 26
  • buildToolsVersion "26.0.3"
  • device

    • A: Sony XZ Premium (Android 8.0.0, Google Play Service 11.9.51)

    • B: Android emulator (7.1.1 Google APIs Intel x86, Google Play Service 11.7.43)

    • C: Android emulator (6.0.0 Google APIs Intel x86, Google Play Service 11.7.43)

Result:

| | targetSdkVersion 23, A/B | targetSdkVersion 24, A/B
| ----------------------- | -------------------------- | ---------------------
| Debug, First Run | No | No
| Debug, Ctrl-m/Reload | Yes | No
| Release | No | No

| | targetSdkVersion 23, C | targetSdkVersion 24, C
| ----------------------- | -------------------------- | ---------------------
| Debug, First Run | No | No
| Debug, Ctrl-m/Reload | Yes | Yes
| Release | No | No

As a work around, you can try setting targetSdkVersion to a number no more than 23, then

constructor(props) {
    super(props);
    this.state = {
        imagemarker_workaround_cnt: 0
    };
}
componentDidMount() {
    let self = this;
    setTimeout(() => {
        self.setState({imagemarker_workaround_cnt: 1});
        setTimeout(() => {
            self.setState({imagemarker_workaround_cnt: 2});
        }, 10);
    }, 10);
}



md5-4e9b515b6f627c20c095db04c474037e



render() {
    if (this.state.imagemarker_workaround_cnt == 1) return <View></View>;
    return <MapView>
        {this.state.imagemarker_workaround_cnt == 0 && 
        <MapView.Marker coordinate={{latitude: 0, longitude: 0}}>
            <View><Image source={require('./icon.png')} style={{width: 1, height: 1}} /></View>
        </MapView.Marker>}
    </MapView>;
}

In my case images disappear on marker addition. I'm moving the map and adding only those which fall into the viewport. So they consistently disappear. If I put other elements in the custom view, they are shown. So there's a huge problem with Image rendering. Great investigation anyway.

I tried to fix this few months ago but failed to succeed, I guess i've done some messy code.

My idea was actually to implement here https://github.com/react-community/react-native-maps/blob/master/lib/android/src/main/java/com/airbnb/android/react/maps/AirMapMarker.java#L350 a bitmap caching system (https://developer.android.com/topic/performance/graphics/cache-bitmap.html) which would use the marker key as a key of our cache map, and the Bitmap as a value. Maybe this is a wrong idea, just proposing this if someone has time to try and all that stuff

Can someone fix this issue ?
It is really annoying that we can't have images on markers. I don't know if someone found a workaround ?

For now use Marker's image prop. That is working ok. Having Image in custom view may not be resolved recently.

@foyarash The problem is not the caching system, the problem is that every time it creates a bitmap of the view, and sometimes it does not happen or I don't know what happens, but it does not draw.

Yeah that's what I noticed.

I actually tried some solution and particularly invalidating the MapView after the image has been loaded, but that didn't work.

That's really a weird behavior and I'm curious about what is wrong with this

Yep, I hope someday someone reviews and refactors that, by now if you need a picture use image prop (it works ok along with the custom view if you need text). Don't forget to use @2x and @3x otherwise the images will be of different sizes.

My first thought was that fresco was causing a problem, with the error 'DraweeHolder not attached' something like that, but the thing is that it's actually almost the same code that you can see in the fresco doc

actually in custom view there's no direct call to Fresco. It's done through View.draw(Canvas). But it also looks suspicious having those warnings in log.

I'll try to refacto all that stuff maybe one day with the few knowledge i have

Thank you @foyarash and @alvelig for taking seriously this bug.

For some reasons, I won't be able to use the image prop way to fix my issue. I hope someone could fix this soon !

When I'll have the time - because it is not the case for now - I may submit a PR (with the few knowledge I've too).

@elieteyssedou Why not? Image prop can go along with text in custom view, so it should do in most cases.

@alvelig Because :

Still no update on this one?

@dashracer It would be nice if we could at least specify image size. Currently if I provide a small image its blurred. If I provide a high def one it just fills up the map :(

I tried to work on this, tried every solution that came into my mind even invalidating the child view of the marker, forceUpdate the component when the image has loaded, but nothing is working correctly. The only thing I could get is an almost transparent view (wtf ???) and only for a few amount of markers.

So I'm giving up on this

@gilbertKaradja use @2x and @3x sizes

@foyarash that is the problem. GoogleMaps are using only images, images are made by drawing canvas on the fly. So it does not always work.

@alvelig Im not sure that will change anything. I need a way to provide the size for the image i want to use. If i provide width and height as, lets say, 25x25 , and provide an image of 24x24 it looks blurry. I would like to provide a higher res image, like 64x64, so when it scales down its still sharp. IF I do as you advised I just get a bigger image

@gilbertKaradja You must provide a 25x25 (the size you originally want the image), 50x50 (@2x) and 75x75(@3x) image as you would do for native platform development. See https://facebook.github.io/react-native/docs/images.html.

I'm having this issue with images and text in the Markerview.callout, has anyone found a work around for this? I can't use the image in Markerview.Marker as a different image is used for the marker and different images for each callout as well.

My test-phone (Nokia 3) just "upgraded" to 7.1 and now my map markers won't work. I am using <Image /> and <ImageBackground /> as ´children` when I need to show a number on top.

The second use-case is not possible with using the image prop as far as I know.

  • Has anyone found a work-around for this?
  • Can a maintainer tell me if this is being worked on?

Edit: My work-around is to convert (by hand) our SVG files into React components and that works on iOS, Android (7.1) and Android (5.0).

@andrioid That's interesting.

Just to mention: you can use image prop as a background image for the marker and have your custom text in the MarkerView.
<Marker image={markerImage}/><Text>10</Text></Marker> is a valid use case.

Can you please elaborate on the problem (you had svg, not png files, did not you?), and tell how you are converting them in react components?

P.S. This issue is one of the priorities (at least for me) but we have not much time to dedicate to it. So PRs and insights are welcome.

Can you please elaborate on the problem (you had svg, not png files, did not you?), and tell how you are converting them in react components?

Sure @alvelig

Our designer delivers in AI (or SVG), but we had PNG files as map-markers in a few sizes, because at the time, I thought SVG support was bad.

I have three types of markers. A spot, a cluster (with a number inside) and a city (with a number inside). That was being solved with <Image /> and two <ImageBackground />

As to converting SVG files to React components, I tried a tool (and there are a few) to convert it automatically. It ignored all styling, and resulted in a black circle. But then I opened the resulting file and manually applied the styles. That turned out great... if anything, the map performs better now.

It is a lot less scary than it sounds. Because SVG files are essentially just shapes with some fill applied to them. So, I just copy paste the SVG content into a JS file and then replace all the <g> with <Svg.G> and so on.

This also has the added bonus of applying colors through props. So I can have a selected prop on my marker icon and that changes the SVG in a subtle way. I like that!

Just to mention: you can use image prop as a background image for the marker and have your custom text in the MarkerView.
10 is a valid use case.

Thank you. I did not know that.

I'll add that my SVG work-around didn't perform well enough to use. With 30+ markers on an iPhone 6s everything was stuttering, so I'm back to using <Marker image={prop} />, which has a minor issue on iOS (see #678)

So, I understand that you can provide the component a image prop, but is there any workaround known for getting images to display on Android inside of the component??

Much appreciation in advance!

Reading through this thread, it looks like there are two issues being discussed. There is a lot of discussion around using an image for , but not a lot of discussion around nesting and inside of a component on Android, which is the issue me and my team are currently trying to fix.

@alvelig would it make more sense to split the thread into two different discussions?

I've investigated this issue for a couple of hours.

Because of I'm not an expert on react-native-maps and the structure of react-native I could just review the code.

I guess addView method adds the custom markers into parent view. So, after this method the control belongs to react-native code base.

By using the same custom marker method, I can use a text as custom marker. Also I can color a view's backgorund as a custom marker. Both of them can appear on the map as a marker. But <Image /> image component can not.

It may be there but I could not find any specific condition code for API >= 25 in react-native code.

Also I tried to find any deperecation message on Android classes that are used by related java files of react-native. However I found nothing if I didn't overlooked something...

It render custom markers on Android 24 and cannot render on Android 25.
This page shows us differents:
https://developer.android.com/sdk/api_diff/25/changes.html

I wonder that a custom marker can appear on an iOS? Is this an android-specific issue?

@efkan it works on iOS if i remember well

@arronhunt Actually they have the same origin. Images sometimes don't render in Android because View.draw() does not render the image in time (that's where I came to in my investigation)

@efkan yes, it's android specific

Given that the custom view markers are not rendering, is there any way to style/resize the image prop supplied to Marker?

I fixed this problem by follow this solution https://github.com/wkh237/react-native-fetch-blob/issues/574
you can pass image to <WebView/> and place it in <Marker/> or <Callout/> like this
<Callout tooltip={true}> <View style={{flex: 1,}}> <WebView source={{ baseUrl: RNFetchBlob.fs.dirs.DocumentDir, html,}} style={{ width:50,height:50, }} /> </View> </Callout>

@Afalook Is there a way to feed the WebView an image without more html? Also, in my case the image might be both local and a url, if that matters.

@Afalook Have you found a chance to check its performance?
BTW thanx for sharing.
For example: How many Marker could you use at the same time without any screen lag?

(I had also tried WebView with base64 but I could not achive your result)

@Afalook that's dirty man. But that's valid! Better that not having any solution.

For some reason the webview solution doesn't work for me. It works outside of a map/marker, but once I put it in a marker it renders only the background.

That bug is super annoying, I hope there exists (even if no one knows it yet) a real solution for it.

The same result here. Just like as @Doychev 's. It works only out of MapView component.
(I have never tried on Android 7.1 and with file// path because I could not get it worked on Android 6.0)

The reason of this issue is this -> https://github.com/facebook/fresco/issues/1445#issuecomment-362551065

And as a workaround these steps can be followed:

  1. Download Fresco 1.3.0 source (https://github.com/facebook/fresco/archive/v1.3.0.zip)
  2. Mark as comment line these lines
  3. Build Fresco as directed over here (add a .gradle/local.properties file into root direactory and Android NDK may need updated to a newer version) and copy drawee-debug.aar file into your libs folder
  4. Modify build.gradle file by specifying *.aar files (actually related file is only drawee-debug.aar file if you know how to set dependencies you can use only it)
  5. Build your project. And your custom markers will be shown

I've spent 16 days to find this workaround.

Enjoy!

@efkan dont think so, fresco is only used to load the markers from the image prop, but when adding child to the Marker, fresco wont be used

@foyarash I've updated my comment above. You might check it out..

Actually if a workaround is added into react-native source it would be more correct.

@efkan Can you show what's done in step 4 in a bit more detail / by example? Also, is it possible to share the .aar files generated by step 3? Thanks!

@Doychev , I've needed to change some of build.gradle files that belong to some other project in my main build.gradle file.

Sample theProject/android/app/build.gradle changes after putting *.aar file into libs folder:

...
dependencies {
    ...
    compile (name:'drawee-debug', ext:'aar')
}
...
allprojects {
    repositories {
        flatDir {
            dirs 'libs', './libs'
        }
    }
    configurations {
        all*.exclude  module: 'drawee'  // Doychev's suggested solution can be found over here
    }
...
}
...

Last night I build Fresco again and I have a built drawee-debug.aar file.
Becaus of building takes long time I'm sharing the built file:
https://drive.google.com/open?id=1c71C9D1bCuUTixCvtkhNNTwq8Jb88N6C

In fact I've been searching if I can apply another workaround into MainActivity.java file
(edit: I could not achieve this because there is no eligible method to use for catching View object in MainActivity.java)

BTW, @Doychev keep in mind, react-native compile Fresco packages in its own dependencies section. So drawee module must be excluded in build.gradle file.
Otherwise it throws an exception..

The Maven repo fresco package contains drawee, fbcore and imagepipeline modules.

For reference for anyone else, that's the additional change:

android {
...
    configurations {
        ...
        all*.exclude  module: 'drawee'
    }
...
}

@Doychev , your solution also works within allprojects section. it's a good practice for to provide unity .

allprojects {
    repositories {
        flatDir {
            dirs 'libs', './libs'
        }
    }
    configurations {
        all*.exclude  module: 'drawee'  // Doychev's suggested solution can be found over here
    }
...
}

Many thanks for posting a solution for this infuriating bug! It's solved all our issues with custom markers for API 25+.

Scary how this wasn't spotted sooner. Hopefully there's not too many apps out there with this bug.

This fix doesnt work for me on Android Moto 4

@hugoh1995 did you follow the steps (https://github.com/react-community/react-native-maps/issues/1870#issuecomment-370751929) and add the following to your apps build.gradle file?

dependencies {
    ...
    compile (name:'drawee-debug', ext:'aar')
}

Make sure you have the aar file in the libs directory within apps directory (apps should contain build, src and libs).

I've tried it out on a couple of emulators and it's working fine. Haven't tried it on a physical device just yet.

What version of Android is your Android Moto 4 using? What version of React Native / React Native Maps are you using?

After a few more iterations, I found out something peculiar in my project.

I have multiple marker styles, using different images. Some of them are a bit larger than the others (basic marker - 15.2KB, 15x15 pixels; special marker - 18.5KB, 60x81 pixels).
In my project, I gather the information about all markers simultaneously and I try to display them at once, whenever they are ready.

After the fix proposed by @efkan markers started appearing but I noticed another, probably unrelated bug - the bigger markers didn't appear unless I reload the marker data or reload the whole app (through the 'Reload' feature of RN). Also, markers are always being set on the map, they are just not rendered.
Currently I found out that by delaying the display of all markers by 0.5 seconds this problem is fixed (or rather worked-around). In my case, I am displaying the markers by mapping a property from this.state, so I just delay the this.setState({markers}) execution.
It might be just a problem with my project but it might help someone :)


TL;DR - Try artificially delaying the showing of markers by ~0.5-1 second and see if there is any difference.

@Doychev can you share the code you use for delaying the markers?

@hugoh1995 did you download the aar file provided by @efkan?

No because I'm not sure where to put the file 🤔

Icon images only show after I reload the map a few times, sometimes it works on the second time, sometimes doesn't.

    setTimeout( () => {
      this.setState({
        markers : currentMarkers,
      });
    }, 500);

Also, the .aar file should be located in: YourProjectDirandroidapplibs

@Doychev thanks! doesn't seem to change anthing for me tho.

@hugoh1995 , you might also try this code

@efkan thanks! just tried without luck 😅

@hugoh1995 after adding the aar in that directory you still need to carry out all the changes to your gradle files to get it to work

Recently, I found the sample solution for this problem without convert image to base64, just pass the image URL to html property then place it in <img/> tag like this
capture-20180310-165926
By the way, I'm using cloudinary to store my image that's work fine.
Hope this help.

So the only ways around this right now are the WebView and drawee-debug workarounds? Is this a problem with React, React Native, or react-native-maps? Is there any hope for a complete solution to this in the foreseeable future?

@wbattel4607 it's a problem with the Android Fresco library which is breaking it for API 25+. @efkan has posted a workaround which will mean should work for now.

Have a read from here and below: https://github.com/react-community/react-native-maps/issues/1870#issuecomment-370601097

When I was using com.google.android.gms:play-services-maps:10.0.1, custom marker views were rendering well. But since I am using com.google.android.gms:play-services-maps:11+, it doesn't work. Any idea?

@bdavid68 I think I've been using 10.2.4 the entire time

@MarkOSullivan94 Actually, it's working with 10.0.1.
I need to use react-native-geolocation-service library and It requires 11.+.
But I can't use different google service versions.

@bdavid68 I haven't done extensive testing with the different versions, have you raised an issue about it?

I added the .aar file in the comments above, and changed the gradle files, but the callout images still don't seem to load. Weirdly, after the callouts are opened, on the 3rd time the image loads

@MarkOSullivan94 It doesn't look like an issue of plugin version.
Last night, I upgraded my android device to 8.0 and I can't see markers now. Google map marker is working well on Android 7.0, but not working on android > 7.0. It might be an issue of google service plugins for new android OS versions.

@MeganKurz if you could share a public project, someone here could hopefully point out what you need to do to fix your problem.

@bdavid68 it's API 25 and above so you'll have no issue with 7.0 or below, it's when you use 7.1 and above.

<Marker
                coordinate={marker.latlng}
                key={index}
                onPress={this.onMarkerPress}
                identifier={marker.id.toString()}
              >
                <Image
                source={marker.image}
                style={{ width: 50, height: 50 }}
              />
              </Marker>

works on Moto X Style (7.0), not on S8 Note (7.1)

Looks like React Native might finally be updating their Fresco dependency. Whenever this gets packed into an RN version we might see the end of this bug...

https://github.com/facebook/react-native/commit/8e065baad43a124a999d4f3c253b1081a3045a1a

I'm trying to determine if Fresco has fixed this problem internally. This RN commit would bump the version to 1.8.1, with RN currently way behind on 1.3.0.

EDIT: It's not included :(

Has anyone been able to test RN-Maps with it being bumped to 1.8.1? Don't want to get my hopes up and think this will be a fix to our issues only to find out it's still broken.

@MarkOSullivan94 they haven't packaged it yet.

<ImageBackground source={busMarker} style={{ width: 50, height: 50 }} onLoad={() => this.forceUpdate()}> <Text style={{ width: 0, height: 0 }}>{Math.random()}</Text> </ImageBackground> works for me

Still not working for me, even if Fresco seems to have been updated in the latest version.
I'm using Expo, and I still have the same issue being :

Everytime I open the app and display the map for the first time, some Images in some custom Markers don't appear for no reason, like one Image appears in one marker but not in another one...

And when I go to another view, and then come back to the view with the map, this time every Markers are displayed correctly...

@nerdyzia Well, it works for me too now, thanks!
Even if it doesn't look clean for the moment, it's working at least 👍

@nerdyzia Are you doing anything special in your ImageBackground component or busMarker variable? Your solution isn't working for me.

@AdrianMrn no nothing. bus marker is
import busMarker from '../images/bus_marker.png';
Hope its helps you.

Has anybody tested it with RN 0.55? this is the version shipped with the fresco updated.

@alvelig
Tested with react-native 0.55.2, and not working.
screenshot_1523434656

Actually I had specified the real reason before.

I guess that nothing will change as long as the visibility issue of fresco is not solved.

Two steps must be taken to solve this issue:

  1. The visibility issue of Fresco should be solved
  2. The newest Fresco library -that has not any visiblity issue- should be added into ReactAdroid dependencies block.

Can we use the temporary fix in release @efkan ? In release compile too ?

Is it possible to remove the bugged drawee from react and use the good one recompiled localy ?
I got the following error : more than one library with package name 'com.facebook.drawee'

Please I need a fix on react 0.53.3 for release build.

@z4qx

Can we use the temporary fix in release @efkan ? In release compile too ?

I hope so. There is no any difference I remember between release and development compilations.

Is it possible to remove the bugged drawee from react and use the good one recompiled localy ?

IMHO this is not a good practice than changing drawee module.

Also I had checked to see if this solution can be implemented my MainActivity.java file. I could not find any way.

@efkan
Thanks for your return. Your solution seem's to work on release but randomly. Sometime the images are loaded and sometime not.

It can be awsome if you can implement the solution in the MainActivity.java !

Let me know. Do you have any other possible solution to solve the problem ?

@z4qx

It could be another issue. I recommend checking this out.

I have already try this solution but it doesn't work for me. I dont know why :/

I'd just tried this solution on a couple of phones.

hugoh1995 has encountered the same issue too.

The issue may be continuing.

The issue I remember was that when calling a view (object) second time android library returns its visibility value as false.
Someone who good at Fresco, React-Native and Android libraries can find it easily, but I had tracked clues for days.

However we know the real problem now. Maybe someone who encountered this entry and handles this solution again and finds a more stable solution.

Hopefully Fresco developers handle this issue. The real medicine is this..

It's very weird, some images never have the issue and some randomly...

Do you have any idea where is the problem in Fresco ? Maybe we can fix it ?

@z4qx I mentioned this before and it might have relation - in my case, before implementing a workaround, bigger images were not showing while smaller images were fine. I think it's a matter of a thread finishing in time for something dependent on it to work. Check my comment on the same thread from the 8th March here - https://github.com/react-community/react-native-maps/issues/1870#issuecomment-371544597

@Doychev Interesting !
It's seems to be the same problem. The marker is on the map, it's just not rendering.
Where do you do the setState ?

@z4qx I can't recall exactly what my implementation was, but I remember that if the map features a way to reload the markers, everything appeared fine. Anyway, the solution / workaround proposed by efkan worked for me and until the fresco issues are resolved in a more permanent way, I'll be sticking with it.

            <Image
                    source={require('../listings/marker.png')}
                    style={{ height: 32, width: 20 }}
                    onLoad={() => this.forceUpdate()}/>

This works for me... the last line did the trick.

@hegelstad Doesn't works in my case. Always the same picture dont show normaly. It's very strange because will i'm clicking on the marker, the image showing, most of the time. It can be an other issue ?

I have run across this issue as well, I have tried several of the workarounds on this thread, however none of them appear to have worked.

I am hopeful that a fix comes out soon, but will continue to test things here and there. Thanks to everyone here who has put a heap of effort into trying to find the problem and a fix for them.

@redisean Same for me. Only the trick of @efkan improve it a bit, by intermittence. All other trick (onLoad => refresh, timer doesn't works).

Currently what is saw is that the same image always have this issue. BUT, only when it's rendered in the map. I have the same image on a normal screen and it's works perfectly.
So I guess if we can do the diff between normal image render and marker image render used by the map, we will find the issue.

Anyone have try to change some code into the react java code ?
Following this comment , we can find the possible change to apply ?

I'm having the same issue. Image component inside Marker does not render. It does not even fire the onLoadEnd. But when Image is outside the Marker it is working fine.

Loading the Image in the React view is probably async, so the subview to bitmap function of the native implementations converts the view before the image is rendered. That's why my images disappear sometimes, theres a race condition.

Is there a way to block the conversion of the React view to Bitmap format until the image is loaded? I am not too familiar with either iOS or Android code..

Isn't it possible to add "style" prop to a marker? This might be a suitable workaround while Fresco library get fixed

Tried all the hack proposed their but nothing work in my case. I really need to fix it to release my app...

Hi, I found something working in my case :
1 - Preload and do a render of your images before the MapView !

    let preload = null;
    if(!this.loaded && Platform.OS == 'android') {
      preload = (<View style={{height:0, width:0}}>
         {Object.keys(constants.emoji).map(marker => (
             <Image key={marker} style={{opacity:0, width:0, height:0}} source={constants.emoji[marker]} />
         ))}
        </View>)
      this.loaded = true;
    }
    return (
             <View>
             {preload}
        <MapView> ...

2- Force to marker to reRender once is loaded :

render() {
    return (
        <View style={style.container}>
          <View style={style.imageContainer}>
            <Image style={style.markImageStyle} source={this.image} onLoadEnd={() => {this.setState({iconLoaded: true});}} /> 
          </View>
        </View>
      ) 

So, the real problem seems to be that the image is rendered before it was completely loaded. Once it's done, the problem is gone. Or maybe a problem of caching ?

Sort of a mix of answers that ended up working for me...

In the render method of your component where the <MapView /> is located, I added an <Image /> tag with the following:

<Image source={gLogo} style={{ width: 0, height: 0 }} onLoad={() => this.forceUpdate()} />

Then in my <MapView.Marker> tag, I nested the same <Image /> but with width and height set to my desired sizes.

Hope it helps

Hello everyone,

Any news on a potential fix? Tried every workaround but no success so far.
Is it possible that the new RN version 0.55.4 comes with a fix for that?

Thanks.

In my case, it not showing on Android, working on iOS.

That is the case for everyone. This is an Android issue. iOS is not affected.

Was facing the same issue, managed to fix it based on what @nerdyzia proposed.

The structure of my marker component _was_:

const CustomMarker = () => (
  <Marker>
    <View>
      <View><Text /></View>
      <Image />
    </View>
  </Marker>
)

That worked fine on iOS, but for android the Image rendered blank. So adjusting the above to the following, displays the Image correctly:

const CustomMarker = () => (
  <Marker>
    <View>
      <View><Text /></View>
      <View><ImageBackground /></View>
    </View>
  </Marker>
)
  1. Use ImageBackground instead of Image
  2. Wrap ImageBackground in a View

@breadadams Can you share what version of React-Native and React-Native-Maps you're using?

Hey Guys, so I had this problem today, and this worked for me :
import React, { Component } from 'react';
import { AppRegistry, Image, StyleSheet, Text, TouchableOpacity, View } from 'react-native';

import IDGenerator from '../../utils/IDGenerator'

import MapView from 'react-native-maps';

const CAR_IMAGE = require ('../../../assets/Car.imageset/car.png')
const Callout = MapView.Callout

export default class MapCallout extends Component {

static callouts = []

constructor (props) {
    super (props);
    this.id = IDGenerator.ID ()
    MapCallout.callouts.push (
        {
            id     : this.id,
            loaded : false
        }
    )
}

static checkLoaded () {
    return MapCallout.callouts.filter ( (img) => !img.loaded ).length == 0
}

render () {

    return (
        <Callout>
            <Text style = { styles.headerText } >{ this.props.title }</Text>
            <TouchableOpacity onPress = { () => {
                console.log ("PRESSED")
             } }>
                <Image
                    source = {
                        CAR_IMAGE
                    }
                    onLoadEnd = {
                        () => {
                            this.forceUpdate ()

                            index = MapCallout.callouts.findIndex (obj => obj.id === this.id)

                            MapCallout.callouts [index].loaded = true

                            if (MapCallout.checkLoaded ()) {
                                console.log ("FINISHED LOADING")
                            }
                        }
                    }
                />
            </TouchableOpacity>
        </Callout>
    );
}

}

My logic is basically, have something listen where you use the callouts by using the function that checks if all the markers are fully loaded and if are not, load a spinner.

EDIT: Fixed my marker's problem with @adlondon solution. Just pre-rendering the image with width and height = 0.
But now I'm not able to fix the callout's bug where image is not shown on first click on Marker.

None of the hacks work for me with the latest version of React native.

this comment https://github.com/react-community/react-native-maps/issues/1870#issuecomment-372018414 fixed my problem with images inside callouts

Sure @Bobobrien92,

"react-native": "0.54.2",
"react-native-maps": "^0.19.0",

Loading the image with height and width of 0 and then again later works for some devices. from what I can see they stop working at around API level 26.

@Fr1kki3 yep, it's already been reported to cause issues with API 25+

Yeah I solved mine now by pre-loading the image with height and width of zero. This seems like it might be unreliable but I haven't had any known issues yet. Still hoping for a fix though.

Use Image with resizeMode: "cover" or use ImageBackground . Both are working for me on android.

I used Image like this

import FastImage from 'react-native-fast-image'
import { createImageProgress } from 'react-native-image-progress'
const Image = createImageProgress(FastImage)

and then I called it like this

<Image resizeMode={FastImage.resizeMode.cover} source={Images.simple} style={{width: 17, height: 25}} />

while ImageBackground like this

<ImageBackground source={Images.simple} style={{width: 35, height: 50}} />

"react-native": "^0.49.3",
"react-native-maps": "0.17.0"

I am using this only for marker.
Calling forceUpdate will crash your application if you have may markers. So don't use it.

Hope this is useful.

which android version?, the error happens from version 7.1 (API level 25)

Unfortunately, I am not getting any devices with Android version 7.1.
But I checked on OnePlus 6.0.1/ Samsung 7.0.1/ Sony 8.0.0
It is working there.

Quick question: it is happening only on 7.1 or from 7.1?

@SandeshVakale (in my case) only happens 7.1 or higher (from API level 25)

@outaTiME I really don't have any idea Why it's not working for you...

screenshot_20180530-104519

Marker pin images are copyrighted to Air France.

For me, it's working fine even on android 8.
I can just show you my example.

This is my function to render pins.

renderMapPin (Pin) {
    switch (Pin) {
      case 'simple':
        return <Image resizeMode={FastImage.resizeMode.cover} source={Images.simple} style={{width: 17, height: 25}} />
      ..... other cases...
      default:
        return <Image resizeMode={FastImage.resizeMode.cover} source={Images.default} style={{width: 17, height: 25}} />
    }
  }

And then I called this function outside callout and inside the marker.

<MapView
            provider={this.props.provider}
            ref={ref => { this.map = ref }}
            style={styles.map}
            initialRegion={{
              latitude: LATITUDE,
              longitude: LONGITUDE,
              latitudeDelta: LATITUDE_DELTA,
              longitudeDelta: LONGITUDE_DELTA
            }}
          >
            { data.map((Url, index) => {
              const a = {
                latitude: Url.latitude,
                longitude: Url.longitude
              }

              return <MapView.Marker style={{zIndex: 5}}
                identifier={Url.target}
                key={Url._id}
                coordinate={a}
                onCalloutPress={() => this.onPressItem(Url)}
              >
                { this.renderMapPin(Url.pin_icon) // <-- here is my render Pin }
                <MapView.Callout style={{width: 300, height: 60, paddingHorizontal: 2, justifyContent: 'center', alignContent: 'center', alignItems: 'center', backgroundColor: '#' + Url.color[1].substring(2), borderRadius: 10}} tooltip>
                  <Text style={{color: 'white', fontWeight: 'bold', textAlign: 'center'}}>{Url.titres[0]}</Text>
                  <Text style={{color: 'white', textAlign: 'center'}}>{Url.titres[1]}</Text>
                </MapView.Callout>
              </MapView.Marker>
            }) }
          </MapView>

Can you try to pass zIndex for your marker? Let me know if it is still not working. If possible then share your code.

@SandeshVakale Im using Expo (SDK 27) that brings React Native 0.55 with react-native-maps 0.21 and in android 7.1 or higher does not show the images inside of custom components ... this is why this incident is open 😢

I see you use FastImage, what happens if you use a Image from react-native?

Marker component:

import React from 'react';
import PropTypes from 'prop-types';
import { MapView } from 'expo';
import { Image } from 'react-native';

export default class DeviceMarker extends React.PureComponent {

  static propTypes = {
    coordinate: PropTypes.object.isRequired,
  };

  constructor(props) {
    super(props);
    this.state = {
      initialRender: true
    };
  }

  render() {
    const {
      coordinate,
    } = this.props;
    return (
      <MapView.Marker.Animated
        coordinate={coordinate}
        centerOffset={{ x: 0, y: -18 }}
      >
        <Image
          source={return require('./assets/images/marker-car-exceeded.png')}
          // hack to first render on android
          // https://github.com/react-community/react-native-maps/issues/924#issuecomment-311648778
          onLayout={() => this.setState({ initialRender: false })}
          key={`${this.state.initialRender}`}
        />
      </MapView.Marker.Animated>
    );
  }
}

Component usage:

<MapView
  ref={ref => (this._mapRef = ref)}
  style={styles.map}
  initialRegion={initialRegion}
>
  <DeviceMarker
    coordinate={animatedRegion}
  />
</MapView>

This code works as expected on iOS / Android (until API 24)

svg works fine on android

@rheilgm Can you go into a little more depth than that?
"Mention your lib version, react-native version, Android version, and is it a device or emulator."

This issue has been open forever and plagued with well-intentioned/useless recommendations concerning the extent of this GitHub issue.

There hasn't been any milestones set/accomplished that I know to fix this.

Same problem, whether it be an emulator or a phone, from 7.1 upwards Images as custom markers do not show in maps (Wrapped inside markers). Seems the image property of markers is the only way to go, just so little control over the size etc.

@outaTiME Your solution and other forceupdate solutions simply don't work.

yeah since im out of options, converted the image to an svg then used https://github.com/necinc/msvgc to convert it to a react component

note that the react component generated by such lib is using react-native-svg

was lucky since the image we used is just some simple icon, easily converted it to an svg

@TitanKing Yup you are right, my solution only works until Android 7.0 (API 24), for higher version i use the following workaround in marker component:

import React from 'react';
import PropTypes from 'prop-types';
import { MapView } from 'expo';
import { Image } from 'react-native';

export default class DeviceMarker extends React.PureComponent {

  static propTypes = {
    coordinate: PropTypes.object.isRequired,
  };

  constructor(props) {
    super(props);
    this.state = {
      initialRender: true
    };
  }

  render() {
    const {
      coordinate,
    } = this.props;
    // https://github.com/react-community/react-native-maps/issues/1870
    if (Platform.OS === 'android' && Platform.Version >= 25) {
      // bad image pixel ratio using the following way
      return (
        <MapView.Marker.Animated
          coordinate={coordinate}
          centerOffset={{ x: 0, y: -18 }}
          image={return require('./assets/images/marker-car-exceeded.png')}
        />
      );
    };
    return (
      <MapView.Marker.Animated
        coordinate={coordinate}
        centerOffset={{ x: 0, y: -18 }}
      >
        <Image
          source={return require('./assets/images/marker-car-exceeded.png')}
          // hack to first render on android
          // https://github.com/react-community/react-native-maps/issues/924#issuecomment-311648778
          onLayout={() => this.setState({ initialRender: false })}
          key={`${this.state.initialRender}`}
        />
      </MapView.Marker.Animated>
    );
  }
}

@outaTiME

React Native's Image component handles image caching like browsers for the most part. If the server is returning proper cache control headers for images you'll generally get the sort of built-in caching behavior you'd have in a browser. Even so many people have noticed:

  1. Flickering.
  2. Cache misses.
  3. Low-performance loading from cache.
  4. Low performance in general.

FastImage is an image replacement that solves these issues. FastImage is a wrapper around SDWebImage (iOS) and Glide (Android).

Features

  1. Aggressively cache images.
  2. Add authorization headers.
  3. Prioritize images.
  4. Preload images. $$$
  5. GIF support.
  6. Border radius.

Find More information here https://github.com/DylanVann/react-native-fast-image

Probably using Image from this library fixed my problem. I am not using any forceUpdate neither converting Image to SVG. Working fine on all devices and both OS.

Question: @outaTiME Can you please try my solution once and let me know if it is working for you or not? I never used expo before, so, don't know much about it.

@SandeshVakale I know the adventages of FastImage but unfortunately Expo uses its own asset manager for preloading and catching.

This is why I'm trying to use react native maps in the basic way.

Sorry but im unable to try your solution, by the moment my best effort was the example that I published, thanks !!!

@SandeshVakale since the library your are linking requires detaching from expo, I have used
react-native-expo-image-cache
which is working perfectly at my app. (@SandeshVakale maybe it fits for your development)

However, even using this component, the images are not displaying at Android callouts (it does at iOS).
Thank you for your point anyway.

Added my personal summary in https://stackoverflow.com/questions/49978119/react-native-android-markers-with-custom-images/50632024#50632024

From my tests, the following work with React-Native Image component (children to the marker):

  • Android 6 (Samsung Galaxy S6 and Nexus 5 Genymotion Emulator)
  • Android 7.0 (Samsung Galaxy TAB S2)

The following DO NOT work with the React-Native Image component:

  • Android 7.1 (Samsung Galaxy S6 and S7 Genymotion Emulator)
  • Android 8.0 (Samsung Galaxy S7)

They seem to work with @outaTiME solution (image as marker prop) from above (I didn't test enough yet), but I don't like this solution, because of not being able to specify width/height for the images. I also have hard time positioning the images (again, didn't try enough yet, hoping that the bug with the children images will be solved).

@rahamin1 my snippet works in all iOS / Android versions and the marker behaviour is the same for all versions.

The custom components inside of markers work until version 7 of android (API 24), for higher versions I need to make special handling using the Marker image property.

I didn't try the @adlondon idea, I don't know if it works in all iOS / Android versions.

@outaTiME Thanks. Can you explain the solution for advanced android versions? I see that you are not changing the key and thus not forcing re-rendering... why is that? And I don't see any other difference from older versions...

Also, btw, why don't you use android version but expo version? Won't android version be better if in the future detach your app?

@rahamin1
Like he said, he's using image property, which work fine on later versions of Android. The downside of this solution is that you cannot manipulate image width/height using styles.

As for FastImage library it doesn't support local images from assets:
https://github.com/DylanVann/react-native-fast-image/issues/160#issuecomment-372157050

@jczerniakiev Thanks. I see now. Then it is not useful for me...

Inspired by @rheilgm's suggestion using svg, I took a bit different approach, which seems to be working for Android 7.1+. I've installed react-native-svg and produced this (Image and Text components inside Svg are imported also from svg library):

<MapView.Marker>
   <View>
       <Svg height='65' width='65'>
          <Image width='65' height='65' href={ClusterImage} />
          <Text x='51%' y='60%' textAnchor='middle' fontWeight='bold' fontSize='16'  fill='white'>
               Random text
          </Text>
      </Svg>
   </View>
</MapView.Marker>

href attribute supports local images

I'm experiencing the same issue with custom marker images not rendering on Android -- they work fine on iOS. Using FastImage as noted above and seeing performance improvement on iOS but NO JOY on Android. Simple console.log debugging on the onLoad callbacks shows shows "success" response on iOS
image.
On Android though, there is no "success" response after the request to load
image
Any thoughts or suggestions as to why this might be this case or next steps to debug? Feels like if I can get a "success" response on Android it may solve the image rendering. In fact, there is not even a response on the onError callback either.

What's happening with react-native-maps? As I see something has changed in Android 7.1 and higher, at least it's a bit different experience, some stuff doesn't work with react-native-maps.

  • I cannot get Image to render in custom Callout on Android higher 7.1 (API 25) ... I have the same thing as @YankeeSoccerNut, on 7.0 onLoad, onProgress, onLayout fires but in 7.1 and higher only onStartLoad and then nothing happens... the space where image is supposed to be is just empty

What I've tried:

  • using FastImage, ImageBackground and SVG
  • removing all styles from map
  • setting zIndexes
  • using local image from folder instead of url
  • downgrading, tried 24-28 compile tools (7.0-8.1 Android) with appropriate gradle tools and plugins, tried all major versions of react-native from 0.49-0.55, with appropriate react versions

absolutely nothing worked with 8.0 and 8.1, couldn't display an image in the Callout, of course it worked if i set image instead of marker, even with url ... but every solution worked fine on 7.0... I'm mostly out of ideas at this point

Unrelated to this original issue, I've actually stumbled upon another bug using maps with react-native-gifted-chat... because of react-native-maps can't share position in chat on android higher then 7.1 android, location request times-out, totally frustrating since these two bugs are last major bugs left in my app...

I've got only a few ideas left, like will it be possible to make a clickable overlay-Callout a bit above the marker?

And those who got a working Image in Custom Callout on Android 8.1 what react-native/gradle/buildToolsV/compileSdkV did you use? @jczerniakiev for me it didn't work for some reason, I think it worked on 7.0 android but idk, maybe versions of tools and packages are different

It seems just had to ask and everything got resolved itself somehow... idk maybe some modules or some stuff in caches didn't clean properly or didn't properly install or apply or whatevs, but after a couple of hours after I've asked image started working in my custom callout on map... haven't changed anything in code, just tried different versions but in the end returned to those I started with ...

  • react-native-maps 0.21.0
  • react-native 0.54.4
  • gradle wraper 4.4
  • compileSdk 25/buildTools 25.0.3

@FishButt can you please point out which workarounds/techniques helped you to resolve "image not showing" issue please. It would be very helpful for other users and also for us to find the cause of the bug.

hey @alvelig I fixed the "not showing image" problem on Callouts by this way (just using Webview instead of Image)

var url ='https://.....';
var html = '<img src="'+url+'" width="122" height="75" style="position:absolute; top:0; left:0;"/>';
<Callout>
<TouchableOpacity>
<View style={{height: 75, width:'100%'}}>
    <WebView source={{html: html}} style={{flex:1}} />
</View>
</TouchableOpacity>
</Callout>

I've made something simple like

render(){
  return(
    <MapView
      style={styles.map}
      region={this.state.mapRegion}
      showsUserLocation={true}
      onPress={this.onMapPress.bind(this)}
      >
        {this.renderMapMarkers()}
    </MapView>
  )}


renderMapMarkers() {
  return(
    this.props.activities.map(marker => (
      <MapView.Marker
         key={marker.id}
         style={styles.customMap}
         coordinate={ {
           latitude: marker.location.latitude,
           longitude: marker.location.longitude
         } }
         image={this.getMarker(marker.category)}
      >
// -- Callout --
        <MapView.Callout tooltip={true}>
          <TouchableOpacity
            onPress={() => Actions.viewActivity(marker.id)}
          <ImageBackground
            style={styles.image}
            source={{
              uri: image,
            }}
          />
        </MapView.Callout>
// --
      </MapView.Marker>
    ))
  )
}

Also worked with FastImage, but ImageBackground worked much better on Android 8.0

I wonder if ImageBackground also works for Marker not only for Callout.

That's very interesting. Soon I'll have some time to investigate this effect. Hope we get it solved.

I had absolutely no trouble with marker images on all androids, I'm setting them here

image={this.getMarker(marker.category)}

but it's just a switch that returns require('../dir_to_images/image.png')... If it doesn't work you could try this, worked on some androids, like on 7.0 and 7.1 i think

// -- Callout --
  <Image 
    source={this.getMarker(marker.category)} 
    style={{ width: 40, height: 40 }} />
  <MapView.Callout tooltip={true}>

...
  </MapView.Callout>
// --

I've actually tried passing url to marker, it rendered an image from internet and it always loaded images, on the map as marker, seemingly with no problems, but not in callout ... I've only had problems with images in callouts... actually still, even now ImageBackground is not always getting images before the first click on the callout, sometimes it takes a couple of clicks, map, callout, map, callout... and I'm pretty sure, that while I was using FastImage or ImageBackground, when images didn't load, I didn't catch any onError or onProgress events ... and it's also the best I could get out of 7.0 android or any higher, for now. Only way I've got images to load from "first marker click" is after a couple of app restarts

Thank you very much for this info.

FastImage not working on Android API 27

@outaTiME Fresco still has not fixed the problem, so unfortunately that update will not solve it.

Yeah I still can't get this to work several months later. I've tried everything, including the drawee-debug aar, webview, backgroundimage, etc.. but I can't get my Marker images to display.

EDIT: This is really a problem for us, and it has been for a long time, so we're just going to switch to MapBox.

@wbattel4607 can you try this PR (was merged today, so try master)
https://github.com/react-community/react-native-maps/pull/2320?

@alvelig just tried it, no luck.

no lock either !

@efkan @alvelig just for the sake of providing more information, I am trying this on

Adding the custom drawee-debug module caused the images to appear in the markers _after_ re-rendering the markers in-app. In other words, the images are missing when the map appears for the first time, but when the markers are programmatically removed and re-added to the map, the images appear.

I also tried using the latest code on master, including the PR #2320, but while that may have resolved other problems, this was not one of them.

Beyond this I have no idea what to do, and it's really a major problem for us, as our whole app relies on the images in these markers. At this point we're likely just going to switch to MapBox for better or worse- as we're out of options. I've taken a look through the Fresco code but am still a ways away from even _understanding_ the mechanics of that library- much less finding the solution.

No luck on any of those suggestions.

@ewein @wbattel4607 Did you try @outaTiME solution? Seemed to work for me (although it is not ideal, not being able to set width/height for the images, and positioning the images seemed difficult).

I'm also seeing this issue.

Mention your lib version, react-native version, Android version, and is it a device or emulator.

library = https://github.com/expo/react-native-maps/archive/0.20.1-exp.0.tar.gz#81d607e2d77481c0441aecfdbc303389a34084c0
react-native = https://registry.yarnpkg.com/react-native/-/react-native-0.54.0.tgz#1582cc2b2a639d46e39c44bcc50e051d0061820a
Android = 8.0.0 on the One Plus 3 (1 May 2018 patch level)

It's a real device.

@efkan @wbattel4607 trying to follow the drawee-debug/fresco source approach but getting "A problem occurred starting process 'command 'ndk-build.cmd'" when trying to build it on Windows. Any ideas? Probably something to do with my ndk path but I've followed the instructions and seem to have set things up correctly.

@dancherb yeah I couldn't get it to build either so I used the one pre-compiled by efkan.

https://github.com/react-community/react-native-maps/issues/1870#issuecomment-370751929

Worked for me, thanks a bunch!!

thank god @efkan 's solution worked for me too!

I've found I'm still getting some markers not showing up when there's a lot on the map at once (over 15) - are any of you guys getting this as well? @mursang @efkan @wbattel4607

@wbattel4607 i add that fix, but only work in some android devices.

@luisfuertes yeah, read my previous remark: https://github.com/react-community/react-native-maps/issues/1870#issuecomment-397397682

Anyone managed to use both a custom image marker and a custom callout component?

You can't have both as children to Marker...

After reading through the comments here and trying @efkan 's solution, I'm a little confused as to where to put the .aar file. I don't have a libs folder in projectDir/android/app. Do I have to create it, or is it automatically generated? If I do create it, what else needs to go in it?

Definitely hoping this works. Super annoying bug.

@pianoman730 ,

Yes, you have to create a libs folder manually, if you don't have.
I hope this answer helps you...

@jczerniakiev Solution works fine for me

Android version 8.0.0

....

 import * as svg from 'react-native-svg';
......

renderMarker = pin => {
    return (
      <Marker
        key={pin.id}
        coordinate={pin.location}
        onPress={() => this.showModel(pin)}
        //image={Icons.location}// This is working but large size of image in release apk
      >
        {/* Cause of the new map not loading images issue */}
        {/* <Image style={styles.markerImage} source={Icons.location} /> */}

        {/* import * as svg from 'react-native-svg';
            This is working fine */}
        <View>
          <svg.Svg width="40" height="50">
            <svg.Image width="40" height="50" href={Icons.location} />
          </svg.Svg>
        </View>
      </Marker>
    );
  };
renderCluster = (cluster, onPress) => {
    const pointCount = cluster.pointCount,
      coordinate = cluster.coordinate,
      clusterId = cluster.clusterId;

    const clusterEngine = this.map.getClusteringEngine(),
      clusteredPoints = clusterEngine.getLeaves(clusterId, 100);

    return (
      <Marker
        onPress={onPress}
        coordinate={coordinate}
        key={cluster.clusterId}
        //image={this.state.icon}
        //anchor={{ x: 0.2, y: 0.5 }}
      >
        <CustomMarker
          amount={pointCount}
          icon={this.state.icon}
          text={this.state.name}
        />
      </Marker>
    );
  };
class CustomMarker extends React.Component {
  render() {
    const { fontSize, amount, icon, text } = this.props;
    return (
      <View style={styles.container}>
        {/* <View style={styles.markerImage}/> */}
        <svg.Svg width="50" height="60">
          <svg.Image width="50" height="60" href={icon} />
          {/* <Image style={styles.markerImage} source={icon} /> */}
        </svg.Svg>
        <View style={styles.bottomBubble}>
          <PlainText style={[styles.amount, { fontSize }]}>
            {amount} {text}
          </PlainText>
        </View>
      </View>
    );
  }
}

untitled

@Danushka50 @jczerniakiev not ideal for me as I want to load images from a URL - do you know if react-native-svg supports this?

I was able to render an Image inside a Callout on Android using the WebView method.
However, it only works for remote images and base64 images.
Example:

const imageUri = 'https://blabla.com/bla.png' // remote image works
const imageUri = 'data:image/png;base64.....' // base64 image also works
<View>
<WebView
            source={{uri: imageUri}}
            style={{height: 32, width: 32}}/>
</View>

by setting zIndex of Marker more than MapView, solve my issue..

I updated to RN .56 because of an issue with not being able to make api requests. So after trying @efkan's solution, when I try to render an image in 2 different ways, it either errors out, or crashes. I don't have any styling on the marker or anything, just a plain attempt to render. I updated my app/build.gradle with the recommended settings:

android {
    compileSdkVersion rootProject.ext.compileSdkVersion
    buildToolsVersion rootProject.ext.buildToolsVersion

    defaultConfig {
        applicationId "com.logantransitapp2"
        minSdkVersion rootProject.ext.minSdkVersion
        targetSdkVersion rootProject.ext.targetSdkVersion
        versionCode 1
        versionName "1.0"
        ndk {
            abiFilters "armeabi-v7a", "x86"
        }
    }
    splits {
        abi {
            reset()
            enable enableSeparateBuildPerCPUArchitecture
            universalApk false  // If true, also generate a universal APK
            include "armeabi-v7a", "x86"
        }
    }
    buildTypes {
        release {
            minifyEnabled enableProguardInReleaseBuilds
            proguardFiles getDefaultProguardFile("proguard-android.txt"), "proguard-rules.pro"
        }
    }
    // applicationVariants are e.g. debug, release
    applicationVariants.all { variant ->
        variant.outputs.each { output ->
            // For each separate APK per architecture, set a unique version code as described here:
            // http://tools.android.com/tech-docs/new-build-system/user-guide/apk-splits
            def versionCodes = ["armeabi-v7a":1, "x86":2]
            def abi = output.getFilter(OutputFile.ABI)
            if (abi != null) {  // null for the universal-debug, universal-release variants
                output.versionCodeOverride =
                        versionCodes.get(abi) * 1048576 + defaultConfig.versionCode
            }
        }
    }
}

dependencies {
    compile project(':react-native-vector-icons')
    compile (name:'drawee-debug', ext:'aar')
    api fileTree(dir: "libs", include: ["*.jar"])
    api "com.android.support:appcompat-v7:${rootProject.ext.supportLibVersion}"
    api "com.facebook.react:react-native:+"  // From node_modules
    api project(':react-native-maps')
}

// Run this once to be able to run the application with BUCK
// puts all compile dependencies into folder libs for BUCK to use
task copyDownloadableDepsToLibs(type: Copy) {
    from configurations.compile
    into 'libs'
}

allprojects {
    repositories {
        flatDir {
            dirs 'libs', './libs'
        }
    }
    configurations {
        all*.exclude  module: 'drawee'
    }
}

The error I'm getting is

Error while updating property 'image' of a view managed by: AIRMapMarker

null

abstract method "com.facebook.drawee.controller.AbstractDraweeControllerbuilder com.facebook.drawee.controller.AbstractDraweeControllerBuilder.getThis()"

```import MapView, { Marker } from 'react-native-maps';
import React, { Component } from 'react';
import { View, Image } from 'react-native'
import styles from '../styles'
import { Button } from 'react-native-elements';
import CVTDPin from '../assets/cvtdpin.png'

class MapScreen extends Component {
render() {
const { navigation, color, initialRegion } = this.props
return (
initialRegion={initialRegion}
region={initialRegion}
style={styles.map}
showsUserLocation={true}
>
coordinate={initialRegion}
onPress={() => navigation.navigate('Details')}
pinColor={color}
image={CVTDPin} //This way gives the error above.
>
//Trying this way crashes the app with no errors

    </MapView>

  </View>
)

}
}

export default MapScreen
```

I have tried literally all proposed solutions.
Declaring images before map load, svg, keys, image property, image background child, tracksViewChanges etc. None work.
I use maps 0.20.1 and RN 52.1
In my case when I load map marker is not visible.
If I move map markers become visible and then work. And markers are not rendered only initially first time once in about 10 times (when I refresh data on map).
If user see map he doesn't know that if he drag map markers will appear.

Are there any news on this problem?

@pianoman730 I'm also seeing that same error when using the debug-drawee method on RN 0.56

This is absolutely gating our upgrade to 0.56 so it is very frustrating... is it possible that the .aar that was posted on Google Drive is out of date with the version of Fresco shipped with RN 0.56?

@bbil We'd have to hear from @efkan on that one.

@bbil @pianoman730
It does appear to be the case that the .aar uploaded by @efkan was for an older version of Fresco. React Native 0.56 uses Fresco 1.9.0, so I just built this version from source (he's right, this does take a while), commenting out the same lines, and it seems to fix the issue for my app.

Here's the .aar, if anyone else on RN 0.56 wants to try this fix:
https://drive.google.com/open?id=1Pde3G3Ms9BR4jYSR26GNJ68LUu6LWbez

@iak0 Yeah, that looks like it is working for me. I'm not getting that error anymore and it loads and everything. First time in a long time that the image has been able to appear on the marker! We'll see if it disappears after a while.

Goliath

@pianoman730 sorry far late.

Actually I had share over here the steps how to build drawee.aar in case of need.

However @iak0 had already overcome this job. Thanx Kai Si.

Alexander Oprisnik had reported the visibility issue to Google (issue tracking link)

I guess, we'll need to build drawee file until Google correct or advising something and react-native upgrade Fresco version. Then we'll need to build the file as a workaround for a while to make compatible with problem APIs. This is really a time-consuming problem!

Having the same issue , here how i structure my code :

<Marker>
  <Image/>
  <Callout>
    <View>  
       ...
    </View>
  </Callout>
</Marker>

I also notice the following things :
My app uses multiple routes. In my case images are always showing except the first time I visit the map route. I can't figure out why it always work except the first time I open the map 😕

@dopey2 Seems like it is related to the time it takes for the image to be downloaded : when I open my app, I load a list where logos are displayed, I then open the map and only the images which have been previously loaded on my list can be displayed in the Callout.

Will try to fix this.

I got the same issue with local asset. My component containing it is displayed elsewhere in the app without any glitch. But on map (only Android, targeting API 26), i got a blank area. Tried to used ImageBackground, setting width and height, using few resize modes, anyway.

react-native-maps: 0.20.1
react-native: 0.52.2

capture d ecran 2018-07-27 a 12 46 54

thanks Kai

Goliath

On Tue, 24 Jul 2018 03:58 Kai Si, notifications@github.com wrote:

@bbil https://github.com/bbil @pianoman730
https://github.com/pianoman730
It does appear to be the case that the .aar uploaded by @efkan
https://github.com/efkan was for an older version of Fresco. React
Native 0.56 uses Fresco 1.9.0, so I just built this version from source
(he's right, this does take a while), commenting out the same lines, and it
seems to fix the issue for my app.

Here's the .aar, if anyone else on RN 0.56 wants to try this fix:
https://drive.google.com/open?id=1Pde3G3Ms9BR4jYSR26GNJ68LUu6LWbez


You are receiving this because you are subscribed to this thread.
Reply to this email directly, view it on GitHub
https://github.com/react-community/react-native-maps/issues/1870#issuecomment-407255340,
or mute the thread
https://github.com/notifications/unsubscribe-auth/ATj5b8xnbXNTluy45lxkJCDYZ12jD9Qmks5uJn9igaJpZM4Q-Nkv
.

@goliath45 where should we put this file?

Hi all, I'm using local images (JPG's from an assets directory) inside the marker component with Expo SDK 29 (RN 0.55.4).

The marker images load most of the time, however when they don't load there is no action that will cause them to render (moving the screen doesn't fix this, for example). I have to reload the app to see the images render.

<MapView.Marker key={title} coordinate={coordinates} title={title}>
    <Image source={images.card} style={{ width: 60, height: 60, borderRadius: 50, borderWidth: 3, borderColor: "#fff" }} />
</MapView.Marker>

Is anybody else on Expo experiencing this?

I tried all the workaround (webview, drawee, preload marker before map) nothing work. Do you have other ideas ?

React native : 0.54
React native maps : 0.21
Android : 8.1.0

For the drawee, there are two files posted here. One is for RN .55.4 and the other for .56. You'll need to use those versions to try that aar file fix.

my maps is working now... thank you

Goliath

On Mon, 30 Jul 2018 23:55 pianoman730, notifications@github.com wrote:

For the drawee, there are two files posted here. One is for RN .55.4 and
the other for .56. You'll need to use those versions to try that aar file
fix.


You are receiving this because you were mentioned.
Reply to this email directly, view it on GitHub
https://github.com/react-community/react-native-maps/issues/1870#issuecomment-409024659,
or mute the thread
https://github.com/notifications/unsubscribe-auth/ATj5b7kC8MCWF3KxTYg2D_XZQV-Tjh70ks5uL4DhgaJpZM4Q-Nkv
.

It still won't work for remote urls.

+1

I have had to give up on this due to it's unreliability and revert to the Marker image prop.

https://github.com/react-community/react-native-maps/blob/master/docs/marker.md#marker--component-api

@SKempin, what were you using before?

I'm using the drawee fix and my icons disappeared this morning. It just shows the classic red marker now. Going to have to try something else.

@pianoman730 I couldn't find a fix for this that worked, the Image component only intermittently rendered.

@SKempin Right, I had tried that a while back unsuccessfully. Mine is currently using the Marker image prop and it renders ok and everything, but it's the same issue I've had for about 6 months now, where after a while (maybe a day, maybe a few days) the images don't render anymore and only the markers will show up correctly. I know for a fact that the markers are always rendered, but the images inside the markers for some reason are not guaranteed.

@pianoman730 Thanks, that's not ideal but at least the marker will always render (which is not the case when using an Image inside the Marker component). Hoping for a fix for this issue soon but there doesn't seem to be much traction?

Maybe we could hear from @alvelig to see if there is anything in the works or if we are just left to our own devices.

@efkan Is your drawee fix working for you? Have you had the images disappear from the markers?

@Danushka50 works!

with react native svg

@pianoman730 , I use drawee on RN v53 and _rarely_ images can not appear on the markers.
However I could not find better solution and this is just a workaround.
I've tried on Genymotion and AVD emulators, several Samsung devices and Xperia Z. drawee works on the all Android OSes.

try this one

Michael le Grange

On Wed, 1 Aug 2018 22:10 pianoman730, notifications@github.com wrote:

@efkan https://github.com/efkan Is your drawee fix working for you?
Have you had the images disappear from the markers?


You are receiving this because you were mentioned.
Reply to this email directly, view it on GitHub
https://github.com/react-community/react-native-maps/issues/1870#issuecomment-409705791,
or mute the thread
https://github.com/notifications/unsubscribe-auth/ATj5b-eit_uTk5A3uaelWuCnkBlUqNQRks5uMgtAgaJpZM4Q-Nkv
.

This solution worked for me:

key={this.state.iconLoaded ? key : ${key}_loading}>
if (!this.state.iconLoaded && Platform.OS === "android") {
this.setState({iconLoaded: true});
}
}}/>

@shameemz How thoroughly has that solution been tested? Are there any performance issues? Thanks

now Is there anyone else experiencing this problem? how you fix it?
I stay with it for 5 hours.
how to plz.

+1

คึมายากคักแท้ละห่วย โพ้ดโพ บักโมบักแตง.

@SKempin Its works with a light flickering! I understood there might be a performance issue because of unnecessarily changing the state. But I couldn't find any other solution for this.

There are two ways I test by recommendation.
Good work.

Thx. @elieteyssedou
1. Use a custom component for my image with react-native-svg

Thx. @Afalook
2. Use Webview render html.

ex.

    <Callout tooltip={false} >
            <View style={{ width: 250, height: 250 }}>
                       <WebView
                               source={{
                                        html: `<img src="http://cuve-stockage-process-eta.com/wp-content/uploads/2018/05/test.png" width="250" height="250"/>`,
                                }}
                        />
              </View>
   </Callout>

It work!!

I used the first solution to this problem.

Nothing works for me, i think we need to wait news from facebook/fresco team 😞

@ccoeder I've started using the image prop on the marker itself.

https://github.com/react-community/react-native-maps/issues/1870#issuecomment-409598283

@SKempin I need to use custom markers, so its not working for me 😢

Just as an FYI, I've been dealing with this issue for about 6 months now and haven't found anything to be a permanent solution until now. Using the image prop, the image would disappear after a while leaving just the normal pin marker. I couldn't get embedding an Image in a View in <Marker></Marker> to work for whatever reason. So this solution, granted, it's a workaround, but it's turning out to be the best solution for me.

I edited my images in gimp and saved them out as .svg's and then followed this tutorial. It covers everything you need to get this to work, but if there are questions I'm happy to answer them. In my code, I used it as

<Marker
   //other marker props
>
   <View>
      <Icon name='iconName' size={40} color={color} />
    </View>
</Marker>

and it's worked like a charm. I can use the same icon but change the color and I haven't really noticed a performance issue at all either. Hope this helps.

p.s. I did try @efkan's solution with building fresco from source as well. So combining that with this may have made a difference, but I don't think so because it's not using the image prop from Marker nor using Image in Marker. This should be a standalone solution.

@pianoman730 Thanks, I will attempt this. How frequently did you experience the image prop not rendering the image? When this happened did it always fall back to a marker (rather than nothing being rendered on the map at all)? Thanks.

@SKempin The image prop would always render for like a day or two. But in reopening the app again it would permanently fall back to the regular marker and would not render an image again until I reinstalled. I never had it where it didn't render anything. The default marker pin always shows up for me, just not the image.

@pianoman730 thanks, was this on Android or iOS, or both? Cheers

@SKempin It was just on Android as far as I know. I think generally, this is an android bug.

@SKempin Yes, this is only an Android bug, as it is caused by a problem in https://github.com/facebook/fresco, (https://github.com/facebook/fresco/issues/1445)

Thanks. So where is this original issue at with being fixed?

@SKempin it has been in limbo for a while. Nobody knows how to fix it, and for all intents and purposes the Fresco team have given up on it until somebody submits a PR.

EDIT: I should mention that the issue has been raised with Google but, while they acknowledged it, they have not made any indications regarding its resolution in the past month. https://issuetracker.google.com/issues/111293868

@wbattel4607 Thanks for the update. This is obviously very frustrating as it is a big issue affecting RN maps. Is there any course of action we can undertake to highlight the demand for a fix?

@SKempin the best thing we can do at the moment is "star" the issue on Google's issue tracker so they know to give it higher priority. Go to the issue here https://issuetracker.google.com/issues/111293868 and press the little ✩ to the left of the title.

Got blocked on this upgrading to RN 57 (0.57.0-rc.3). We had the drawee workaround in place for 55.4, but that stopped working after the upgrade. I went ahead and rebuilt Fresco following @efkan 's steps and this seems to have worked.

Here's the latest aar build ([email protected]) with that patch: https://github.com/FLGMwt/react-native-map-image-issue/blob/9a85d729a26a6525ba2f5a5c1fe7ed347b0e5c7d/android/app/libs/drawee-debug.aar

Hey guys Anyone still facing this issue I have a workaround.. Not sure if its a good one..

Use react-native-svg to render the image inside and Svg component.

`import React from "react";
import Svg, { Image } from "react-native-svg";

const Redmarker = props => (

x="0%"
y="0%"
width="45"
height="70"
preserveAspectRatio="xMidYMid slice"
opacity="1"
href={require('../../../assets/icons/marker.png')}
/>

);

export default Redmarker;
`

and then use this component instead of Image element

@SKempin @wbattel4607

Any update?

@decodez Thanks. So far I haven't experienced any issues when using the image prop on the marker element, but I know this is reported to be unreliable too. Will try your approach if I start experiencing issues.

@pianoman730

Using the image prop makes icon sizes unpredictable, especially when using code-push. But using an Svg Image from react-native-svg instead of Image seems to work:

import * as React from 'react'
import Svg, { Image } from 'react-native-svg'

const MapMarkerImage = props => (
  <Svg width={props.width} height={props.height}>
    <Image href={props.source} width={props.width} height={props.height} />
    {props.children}
  </Svg>
)

MapMarkerImage.defaultProps = {
  children: null,
}

export default MapMarkerImage

Then:
<MapView.Marker coordinate={{latitude: 0, longitude: 0}}> <MapMarkerImage source={icon} width={50} height={50} /> </MapView.Marker>

(tested on android 26 and ios)

Good new guys. I have investigated the problem, and found out that it is based actually on two separate problems. And I've created two separated PRs which fix the problem.

No need for SVG or other hacks anymore. Just wait for them to be merged in, and for a new version to come out.

In the meantime, you could point your package.json to my branch, which includes my other pending PRs also (#2445, #2390, regarding coordinate<->point conversion).
package.json "react-native-maps": "git+https://github.com/danielgindi/react-native-maps.git#merged",

Merged to master. Please, everybody to whom may concern pull master and test if it resolves the issue.

Are you going to publish a new version?

@ccoeder Only after tests confirm ok

I've left some feedback on the PR (https://github.com/react-community/react-native-maps/pull/2478#pullrequestreview-153587452), should we continue conversation there or here?

\react-native-maps\lib\android\src\main\java\com\airbnb\android\react\maps\AirMapView.java:192: error: cannot find symbol
    attacherGroup.setOverflow(ViewProps.HIDDEN);
                                       ^
  symbol:   variable HIDDEN
  location: class ViewProps

I got this error.

unfortunately work-around in last edit of this comment did just work on Android 6 but using react-native-svg library which also can handle images like *.png did fix the problem on all versions.

import React, { Component } from 'react';
import {
  View,
  Text,
  ImageBackground,
  StyleSheet
} from 'react-native';
import MapView, { Marker } from 'react-native-maps';

import Svg, { Image } from 'react-native-svg'

export default class CustomMarkerUpdate extends Component {
    render() {
        return (
            <Marker
                coordinate={{
                  longitude: -67.23,
                  latitude: -35.23,
                }}>
              <View style={{
                flexDirection: 'row', width: 140, height: 60,
                borderRadius: 70, backgroundColor: 'orange' }}>

                <Svg width={50} height={50}>
                    <Image
                        href={{uri: 'http://sample.com/images/sample.png'}}
                        //href={require('./assets/marker.png')}
                        width={50} height={50} />
                </Svg>

              </View>
            </Marker>
        );
    }
}

@zagoa and other experiencing problems with the last PR pull master again please. It was fixed in https://github.com/react-community/react-native-maps/commit/710dca49a515f0f781f51fcc6997af43da9923cc

i am having this problem too.android

@lastpeony which problem? Did you pin your react-native-maps to master?

trying this out right now, just to confirm (because I have never done this before) I just have to run npm install git+https://github.com/react-community/react-native-maps.git from my project and compile+run it as usual right?

UPDATE:
getting this error

C:\Users\Admin-ESS\mapTest\android\app\src\main\java\com\maptest\MainApplication.java:6: error: cannot find symbol
import com.airbnb.android.react.maps.MapsPackage;

Did I do it wrong? lol
for some reason this 'com.airbnb.android.react.maps' path is an empty file in android folder I got from installing with the above method..

I'm not sure how npm install will treat it, as it won't know to name it react-native-maps. Just go to your good old react-native-maps reference in package.json, and replace the version with a git url. Then run npm install

@danielgindi npm installing it the way I mentioned results in changes to package.json too just like the way you suggested. my way is just doing it backwards i guess:

"dependencies": {
"react": "16.3.1",
"react-native": "~0.55.2",
"react-native-maps": "git+https://github.com/react-community/react-native-maps.git"
}

screenshot_1536738948

<View style={{ flex: 1, justifyContent: 'center', alignItems: 'center' }}>
        <Text>Test Map</Text>
        <Animated
          provider={PROVIDER_GOOGLE}
          region={this.state.region}
          style={styles.map}
          onRegionChange={this.onRegionChange.bind(this)}
        >
          <Marker title={'Test'} description={'You are here'} coordinate={{
            latitude: -6.2261,
            longitude: 106.8400
          }}>
            <Image source={require('./personPin.png')} style={{ width: 40, height: 40, resizeMode: 'contain' }} />
          </Marker>
          <Marker title={'Office'} description={'Office is here'} coordinate={{
            latitude: -6.2264,
            longitude: 106.8323
          }} >
            <Image source={require('./pinTrans.png')} style={{ width: 40, height: 40, resizeMode: 'contain' }} />
          </Marker>
          <Circle center={{
            latitude: -6.2264,
            longitude: 106.8323
          }} radius={700} strokeColor={'#1C86EE'} fillColor={'#1C86EE80'} />
        </Animated>
      </View>

Got it to work on Android simulator Nexus 5X API 24!!
Just had to delete node_modules and npm install again.

Thanks man!
When should I expect a release so that I can update my project dependencies?

So relieving to see the markers finally working on Android right? It's so frustrating developing on Android, and with React Native specifically. As they have so many challenges implementing simple stuff on Android that is just basics with iOS.

A big thank you to @danielgindi and all people who helped with the fresco workaround, a big issue seems to be finally resolved 🙏

So I believe we can FINALLY close this issue!

How fix it finally? I delete node_modules and did yarn install but bug in Android continue
Edit: react-native-maps v 0.21.0
Edit2: Ok, only fix with "react-native-maps": "git+https://github.com/react-community/react-native-maps.git".

Thanks for fix!

@alvelig @danielgindi the PR solves the android custom marker problem but i'm noticing a constant increase of memory and CPU usage (Android Studio Simulator: 188% CPU and my PC fan going crazy. Real Device: the garbage collector logs memory allocation warnings one time per second).

@leolusoli You should set tracksViewChanges to false after the image is loaded/rendered, like you do in iOS. It has the same behavior now. You could do it in the onLoadEnd or onLoad/onError callbacks of the Image.
For markers that do not have images inside them, set tracksViewChanges to false in the componentDidUpdate method of the Component.

I am still having a problem with this. I deleted node_modules and ran npm install

<MapView
      style={{
          position: 'absolute',
          top: this.props.screenProps.state.searchFilter.length === 0 && Object.keys(this.props.screenProps.state.filter).length === 0 && this.props.screenProps.state.filter.constructor === Object ? 100 : 150,
          left: 0,
          right: 0,
          bottom: 0,
        }}
      initialRegion={{
        latitude: global.lat,
        longitude: global.lon,
        latitudeDelta: 0.0922,
        longitudeDelta: 0.0421,
      }}
      showsUserLocation={true}
      followsUserLocation={false}
      showsMyLocationButton={true}
      loadingEnabled={true}
      onLongPress={()=>this.setState({deals:[]})}
      >
      {this.props.screenProps.state.filteredDeals.map(marker => (
        <Marker
          key={marker.key}
          coordinate={{
            latitude: marker.lat,
            longitude: marker.lon,
          }}
          onPress={() => this.showAllDeals(marker.business_id)}
        >
          <Image
            style={{height: 40, width:40}}
            source={{uri: marker.icon}}
          />
        </Marker>
        ))}
      </MapView>
"dependencies": {
    "fbjs": "^0.8.16",
    "geolib": "^2.0.24",
    "moment": "^2.22.2",
    "prop-types": "^15.6.1",
    "react": "^16.3.1",
    "react-moment": "^0.7.9",
    "react-native": "^0.55.3",
    "react-native-actionsheet": "^2.4.2",
    "react-native-elements": "^0.19.1",
    "react-native-fbsdk": "^0.7.0",
    "react-native-firebase": "^4.0.7",
    "react-native-google-signin": "git+https://github.com/invertase/react-native-google-signin.git#v0.12.2",
    "react-native-maps": "git+https://github.com/react-community/react-native-maps.git",
    "react-native-modal-overlay": "^1.2.3",
    "react-native-phone-call": "^1.0.8",
    "react-native-root-toast": "^3.0.1",
    "react-native-vector-icons": "^4.6.0",
    "react-navigation": "^1.5.11",
    "react-redux": "^5.0.7",
    "redux": "^4.0.0",
    "redux-form": "^7.3.0",
    "rn-sliding-up-panel": "^1.2.1",
    "update": "^0.7.4",
    "validator": "^9.4.1"
  }

Run yarn cache clean or npm cache clean then run yarn upgrade react-native-maps or npm update react-native-maps

For what its worth my Image's now display correctly. Thanks for the fix!

Still no.

Could it be because I'm using an external image?

Maybe. Try it with a local one.

Still no. But i guess that's a good thing as I really need external images to work.

<MapView
      style={{
          position: 'absolute',
          top: this.props.screenProps.state.searchFilter.length === 0 && Object.keys(this.props.screenProps.state.filter).length === 0 && this.props.screenProps.state.filter.constructor === Object ? 100 : 150,
          left: 0,
          right: 0,
          bottom: 0,
        }}
      initialRegion={{
        latitude: global.lat,
        longitude: global.lon,
        latitudeDelta: 0.0922,
        longitudeDelta: 0.0421,
      }}
      showsUserLocation={true}
      followsUserLocation={false}
      showsMyLocationButton={true}
      loadingEnabled={true}
      onLongPress={()=>this.setState({deals:[]})}
      >
      {this.props.screenProps.state.filteredDeals.map(marker => (
        <Marker
          key={marker.key}
          coordinate={{
            latitude: marker.lat,
            longitude: marker.lon,
          }}
          onPress={() => this.showAllDeals(marker.business_id)}
        >
          <Image
            style={{height: 40, width:40}}
            source={require('../../../assets/whatelse_icon.png')}
          />
        </Marker>
        ))}
      </MapView>

The image is for sure there, as its clickable. It's just invisible.

@bmkopp10
It does work with external images too, no problem.

Try with "react-native-maps": "git+https://github.com/danielgindi/react-native-maps.git#merged",, as it has some performance improvements, and has a new redraw() method on the marker to manually tell it to redraw, which gives complete control over performance.

You should set onLoad event on your Image, and do two things with that:

  1. Validate that the event is actually called (before this PR it was not!)
  2. If/when onLoad kicks in - call redraw() on the Marker and let's see what happens. (You will have to keep the ref to the marker)

@bmkopp10 Have you considered checking the styling? maybe add resizeMode: 'contain' or something like that? if you said image is clickable but just not visible it might be that the image was cropped weirdly?

@danielgindi thanks again for making it work AND making PR for performance improvement as well! :D

@danielgindi thanks for the advice. I tried to solve this morning but the performance issue still present.

My package.json dep is:

"react-native-maps": "git+https://github.com/react-community/react-native-maps.git"

Here's my custom marker codebase:

class BubbleMarker extends Component {
  constructor(props) {
    super(props)

    this.state = {
      tracksViewChanges: true
    }

    this.onPress = this.onPress.bind(this)
    this.stopTracksViewChanges = this.stopTrackViewChanges.bind(this)
    this.startTracksViewChanges = this.startTrackViewChanges.bind(this)
  }

  shouldComponentUpdate(nextProps, nextState) {
    return (this.state.tracksViewChanges && !nextState.tracksViewChanges)
  }

  onPress() {
    this.props.onPress(this.props.data.objectId)
  }

  stopTracksViewChanges = () => this.setState({ tracksViewChanges: false })

  startTracksViewChanges = () => this.setState({ tracksViewChanges: true })

  render() {
    const { data, profileImage } = this.props,
          image = profileImage || ENUMERATOR_BUBBLES_TYPE[data.type].image

    return (
      <Marker identifier={this.props.identifier} coordinate={this.props.coordinate} tracksViewChanges={this.state.tracksViewChanges}>
        <View style={styles.bubbleMarkerContainer}>
          <ProgressCircle
            radius={20}
            borderWidth={4}
            percent={Number(this.props.perc)}
            color={ENUMERATOR_BUBBLES_TYPE[data.type].color}
            shadowColor={ENUMERATOR_BUBBLES_TYPE[data.type].backgroundColor}>
            <View style={styles.bubbleImageContainer}>
              <Image
                source={image}
                resizeMode={'cover'}
                style={styles.markerIcon}
                onLoadEnd={this.stopTracksViewChanges}
                onLoadStart={this.startTracksViewChanges} />
            </View>
          </ProgressCircle>
        </View>
      </Marker>
    )
  }
}

@leolusoli try to delete node_modules and reinstall

@luisfuertes nada

@danielgindi I also try to use git+https://github.com/danielgindi/react-native-maps.git#merged. The CPU load is correct but the markers with external images aren't visible (but tappable).

@danielgindi setting an interval between onLoadEnd and this.setState({ tracksViewChanges: false }) solves my problem. (onLoadEnd isn't very accurate?)

Thanks for the great effort.

@leolusoli weird, this could be a case of a race condition (which I haven't met actually). I imagine that if the tracksViewChanges is actually set to false before the next drawing frame is called - it wouldn't draw. You could eliminate this either with a timeout - which is a hack and won't be stable, or with a redraw call along with the setState.

I'm considering now that maybe when setting tracksViewChanges: false - it should always let it render one more time to account for this.

@leolusoli Try to delete node_modules and npm i again. Then test it without the timeout hack. I've added a "last render" frame, that only happens if tracksViewChanges was true and toggled to false.

@danielgindi it works without setInterval now.

onLoad isn't even being called ... I also tried onLoadStart, still nothing. Images work perfect on iOS.

{this.props.screenProps.state.filteredDeals.map(marker => (
        <Marker
          key={marker.key}
          coordinate={{
            latitude: marker.lat,
            longitude: marker.lon,
          }}
          onPress={() => this.showAllDeals(marker.business_id)}
        >
          <Image
            style={{height: 40, width:40}}
            source={{uri: marker.icon}}
            onLoadStart={()=>alert('test')}
          />
        </Marker>
        ))}

Maybe this will help? I tried using react-native-elements Avatar instead of react-native Image

{this.props.screenProps.state.filteredDeals.map(marker => (
        <Marker
          key={marker.key}
          coordinate={{
            latitude: marker.lat,
            longitude: marker.lon,
          }}
          onPress={() => this.showAllDeals(marker.business_id)}
        >
          <Avatar
            small
            rounded
            source={{uri: marker.icon}}
            //onPress={() => console.log("Works!")}
            activeOpacity={0.7}
          />
        </Marker>
))}

And I get this...
image

Seems like it just hates the url? I noticed I'm the only one who's maping my markers. Could that be the problem?

To further clarify, I have other components in the app that map images the same way. Those images work perfectly fine. So it's not a problem with the url. I also tried using a local image in the mapped marker.

@bmkopp10 try the git version

Still no. In addition to trying the new git version, I also tried it without mapping the markers. I tried it with one static marker and its still not working.

<Marker //key={marker.key} coordinate={{ latitude: this.props.screenProps.state.filteredDeals[0].lat, longitude: this.props.screenProps.state.filteredDeals[0].lon, }} onPress={() => this.showAllDeals(this.props.screenProps.state.filteredDeals[0].business_id)} > <Image resizeMode={'cover'} style={{height: 40, width:40}} onLoadStart={()=>alert('test')} source={{uri: 'http://icons.iconarchive.com/icons/designbolts/free-multimedia/1024/Photo-icon.png'}} /> </Marker>

The invisible marker is clickable. onLoadStart is never called. I delete node modules and run npm install after every new pull, I've cleaned my build a billion times and cleaned the gradle a billion and 1 times lol.

As far as I remember, we don't support remote images for markers. Correct me if I'm wrong.

@alvelig We can use remote images with custom views. But I didn't test it with the latest update. Example:

<Marker key={data.id || Math.random()} title={data.name} coordinate={data.location}>
      <View style={Styles.container}>
        <Image
          source={{
            uri: data.image,
          }}
          style={Styles.image}
        />
      </View>
</Marker>

@danielgindi mentioned that it should work. Though, you're right, I did see the documentation states that it is not supported.

However.

1) Image onLoad is never called on Android (both remote and local), which leads me to believe that its not a problem with the source. It's called perfectly fine in iOS.
2) The remote images display perfectly fine on iOS, though I'm not using Google Maps on iOS, so maybe that could affect it?
3) Local images aren't working anyways on Android, yet works on iOS

<Marker
          //key={marker.key}
          coordinate={{
            latitude: this.props.screenProps.state.filteredDeals[0].lat,
            longitude: this.props.screenProps.state.filteredDeals[0].lon,
          }}
          onPress={() => this.showAllDeals(this.props.screenProps.state.filteredDeals[0].business_id)}
        >
          <Image
            resizeMode={'cover'}
            style={{height: 40, width:40}}
            onLoadStart={()=>alert('test')}
            source={Image}
          />
</Marker>

{Image} is a local image that works on iOS but not Android

@bmkopp10 hmm...
Anybody else with the same issue on master?

I would consider myself an average coder and I'm relatively new to react. So there could easily be something I'm missing. However, I've read over my code, as well as others code hundreds of times to see if theres something I'm missing. It'd be one thing if only local images were working, but since no images are working I'm hoping I'm just missing something super basic?

Are there any dependencies I should have? Or react versions that could clash?

@bmkopp10 you need to checkout master branch into your node_modules/react-native-maps. Either manually, or via package.json:

    "react-native-maps": "https://github.com/react-community/react-native-maps.git",

My current version is

"react-native-maps": "git+https://github.com/danielgindi/react-native-maps.git#merged",

I've tried every version suggested here. I will try the normal version again now.

Still not working with master. I deleted node modules and ran npm install, cleaned the gradle, cleaned the build, deleted the app from my emulator and re-installed.

"dependencies": {
    "fbjs": "^0.8.16",
    "geolib": "^2.0.24",
    "moment": "^2.22.2",
    "prop-types": "^15.6.1",
    "react": "^16.3.1",
    "react-moment": "^0.7.9",
    "react-native": "^0.55.3",
    "react-native-actionsheet": "^2.4.2",
    "react-native-elements": "^0.19.1",
    "react-native-fbsdk": "^0.7.0",
    "react-native-firebase": "^4.0.7",
    "react-native-google-signin": "git+https://github.com/invertase/react-native-google-signin.git#v0.12.2",
    "react-native-maps": "https://github.com/react-community/react-native-maps.git",
    "react-native-modal-overlay": "^1.2.3",
    "react-native-phone-call": "^1.0.8",
    "react-native-root-toast": "^3.0.1",
    "react-native-vector-icons": "^4.6.0",
    "react-navigation": "^1.5.11",
    "react-redux": "^5.0.7",
    "redux": "^4.0.0",
    "redux-form": "^7.3.0",
    "rn-sliding-up-panel": "^1.2.1",
    "update": "^0.7.4",
    "validator": "^9.4.1"
  }
}

@bmkopp10 it could be an issue with a specific Android version. Especially if onLoad is not called, because that means that visibility callback on the actual view was not called, and Fresco did not initiate.

It’s possible that the technique used to solve this needs some tweaking on specific Android versions (Or just on older versions).
And if so- I’ll try to improve on that as it might affect me too.

It could also be caused by an older RN version, as I tested on RN 0.56 and 0.57.

So please add some more info (and maybe try your code on latest RN with several android versions on the emulator)

I tried updating my RN version and all hell broke loose. Could you please tell me what Android versions it works on for you? I can test it on those versions and then i'll go from there.

It works with Pixel XL API 23 !!!!!

It was not working with API 28 & 27

RN 0.55.3

Yes, it is an Android-specific issue only affecting API 25+.

What are my options when releasing this to production? Is this something that will be fixed?

We had to switch to MapBox. I’m sure Fresco will fix this eventually but it may be a while yet.

So does this mean its a dead-end now for API 25+ because we're waiting on fresco?

@rayj10.. For now i think use the SVG workaround.. Its working fine on API 25+

Initially, with TargetSdk 22, custom markers were working for me. But to upload my app, Google made a new rule of Targetsdk 26. Now, custom markers are not working for me on Android when I upgraded my target SDK to 26.

Thinking to use https://github.com/reggie3/react-native-webview-leaflet

Same problem! In my case, I'm try using:

<MapView.Marker
            coordinate={{
              latitude: this.state.myLatitude, 
              longitude: this.state.myLongitude,
            }}
            image={require('./icon.png')}
>

And it worked. But I cannot find a way to resize it.

2018-09-20

To resize you need to re-write it like this.

<MapView.Marker
            coordinate={{
              latitude: this.myLatitude, 
              longitude: this.myLongitude,
            }}
>
    <Image
           style={}
           source={}
     />
</MapView.Marker>

Theres a lot in this thread, but read through it if have any issues as i'm fairly certain its covered almost every possible bug and solution possible to date.

@bmkopp10 That is the problem, <Image /> not working

<MapView.Marker
            coordinate={{
              latitude: this.state.myLatitude, 
              longitude: this.state.myLongitude,
            }}
>
     <Image
           style={{width:10, height:10}}
           source={require('./icon.png')}
      />

     <MapView.Callout tooltip style={styles.mapCallout}>
                <TouchableHighlight onPress= {()=>this.markerClick()} underlayColor='#dddddd'>
                    <View style={styles.calloutText}>
                        <Text>Hello there</Text>
                    </View>
                </TouchableHighlight>
       </MapView.Callout>
</MapView.Marker>

2018-09-20 1

Image in Callout is not working on Android.
So, I decided not to use Image for Android.
I use WebView for now.

_renderImageInCallout(json) {
      if(Platform.OS === 'ios') {
        return(
          <Image
            style={styles.callout_image}
            source={{uri: json.image_url }}
          />
        )
      } else {
        return(
          <WebView
            style={styles.callout_image}
            source={{uri: json.image_url }}
            injectedJavaScript={'document.getElementsByTagName("BODY")[0].style.backgroundColor = "#ffffff";'}
            javaScriptEnabledAndroid={true}
          />
        )
      }
  }

Guys I have’nt yet had the chance to work on the same fix for callouts, especially since I’m using my own callouts in the parent view with custom arrows and not google’s very-limited built-in callouts.
I will eventually work on this too, once we see that we got this to be stable on all Android versions.

Those who wait for a Fresco fix need to understand that that will never happen as there is no issue there.
A solution is implemented here now.

As the fix works for many users here (me included), I need the cooperation of those that did not get it to work.
This means trying with RN 0.56/0.57, on master branch, and starting with tracksViewChanges={true}.
Then listing android versions that do not work under these conditions.
If I manage to debug the situation that still fails- then it will benefit everyone.

For me it works on an api 28 simulator, with 27 set as the target api level, with latest master branch.

To resize you need to re-write it like this.

<MapView.Marker
            coordinate={{
              latitude: this.myLatitude, 
              longitude: this.myLongitude,
            }}
>
    <Image
           style={}
           source={}
     />
</MapView.Marker>

Theres a lot in this thread, but read through it if have any issues as i'm fairly certain its covered almost every possible bug and solution possible to date.

How can we use the custom image and also the "Callout" component to display some data on it.

For me it works on an api 28 simulator, with 27 set as the target api level, with latest master branch.

@danielgindi what exactly works for you, component in marker, or in callout?
For me images still don't work while child in Marker.

                <Marker
                  coordinate={{
                    latitude: location.lat,
                    longitude: location.lng,
                  }}
                  key={i + index}
                  style={s.markerWrapper}
                  onPress={() => { rewardsUI.showCarousel(item.brand); }}
                >
                  <Image
                    source={{ uri: item.brand.logoPictureUrl }}
                    style={{ width: 40, height: 40 }}
                  />
                </Marker>
"react-native-maps": "^0.21.0",
"react-native": "0.56.0"

Device: Honor 9, android 8.0

@2vm "react-native-maps": "^0.21.0", that's not the last master, you need to specify the git url

For those who are struggling with rendering remote image inside the Marker on Android.
Here is my solution (https://github.com/brmk/xendera-test):
For me the problem was that onLoad event for the Image inside Marker is never called. I decided to change Image to WebView redrawing marker on WebView onLoad event: https://github.com/brmk/xendera-test/blob/master/src/components/ImageMarker/ImageMarker.android.js
https://github.com/brmk/xendera-test/blob/master/src/components/ImageMarker/ImageMarkerContainer.android.js

@brmk Your solution work perfectly

react-native-maps 0.22 fixes this :)

Yes there is a release, everyone can switch to using latest version instead of directly referencing my branch.

I still have this same issue on react-native-maps 0.22 and react-native 0.57.4. Is should I resort to the webview, or is there something else I can try?

Look at the latest comments, and try to diagnose your problem accordingly. Use tracksViewChanges, and also check that your view is correctly loading when outside of a marker.

If the problem persists, try testing on different android versions (although I didn't encounter a problem in any version that I tested >= 6.0)

The problem persists both when using tracksViewChanges={true} AND {false}. When closing the callout and opening again, the image sometimes does show, sometimes it takes another try. Not at my work PC right now so not entirely sure what version of Android I'm running, but I'm sure it's at least >= 6.0, on an emulator.

The solution is currently for markers only. I haven't figured out a good enough way to do this for callouts yet.
Anyway because I had to have more complex views in my callouts, including shadows etc, and Google's callouts misbehaving - I just created a callout view that I present when tapping a marker (and then deselecting the marker on iOS).
This means that I don't really have an incentive to research that anymore, since I have a nice RN based callout, and not google's crap.

@danielgindi Can you share how you made that RN based Callout view? I'm dealing with a fairly complex Callout on my project and I'm running into the Image rendering problem.

I still see it on:
react-native: 0.57.4
react-native-maps: 0.22

It looks like it depends from platform. My Callout works ok on android 6.0.1 and on 7.0, but does not work on 8.0

I'll put a gist of it here:
https://gist.github.com/danielgindi/922ef5550c6f0de002e469dbd2a49b37

Note that I replaced my own implementation of a "native button" with TouchableNativeFeedback, so it might break something - you'll need to test it. It's a copy paste from my project.

Usage might be something like this:

let position = await this._refs.map.pointForCoordinate(coordinate);

<CalloutView
        {...this.props.calloutProps}
        style={someStyle}
        onPress={this.props.onPress}
        parentLayout={this.state.mapViewLayout}
        position={position}
        arrowColor='#d3403e'
        arrowSize={9}>
   ... content here ...

Add onLayout to the MapView, keep it in state - and pass to the callout (it helps it deduce position and max size correctly).
Put the MapView and the CalloutView inside the same component, so you have the same x/y axis.
What I do is add a state variable to the view hierarchy besides the MapView, and that variable starts as null. When there's an onPress on the marker, I setState and set that variable to a CalloutView template.

I pampered you, it’s with arrows and all.

@danielgindi Thanks a lot! I will take a look.

Hi everyone.

So it looks like images aren't rendering in the Callout components if you don't set the tooltips prop to true. As per the documentation, _"If true, the child views can fully customize their appearance, including any "bubble" like styles."_

Im on RN 0.57 and react-native-maps 0.22.1

Cheers!

Setting tooltips to true is known not to be a solution @faltech

Hmm it's not known so that's why I mentioned it as it fixed my issue. I had an empty all white callout, but then set the tootltips prop to trye and it then showed my image inside the callout. Perhaps it's just my config.

What version of Android are you running it on < 8.0?

Since you say its working for you, why don't you post your config or something to help everyone else? Seems like you are the only person that has gotten it to work (assuming you are on Android 8.0).

@danielgindi Thanks for your component, would you mind setting up a small example project ? I don't understand how to order the components. Should it be:

<MapView>
    <Marker>
        <CalloutView>
            <Image ...>
        </CalloutView>
    </Marker>
</MapView>

? What is mapViewLayout ?

<View style={{width: '100%', height: '100%'}}>
  <MapView
    onLayout={event => this.state.mapViewLayout = event.nativeEvent.layout}
    ref={ref => this._refs.mapView = ref}>
    {...markers}
  </MapView>
  {this.state.calloutView}
</View>
class YourComponent {
  constructor() {
    this._refs = {};
  }

  async showCallout(coordinate, onPress, children) {
    let position = await this._refs.map.pointForCoordinate(coordinate);

    this.setState({
      calloutView: (
        <CalloutView
                {...this.props.genericCalloutProps}
                style={someStyle}
                onPress={this.props.onPress}
                parentLayout={this.state.mapViewLayout}
                position={position}
                arrowColor='#d3403e'
                arrowSize={9}>
           {children}
         </CalloutView>
      )
    })
  }
}

Thanks!

On Thu, Nov 22, 2018, 15:13 Daniel Cohen Gindi wrote:

onLayout={event => this.state.mapViewLayout = event.nativeEvent.layout}
ref={ref => this._refs.mapView = ref}>
{...markers}

{this.state.calloutView}

class YourComponent {
constructor() {
this._refs = {};
}

async showCallout(coordinate, onPress, children) {
let position = await this._refs.map.pointForCoordinate(coordinate);

this.setState({
  calloutView: (
    <CalloutView
            {...this.props.genericCalloutProps}
            style={someStyle}
            onPress={this.props.onPress}
            parentLayout={this.state.mapViewLayout}
            position={position}
            arrowColor='#d3403e'
            arrowSize={9}>
       {children}
     </CalloutView>
  )
})

}
}


You are receiving this because you commented.
Reply to this email directly, view it on GitHub
https://github.com/react-community/react-native-maps/issues/1870#issuecomment-441042510,
or mute the thread
https://github.com/notifications/unsubscribe-auth/AB0EPD_l3UtQYSojMy_JjBcldimociISks5uxrD0gaJpZM4Q-Nkv
.

I solved this issue by replacing 16-bit gamma integer Image with 8-bit gamma integer Image. It can be done in Gimp, once exporting Image select 8bpc RGBA.

I am facing this issue in samsung Galaxy Tab A but it is working in samsung Galaxy S7

Callout image shows in Samsung Galaxy S7 only when I set zIndex of an image.

I think I found the exact problem. Images are visible below android 8 with zIndex. And in latest versions zIndex in not working.
Any solution?

I found a workaround that is working for me until fix is coming. It seems to be a missing rerender after the loading of the remote image. Basically I load a different set of images and remove the invisible ones.

class CustomMarker extends Component {
  onLoad = () => {
    // Hack to prevent non loading images
    this.showSecondaryMarker = true
    this.forceUpdate()
  }
  render = () => {
    const { logo, coordinate, onPress } = this.props
    return (
      <MapView.Marker
        tracksViewChanges={false}
        coordinate={coordinate}
        onPress={onPress}
      >
        <View onPress={onPress}>
          {!this.showSecondaryMarker && <BakeryMarkerLogo source={{ uri: logo }} onLoad={this.onLoad} />}
          {this.showSecondaryMarker && <BakeryMarkerLogo source={{ uri: logo }} />}
        </View>
      </MapView.Marker>)
  }
}

Hope it helps.

@nenti All you have to do is start with tracksViewChanges=true, and change it to false once onLoad is fired. So instead of using that showSecondaryMarker variable, just toggle tracksViewChanges based on the same criteria

Putting the Image into a WebView and did the trick for me

Putting the Image into a WebView and did the trick for me

@michaelhitzker I am facing the same issue in Android. Are you using http image url in WebView ?? can you please share your code ??

Image Background not working still

Everyone seems to be struggling with this issue here. Let me tell you a proper workaround for this. First of all, using WebView is the only proper solution for this right now. Now rather than using webview for your image. you should be having only webview in the callout and create a proper html for your whole callout view and insert it into your webview. For ex:

<MapView.Callout> <View> <WebView style={{ height: calloutDispensaryMainImageHeight * 1.9, width: calloutDispensaryMainContainerWidth, }} source={{ html: Dispensary(calloutDispensaryMainImageHeight, calloutDispensaryMainContainerWidth, ${url}${cover_image}, name, address, timing, distance, services, ), }} /> <View style={styles.viewOrEnterDispensaryButtonContainer}> <Text style={styles.viewOrEnterDispensaryButtonText}> {strings.dispensariesList.enterDispensary} </Text> </View> </View> </MapView.Callout>


Dispensary file code.

const Dispensary = ( height, width, coverImage, name, address, timing, distance, services, ) => ( <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd"> <html xmlns="http://www.w3.org/1999/xhtml"> <head> <style> * { margin:0; padding:0; } </style> </head> <body> <div> <img src="${coverImage}" alt="main image" width="${width}" height="${height}" /> <div style='display: flex; margin-top: 8px;margin-bottom: 8px;'> <p style='flex: 1; font-weight: bold; font-size: 14px; color:${colors.green}'> ${name} </p> <p style='display: flex; font-weight: bold; font-size: 12px;color:${colors.green};'> <img src="image-server-url"(not local) alt="time" width="16" height="16" style='margin-right:4px' /> ${timing} </p> </div> <div style='display: flex;flex: 1'> <div style='display: flex;flex: 1;'> <p style='flex: 2;font-size: 12px;color:${colors.green};'>${address}</p> <div style='background-color:${colors.green};width:1px;margin-left:8px;margin-right:8px'></div> <p style='flex: 1;display: flex;align-items: center;font-size: 12px;color:${colors.green};'>${${distance.toFixed(1)} mi}</p> </div> <div style='display: flex;flex: 1;justify-content: flex-end;align-items: center;'> ${isServiceAvailable(services, servicesNames.kiosk) ? <img src="image-server-url"(not local) alt="time" width="17" height="23" /> : '<p></p>'} ${isServiceAvailable(services, servicesNames.locker) ? <img src="image-server-url"(not local) alt="time" width="30" height="23" style='margin-left:4px' /> : '<p></p>'} </div> </div> </div> </body> </html> );

I know we are all mobile developers here, but writing a quick html is never a big deal, and in CSS too, there is flex box layout system like react native you can take profit of. So change you thought and use html in webview or wait till this is fixed.

This way, you can have multiple images in you callout, rendering exactly you wants and in the very first time, every image will show up.

In the screenshot below, you can see there are 4 images in one callout and callout in a single webview.

Screenshot_1555911407

Could this work even with local images inside webview?

You have to save your local images somewhere on your server. That's where the solutions start. otherwise, there are ways by which you can show local images in webview too. You have to research that part.

People, what helped me is adding images inside of Text component. Please notice tree:

  • Marker
  • Callout with tooltip prop
  • View
  • View with absolute
  • then an condition, if ios or android for this part
    ios: normal render
    android:
    -Text with style: absolute, minWidth minHeight, positioned with top negative (it will be half of image down)
    -Image with props tracksViewChanges and style with width and height

Hey @nemanjas1, I came across your fix for this issue and it is the only one I have been having any luck with.

Although my image is still cut off horizontally though the middle. Any idea why?

@EvanJMarsh, Can you provide some example of tree @nemanjas1 mention.

The workaround I've found, but using WebView working on iOs and Android
https://snack.expo.io/@arthur322/google-maps-example

Answer of another reply to similar issue, if not the same.

If you use Image Component inside Text component image will be rendered.

https://github.com/react-native-community/react-native-maps/issues/431#issuecomment-524123424

I create a pull request , android google map callout support Image.
https://github.com/react-native-community/react-native-maps/pull/3035

I create a pull request , android google map callout support Image.

3035

It work like a charm. Please merge it!

Guys, what about ImageBackground? Works fine on iOs but on Android it doesn't render...

+

for me issue appears only when tracksViewChanges is passed false to resolved try this
coordinate={marker}
key={index}
onLoad={() => this.setState({ initialRender: false })}
tracksViewChanges={this.state.initialRender}
/>

I create a pull request , android google map callout support Image.

3035

It work like a charm. Please merge it!

@HoangTrongKhanh bạn ơi, phần này họ vẫn chưa merge à bạn?

I got it to work with WebView :)
Thank's a lot to you all!!

I added react-native-webview:

yarn add react-native-webview

(For older android versions I had to add react-native-get-random-values):

yarn add react-native-get-random-values

Then, I imported:

import 'react-native-get-random-values'; import { WebView } from 'react-native-webview';

at the top of my map page to work in older Android versions. And, in my render() function I added:

<WebView source={{ uri: myUri }} style={{ height:50, width:50 }} key={index} />

I created a view in my server to serve an html page with only that image, and, got it to work. Please notice that All images are loaded from server When map is populated with markers (one request for each image).

Hope that helps anybody....

Ok I solve it by putting zero width Image inside the Text Component and a full width version of Image outside The Text.

< Image
source = {{ uri: "https://cdn.pixabay.com/photo/2015/04/23/22/00/tree-736885__340.jpg" }}
style = { styles.companyLogoMarker }
resizeMode = "cover"
    />
    <Text style={styles.markerText}>
        {names?.[0]?.value}
        <Image
            source={{ uri: "https://cdn.pixabay.com/photo/2015/04/23/22/00/tree-736885__340.jpg" }}
            style={{ width: 0, height: 0 }}
            resizeMode="cover"
        />
    </Text>

None of the above workarounds works for me.

Here is the work around i found that forces a rerender. But now it doesnt work on IOS!


`import React, { useState, useEffect, } from 'react';
import { Image } from 'react-native';


const PinMarker = (props) => {

    const [extraData, setExtraData] = useState(false);
    useEffect(() => { setExtraData(true); }, []);

    let pinIcon;

    if (props.category === "music") {
        pinIcon = require('../assets/Pins/MusicPin.png');
        console.log("Marker Category: " + props.category)
    }
    else if (props.category === "meeting") {
        pinIcon = require('../assets/Pins/MeetingPin.png');
        console.log("Marker Category: " + props.category)
    } else if (props.category === "party") {
        pinIcon = require('../assets/Pins/PartyPin.png');
        console.log("Marker Category: " + props.category)
    }

    return (

        <Image
            style={{ maxHeight: 75, maxWidth: 75 }}
            // check for platform here, this is because with android we need to force a rerender
            key={Platform.OS === 'android' ? `${extraData}` : null}
            source={pinIcon}
        />

    )
}


export default PinMarker;`

I tried many things and finally I found a solution. Worked for me on Android. Just putting Image tag inside a Text tag

<Text><Image .../></Text>

@sasan-ebrahimi This does not work for me.

ok finally i got something working. I used @akshaygpta007 method. using webview, html and css.

I created a function that took the object that had the image path as a prop. then passed that in
to the html.

export const EventImage = (event) => {

    var value = `<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd"> 
<html xmlns="http://www.w3.org/1999/xhtml">
   <head>
      <style> * { margin: 0px; padding:0; } </style>
   </head>
   <body>
      <div style=' font-size: 70px '>
         <img  style=' margin: 10 ; width: 100% 'src="` + event.image + `" /> 
      </div>
   </body>
</html> `
    return (value)

};

Then i used the above function as demonstrated in the snippet below. You may have to adjust the size and placement of your photo, but it works for me.

```
export const CustomCallout = (props) => {

return (
    <Card>
        <View>
            <CardItem>
                <Left>
                <WebView style={{ height: 80, width: 80, paddingRight:100 }} source={{
                    html: UserImage(props)
                }} />
                    <Body>
                        <Text>{props.event.host.name}</Text>
                        <Text note>{props.event.host.email}</Text>
                    </Body>
                </Left>
            </CardItem>

Then i just place my custom callout out as follows. I do a platform check because normal images display fine on IOS.

coordinate={{ latitude: event.latitude, longitude: event.longitude }}
title={event.title}
pinColor="#341f97"
icon={FlashOnIcon}
description={event.description}
key={event.id}
onPress={onPinPress.bind(this, event)}

style={styles.plainView}
onPress={onEventCalloutPress}
tooltip={true}
key={event.id}

            {Platform.OS === 'ios' ? (<EventCard event={event} />) : (
              <CustomCallout style ={{height:400}} event={event} />
            )}
        </Callout>
      </Marker>

```

Check this answer 2633

Was this page helpful?
0 / 5 - 0 ratings