Giter Club home page Giter Club logo

mapview's Introduction

Maven Central GitHub License

Looking for the Compose version? Check this out.

MapView

MapView is a fast, memory efficient Android library to display tiled maps with minimal effort.

An example of setting up:

val mapView = MapView(context)
val tileStreamProvider = TileStreamProvider { row, col, zoomLvl ->
    FileInputStream(File("path/{zoomLvl}/{row}/{col}.jpg")) // or it can be a remote HTTP fetch
}

val config = MapViewConfiguration(levelCount = 7, fullWidth = 25000, fullHeight = 12500,
                                  tileSize = 256, tileStreamProvider = tileStreamProvider)
                                  .setMaxScale(2f)

/* Configuration */
mapView.configure(config)

MapView shows only the visible part of a tiled map, and supports flinging, dragging, scaling, and rotating. It's also possible to add markers and paths.

This project holds the source code of this library, plus a demo app (which is useful to get started). To test the demo, just clone the repo and launch the demo app from Android Studio.

MapView supports map rotation

To be consistent with previous versions, this is disabled by default. To enable it, use MapViewConfiguration.enableRotation(). You will find a code example inside the demo RotatingMapFragment.

When enabling rotation, the MapView handles rotation gestures by default. If you only want to rotate the map through APIs, then you should use enableRotation(handleRotationGesture = false). The MapView has a new API setAngle:

/**
 * Programmatically set the rotation angle of the MapView, in decimal degrees.
 * It should be called after the [MapView] configuration and after the [MapView] has been laid out.
 * Attempts to set the angle before [MapView] has been laid out will be ignored.
 */
fun MapView.setAngle(angle: AngleDegree)

Migrating from 2.x.x

3.x.x introduced the following breaking changes:

  • The domain name of the library was changed to ovh.plrapps. MapView is now directly published on mavenCentral.
  • The interface ReferentialOwner has been replaced with ReferentialListener. Instead of expecting ReferentialOwners to supply a default value for ReferentialData, ReferentialListener only has a onReferentialChanged(refData: ReferentialData) method. Migrating to this new interface should be straightforward. There's an example of usage inside the RotatingMapFragment demo.

Installation

Add this to your module's build.gradle

implementation 'ovh.plrapps:mapview:3.1.8'

In addition, update the module's build.gradle file (for each module that uses MapView), as shown below:

android {
  ...
  // Configure only for each module that uses Java 8
  // language features (either in its source code or
  // through dependencies).
  compileOptions {
    sourceCompatibility JavaVersion.VERSION_1_8
    targetCompatibility JavaVersion.VERSION_1_8
  }
  // For Kotlin projects
  kotlinOptions {
    jvmTarget = "1.8"
    freeCompilerArgs = ['-Xjvm-default=all-compatibility']
  }
}

Origin and motivation

As a long time contributor to TileView, I wanted to see the performance we would get using idiomatic Kotlin (coroutines, flows). The result was beyond my expectations. The overall design can be seen here. Special attention has been given to efficiency (using non-blocking algorithm to avoiding thread contention). We get smooth animations and high fps.

Thanks for Mike (@moagrius), as this library wouldn't exist without his first contributions.

Principles

Deep-zoom map

MapView is optimized to display maps that have several levels, like this:

Each next level is twice bigger than the former, and provides more details. Overall, this looks like a pyramid. Another common name is "deep-zoom" map. This library comes with a demo app made of a set of various use-cases such as using markers, paths, rotating the map, etc. All examples use the same map stored in the assets. If you wonder what a deep-zoom maps looks like, you have a great example there.

MapView can also be used with single level maps.

Usage

To use the MapView, you have to follow these steps:

  1. Create a MapView instance
val mapView = MapView(context)
  1. Create a TileStreamProvider. See below for the details.
  2. Create a MapViewConfiguration. See below for the details.
  3. Apply the configuration
mapView.configure(config)

For more insight, you can have a look at the source of the various demos.

Convention

MapView uses the convention that the last level is at scale 1. So all levels have scales between 0 and 1. Even though you don't have to be aware of the details, it's important to know that. For example, if you set the max scale to 2, it means that the last level will be allowed to be upscaled to twice its original size (since the last level is at scale 1). This convention allows for a simple configuration.

Technical documentation

The MapView needs to be configured - more on that below. Once configured, you can do a lot of things with your MapView instance. MapView is a subclass of GestureLayout, which has many features. You can:

  • add listeners to events like pan, fling, zoom..
  • programmatically scroll and center to a position
  • respond to various touch events by subclassing MapView and overload related methods declared in GestureLayout

This list isn't complete. You can explore the capabilities in the source of GestureLayout.

MapViewConfiguration

The MapView must be configured using a MapViewConfiguration. It holds the mandatory parameters to build a MapView.

Then, you can set optional properties by calling available methods on your MapViewConfiguration instance. Here is an example:

val config = MapViewConfiguration(levelCount = 7, fullWidth = 25000, fullHeight = 12500,
                                  tileSize = 256, tileStreamProvider = tileStreamProvider)
                                  .setMaxScale(2f)

See documentation here. Below is a description of mandatory parameters:

levelCount

The provided MapViewConfiguration.levelCount will define the zoomLevels index that the provided MapViewConfiguration.tileStreamProvider will be given for its TileStreamProvider.zoomLevels. The zoomLevels will be in the range [0 ; MapViewConfiguration.levelCount-1].

fullWidth and fullHeight

These are respectively the width and height in pixels of the map at scale 1 (that is, the width and height of the last level). In other words, if you put together all the tiles of the last level, you would obtain a big image. fullWidth and fullHeight are dimensions in pixels of this big image.

tileSize

The size of the tiles in pixels, which are assumed to be squares and always of the same size for all levels. For now, MapView doesn't support rectangular tiles or tiles of heterogeneous sizes.

tileStreamProvider

See the section below.

TileStreamProvider

The MapView will request tiles using the convention that each levels has its tiles organized like this:

MapView isn't opinionated about the origination of tiles. This is the purpose of the TileStreamProvider:

fun interface TileStreamProvider {
    fun getTileStream(row: Int, col: Int, zoomLvl: Int): InputStream?
}

Your implementation of this interface does the necessary coordinate translation (if required). This is where you do your HTTP request if you have remote tiles, or fetch from a local database (or file system).

Tile caching

The MapView leverages bitmap pooling to reduce the pressure on the garbage collector. However, there's no tile caching by default - this is an implementation detail of the supplied TileStreamProvider.

ReferentialListener

When the scale and/or the rotation of the MapView change, some of the child views might have to change accordingly. For that purpose, you can register a ReferentialListener to the MapView.

A ReferentialListener is an interface:

fun interface ReferentialListener {
    fun onReferentialChanged(refData: ReferentialData)
}

And ReferentialData holds several useful properties:

data class ReferentialData(var rotationEnabled: Boolean = true,
                           var angle: AngleDegree = 0f,
                           var scale: Float = 0f,
                           var centerX: Double = 0.0,
                           var centerY: Double = 0.0) : Parcelable

A ReferentialListener should be registered to the MapView:

mapView.addReferentialListener(refOwner)
// If you need to unregister it:
mapView.removeReferentialListener(refOwner)

From inside your ReferentialListener implementation, you can have any logic you want. You can rotate some markers, rotate complex views taking into account the centerX and centerY properties, etc.

There's an example of usage at RotatingMapFragment.

Create a deep-zoom map

If you don't already have such a map and you need to make one from a big image, follow this tutorial.

How do I..

Follow this cheat sheet.

API documentation

API documentation has its own wiki page.

mapview's People

Contributors

artudi54 avatar kuromimi avatar p-lr avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar

mapview's Issues

Turn off fade anination on tiles

Hi, @peterLaurence, again)

I found that TileCanvasView that performs that animation is internal. Could you recommend the best way to manage how tiles appear or how to remove the animation at all?

Non-existent zoom on an overlay.

Hi, I try to display a background with an overlay, if the 2 have the same zoom availability I have no problem but I would like that if one of the 2 maps does not have a zoom that it continues to be displayed but with the old zoom.
The problem is that I do the overlay in getTileStream, maybe it's a mistake?
Can we find the previous zoom and row and col value in the getTileStream method?
I'm using a tile database and I don't have all the zoom so you can understand my request better.

Thank you in advance for your response

In french

Bonjour, j’essai d’afficher un fond avec une sur-couche. Si les 2 ont la même disponibilité de zoom je n’ai pas de souci mais j’aimerais que si l’une des 2 cartes n’a pas un zoom qu’elle continue a s’afficher mais avec l’ancien zoom.
Le problème est peut etre lié au faite que je fais la sur couche dans getTileStream c’est peut être une erreur ?
Peut on trouver le zoom précédent et la valeur row et col dans la méthode getTileStream ?
J'utilise une base de donnée de tuile et je n'ai pas tout le zoom pour que tu comprennes mieux ma demande.

Merci d'avance de votre réponse

Help needed for displaying single image from Remote

Thanks for the wonderful library. I have used old java tileview library and now happy to use improved Kotlin version of it. I need one help with respect to displaying of a single image from remote. I just have a single image of size 1200 * 900. I would like to display it with zooming enabled. How would i configure it without using deep-zoom map.
My image : http://androidbash.com/data/floor1.jpg
I tried following config and i am unable to load the map.
var tileSize = 1200
val config = MapViewConfiguration(
1, 1200, 900, tileSize, tileStreamProvider
).setMaxScale(4f).setPadding(tileSize * 2).setWorkerCount(16)

Setting minimum scale mode and zooming below FILL equivalent gives scaling issues

When I use MapViewConfiguration.setMinimumScaleMode() with anything other than MinimumScaleMode.FILL and zoom out below where FILL would stop zooming in normal cases the scaling of the map goes crazy.

See example image of a drawing. Notice how the entire lower half of it is stretched to double size in the y axis. Similarly there is some stretching at the right edge of the image as well:
bild

Another example, here we can see duplication in the lower and right part of the image with both correct and streched data shown at the same time:
bild

Similarly I have noticed that when this happens the CoordinateTranslater.translateAndScaleAbsoluteToRelativeY() misbehaves and gives incorrect values.

As soon as you get back within the limits of FILL everything starts working correctly again.

License hinders use in Android applications

As far as I understand, the GNU GPLv3 license requires derivate work (e.g., an Android app using this library) to publish its source code under the same license.

Unfortunately, this is quite troublesome, not only because of politics around app development, but also because it is hard to strictly comply when publishing an Android app, as stated in the Android Open Source Project's license explanation, because the source code is not published along with the app.

The Android Open Source Project proposes to publish libraries under the Apache 2.0 license. As far as I can tell that license is served by including a notice about the library's license in an about page.

If this license is a conscious decision on your part, that's ok! I just wanted to point this out, because I've just come across and started to learn about this issue.

Offset/padding?

Hey!

Turns out, for whatever reasons our tiles have 1 pixel offset on each side, resulting in a 258x258 tile.

Would there be a way to add such offsets? If you dont want to add features in the non-compose version, I fully understand (we will probably switch to it at the end off the year), but could I even do such a thing, without redrawing the bitmaps?

I already need to fork your version anyway, because of the tileSize being the widthXheight for the bitmap, which didnt work.

I found in the mapConfiguration a setPadding, but didnt had any effect.

Problem is, that on high zoom ratio, the images/tiles are not stiched correctly.

BR

No tiles visible, ability to center?

Hi,

I was reading one of your other threads and you mentioned the ability to centre the maps after the config - any chance you could share how to do this please?

Also when loading have to zoom for scroll to start becoming visible?

Here's my config setup

`
val tileSize = 256
val config = MapViewConfiguration(
levelCount = map.levelCount,
fullWidth = map.fullWidth,
fullHeight = map.fullHeight,
tileSize = tileSize,
tileStreamProvider = tileStreamProvider
).apply {
setMaxScale(2f)
setMinimumScaleMode(MinimumScaleMode.FILL)
setPadding(12800)
}

    binding.mapview.configure(config)
    binding.mapview.defineBounds(0.0, 0.0, 1.0, 1.0)

    Timer().schedule(object : TimerTask() {
        override fun run() {
            if (binding.mapview.width != 0 && binding.mapview.height != 0) {
                this.cancel()
                binding.mapview.scrollTo( binding.mapview.width / 2, binding.mapview.height / 2)
            }
        }
    }, 1, 5)`

MarkerView is not removed from the MapView

Hi Peter.

I added a custom marker with an animation but it is not removed from the mapview.

class AnimMarker(context: Context) :  AppCompatImageView(context)

This method is called when the grey star button is clicked.

    private var animMarker : AnimMarker? = null

    private fun addAnimMarker(){
        animMarker = AnimMarker(requireContext()).apply{
            setImageResource(R.drawable.ic_twotone_lens_24)
            val anim = AlphaAnimation(0.0f, 1.0f)
            anim.duration = 1000
            anim.repeatCount = Animation.INFINITE
            anim.repeatMode = Animation.REVERSE
            this.startAnimation(anim)
        }

        mapView.addMarker(animMarker!!, 4096.0, 4096.0)
    }

This method is called when the yellow star button clicked again.

    private fun removeAnimMarker() {
        mapView.removeView(animMarker)
    }

Do you have any clue to solve this?

sample.mp4

Marker callout disappeared when clicking or moving map view

Hello @peterLaurence! Thank you for this great library. It really helped me a lot.
But a marker callout disappeared as soon as I touch a map.
Is there any way that I could keep marker callout view even though I click or move the map?

scrollTo / scrollToAndCenter using different coordinates after scaling

Hi, I'm having an issue once the map has been scaled, calling scrollTo causes the map to jump to a completely different place, depending on how much the map has been scaled.

It looks like this has something to do with setConstrainedScroll being called and the values there being clipped to scrollLimitX/Y

I'm using a single level with min and max limits set

        MapViewConfiguration config = new MapViewConfiguration(
                1,
                PIXEL_WIDTH,
                PIXEL_HEIGHT,
                RemoteTileStream.tileSize,
                tileStreamProvider
        );
        config.setMaxScale(2f);
        config.setMinScale(0.5f);
        config.setTileOptionsProvider(tileOptionsProvider);
        mMapView.configure(config);

I wonder if this setup is correct. I'm also having an issue with defineBounds not having any effect. This isn't a problem, as it's easy enough to calculate the pixels required, but I'm mentioning it in case it's related.

Issue when setting compileSdkVersion to 34

I get this error when I set the compileSdkVersion to 34:
Class 'TileView' is not abstract and does not implement abstract base class member public abstract fun onFling(p0: MotionEvent?, p1: MotionEvent, p2: Float, p3: Float): Boolean defined in ovh.plrapps.mapview.MapView

Map view rotation feature

I am building a POC for Indoor navigation and i came across TIleview as well as MapView. I would like to use Kotlin version. But i did not find demo on having a rotatable map. Is it possible to rotate the map?

What i want is that in my indoor navigation app, based on magnetic field directions, map should get adjusted/rotated in order to show FPP view. (First person perspective view). Do you have any info on how this can be achieved?

Best performance for many markers

Say that you have a map with thousands of markers, are there any best practices for how to handle that to still have good performance?

  • Just let the library handle it (does the library ignore markers that are out of view? other performance improvements?)
  • Manually remove markers that are out of view (will reduce rendering if the library is bad at culling markers, but adds costs in constantly adding/removing items from lists and creating/destroying views)
  • Set markers that are out of view to GONE or INVISIBLE (unknown if this has any effect, again depends on the library)

Possibility to zoom farther out?

Hey!

Would it be possible, to support zooming out? Lets say, I dont have an infinite map, but its limited to a certain area and I want to see the whole area in a view.

But even with zoomLevel0, the space would be too small.

I can also change the code, if the option doesnt make sense for general purposes, but where should I try it?

So it doesnt need load any additional tile, but basically let the zoomlevel going into negative?

Draw polygon

I want to draw a polygonal area, how should I use it?

Zoom-in/out with animation too fast

Quoting @c0dd3vi11 :
I found this: mapView.smoothScaleFromCenter(mapView.scale * 1.5f). And the opposite is mapView.smoothScaleFromCenter(mapView.scale / 1.5f). But when I call the functions too fast then MapView starts blinking.

rectangular tiles

supporting rectangular tiles just like the previous library (TileView).

Support for .png deep zoom map

Currently, i can't seem to use a deep zoom map generated in .png format. I get the following errors:

W/BitmapFactory: bitmap marked for reuse (131072 bytes) can't fit new bitmap (262144 bytes)

Is there no support for .png maps or am i doing something wrong?

class MainActivity : AppCompatActivity() {
    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        setContentView(R.layout.activity_main)

        val mapView = this.findViewById<MapView>(R.id.mapview) ?: return

        val tileStreamProvider = TileStreamProvider {row, col, zoomLvl ->
            try {

                this.assets?.open("tiles/esp/$zoomLvl/$row/$col.png")

            }

            catch (e: Exception) {

                null

            }

        }

        val config = MapViewConfiguration(levelCount = 6, fullWidth = 8192, fullHeight = 8192, tileSize = 256, tileStreamProvider)/*.setMinimumScaleMode(MinimumScaleMode.FILL)*/

        mapView.configure(config)

    }
}

Thanks you.

Min SDK version

Hi, when I tried upgrading to the latest release version of MapView, I noticed that you have increased to minimum sdk version from 23 to 24. I'm currently supporting version 23 with my apps and I was wondering what the reason for the increase was?

BitmapFactory: bitmap marked for reuse can't fit new bitmap

Hello,

I keep getting these warnings, and nothing shows in the MapView on Emulator.

W/BitmapFactory: bitmap marked for reuse (32768 bytes) can't fit new bitmap (65536 bytes)

I reduced my tile size from 512x512 to 128x128 and I still get the same error.

Does anyone know a workaround?

EDIT: by the way I'm migrating from Moagrius TileView which I was able to use th 512x512 tiles with.

can you support Marker Drag?

I like to use your library, I need to make a function, but Marked points cannot be moved by fingers。I want the marker point to move with my finger, as the func 'enableMarkerDrag' in your Mycompose library. can you support it ?

Set initial scale

Hi, thanks for the library.
I'm new to this lib. I have some questions

  1. I want set the map with some initial scale value when it first renders
  2. In addition, I want to run some ValueAnimator to change scale value.
  3. Look at MapMarkersFragment, a callout is added every time marker is clicked. Does the lib remove the callout when tap outside?

Clear memory

Hello, I tried the demo that you provide and I notice that any time a fragment changed the memory of the old map didn't free even when I use the destroy method. Can you give me some feedback.

Refresh map tiles

Hi, is there a way to force refresh the map tiles. Right now, i use redrawTiles when i need a refresh. But it's only trigger a refresh on map zoom/dezoom or on map movements.
So, is it possible to force redraw tiles when the function is called ?
Thanks

Error on zoom near of border

Everithing work fantastic, but when i put a point near of a border, give a distortion when i do zoom in or zoom out

    val config =
        MapViewConfiguration(8, 24000, 22000, 256, tileStreamProvider)
            .setMaxScale(1.2f)
            .setWorkerCount(4)
            .setPadding(256)
            .setMagnifyingFactor(0)
            .setMinimumScaleMode(MinimumScaleMode.FILL)

mpMap.defineBounds(0.0, 120.0, 100.0, 0.0)

point on 71.09375, 91.78125 (near of a border)

Error on zoom out
error-part-1
Error-part-3

zoom in and error show it
Real position of point
error-part-2

BitmapFactory: bitmap marked for reuse

Hello!
i got this error on logcat:
W/BitmapFactory: bitmap marked for reuse (2097152 bytes) can't fit new bitmap (4194304 bytes)
No tiles are shown. Tiles are 32bit png with alpha, Any suggestions? if i converte them to webp they do not work either.
Those tiles does show in ImageView but not in this tile library :S

Thanks!

Displaying multiple maps

Hello, @peterLaurence! Could you help me how to manage maps switching with your MapView? redrawTiles seems to work not correct.

I tried to make three different MapView's. But then I got a problem that sometimes tiles don't draw when I change visibility from View.INVISIBLE to View.VISIBLE for a next MapView.

Blank tiles

Hi

I'm having issues with a number of blank tiles. Sometimes when zooming those tiles get filled in at specific zoom ranges, but most of the time they are blank.
Depending on the map the number of blank tiles ranges between 0 and +-30. For a specific map, the number of blank tiles and the location of the blank tiles are consistent across app restarts.
I'm only using a level count of 1 and no errors are thrown while loading the map and the tiles.

Do you have any idea what could be the cause of this?

Thanks in advance!

bitmap marked for reuse can't fit new bitmap error (100% reproducible) for Remote HTTP mapview

Hello,
With the code below (modified based on RemoteHttpFragment.kt), I got bitmap load error:

URL:https://cyberjapandata.gsi.go.jp/xyz/std/4/3/5.png
bitmap marked for reuse (131072 bytes) can't fit new bitmap (524288 bytes)

As the screenshot, the mid center of the US continental failed to load. I am using MapView3.4.1. Any thoughts?

Screenshot_1666659045

        val tileStreamProvider = object : TileStreamProvider {
            override fun getTileStream(row: Int, col: Int, zoomLvl: Int): InputStream? {
                return try {
//                    val url = URL("https://plrapps.ovh:8080/mapview-tile/$zoomLvl/$row/$col.jpg")
                    val url = URL("https://cyberjapandata.gsi.go.jp/xyz/std/$zoomLvl/$col/$row.png")
Log.d("DDD","URL:"+url)
                    val connection = createConnection(url)
                    connection.connect()
                    BufferedInputStream(connection.inputStream)
                } catch (e: Exception) {
                    null
                }
            }

            fun createConnection(url: URL): HttpURLConnection {
                val connection = url.openConnection() as HttpURLConnection
                connection.doInput = true
                return connection
            }
        }
        val tileSize = 256
        val MAX_ZOOM = 5
        var zoomLevelScale = FloatArray(MAX_ZOOM + 1)
        var scale = 1f
        for (i in MAX_ZOOM downTo 0) {
            zoomLevelScale[i] = scale
            scale = scale / 2
        }

        val config = MapViewConfiguration(
                MAX_ZOOM+1,     // no level=1 map; need plus one level
                8192, 8192, tileSize, tileStreamProvider
        ).setMaxScale(2f).setPadding(tileSize * 2).setWorkerCount(1)
        .setStartScale(zoomLevelScale[4])

        mapView.configure(config)
        mapView.scale = zoomLevelScale[4]
}

ZoomIn/ZoomOut/Rotate programmatically with animation

Hello, @peterLaurence! I got one more problem.

I was trying to make buttons to zoom in/out and rotate back to north-up position.

Zooming in/out.
I found this: mapView.smoothScaleFromCenter(mapView.scale * 1.5f). And the opposite is mapView.smoothScaleFromCenter(mapView.scale / 1.5f). But when I call the functions too fast then MapView starts blinking.

Rotating.
The best way is do mapView.setAngle(referentialData.angle). But this performs without animation. Could you help me how to do it proper with animation?

p.s. Perfect SDK, btw) Thank you for making it!

BufferOverflow on Channel coroutine

Hi,

I'm trying to use the library in a Java Fragment, and I'm getting this error when set configuration to map (mapView.configure(config);)

java.lang.NoSuchMethodError: No static method Channel$default(ILkotlinx/coroutines/channels/BufferOverflow;Lkotlin/jvm/functions/Function1;ILjava/lang/Object;)Lkotlinx/coroutines/channels/Channel; in class Lkotlinx/coroutines/channels/ChannelKt; or its super classes (declaration of 'kotlinx.coroutines.channels.ChannelKt'
at ovh.plrapps.mapview.core.ThrottleKt.throttle(Throttle.kt:21)
at ovh.plrapps.mapview.viewmodel.TileCanvasViewModel.(TileCanvasViewModel.kt:35)
at ovh.plrapps.mapview.MapView.configure(MapView.kt:107)

Redraw map tiles

Hi, is there a way to force refresh the map tiles. For example, when the user changes some point on the tile, I need to redraw it. Recreating the MapView doesn't work for me as there is a lot of logic there. Maybe there is a way to reload the file or canvas or something like that? Thank you

Marker size when changing the zoom level

Hi Peter.

I’ve been developing metro app using your library and I added multiple markers in the map.
But I come across the problem that some markers are overlapped as you can see below images.

What I want is changing the size of a marker along with the zoom level of the map or replace the marker image with other size. Say, if the map is zoomed out, the marker would be getting smaller so a user can click each marker precisely.

It would be great if you have any advice for solving this problem.

zoom_inzoom_out

Setting initial angle and center

@peterLaurence, could you help me again, please?

I got that I can use MapViewConfiguration.setStartScale to initiate the scale. But how to initiate angle and center for map properly?

p.s. I'm storing angle, scale & center between launching and also want a feature to open map positioned properly on the certain map's zone.

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.