-
-
Notifications
You must be signed in to change notification settings - Fork 861
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Map gets rebuild with every frame while navigating #768
Comments
I think maybe you need to be a bit more specific about what problem you are experiencing. I tend to think of it more as 'widgets update when state updates', or you ask them to update. Obviously a simplification, I don't tend to think of 'config', but it may be we sort of mean the same thing. So when there's a map change, there naturally has to be a widget rebuild somewhere (this may be the 'invisible' bit within flutter_map you mean), but I'm not really sure if we're talking about the same thing, or which widgets you are referencing. So I'd try and add a bit more info, what problem you are experiencing, how you are testing that, and what you expect vs what you experience. What do you mean by 'wrong' in your case, what do you specifically mean by 'frame' here. |
Hi ibrierley, thank you for the comment. I edited my post, hopefully my problem gets clearer now. |
I'm just guessing here a bit, so apologies in advance, just thinking out loud. If there are any child widgets that don't need to get rebuilt, could you make them into const widgets ? |
Hi, First: Yes, you are right. I can use const widgets to avoid rebuilding when navigating the map. This works to a certain degree even with the complex Marker widgets i want to use in my real code, which contain animation, pictures etc. I can navigate the map, the markers move along accordingly, show animation, everything's fine there. And the widgets only rebuild when i rebuild them with new data, which is what i want. Without having constructor values (like see below), I almost got it. BUT: Since this only works with const widgets, i don't have the possibility to set the Marker widgets' const compile time constructor values, like the key and callback functions, which i really, really need. Please see the code:
In summary: I cannot initialize the const widget with the values it needs. Probably this is not a too hard problem, but after messing around for a long time I cannot see it anymore... Best regards |
I'm not a coding expert by any means so I might have misunderstood the problem, but have you looked at flutter_map_marker_popup https://github.com/rorystephenson/flutter_map_marker_popup I'm using this to build markers at runtime. Perhaps that could give you a hint. |
Can u try #719 because as far as I remember I took care of that. I mean in master (latest stable) version gestures.dart uses |
@maRci002 The only possibility to avoid Marker rebuild per frame is to make the Markers' widget constant. This works fine considering performance, but leads me to the other problem, that i cannot initialize them properly:
Maybe I'm just too stupid to use const correctly. If you see my mistake here or you know a workaround, please let me know. |
What happens if you create your marker list outside of the build method (i.e in class LeafletMap) , and then just reference it later? |
@ibrierley I already tried that and the problem of Marker widget rebuilding every frame stays the same. (Edit) I could maybe get rid of the const-problem in the Key by initialising every Marker widget individually, which means, not in a loop, like:
This feels totally stupid, but would at least be a solution for the key. But there would be still no solution for the callback functions i want to pass in the constructor. I want to give every MarkerWidget the same callback functions, but it doesn't seem to be possible to make functions == const... |
@JohnnyRainbow81 rebuilding the layer every frame while panning is the intended behaviour because we have to calculate the new position for the Anyway if you cache a Widget in a statefull widget then Flutter will respect that the Widget is the same instance so it won't rebuild it's subchildren. Here is how to do it manually. #719 just prevents to rebuild the whole FlutterMap because it just updates the layers (the only exception when map is rotating) |
Hi @maRci002 , |
How about putting _buildEmptyMarkers in initState instead of in the build method? |
I got it working now! Hooray 🚀 The MarkerWidgets only rebuild when their data changes and not when User is navigating on the map. On the other hand, one little piece of the code i'm not able to understand 😆 In case you re interested:
(Edit) Forgot to obfuscate my code :D |
What bit aren't you able to understand ? |
@ibrierley |
I'd have to test to be sure, but I "think", your final markerWidget isn't what you think, and has no state. So it's a bit like using an icon or whatever. What has the 'state' is the Marker(). |
@ibrierley The MarkerWidget seems to have state, because my map shows different markers with different data, but i cannot explain why 😃 |
What is the different MarkerWidget state that you are seeing, what's different between them, can you make them different colours ? (as mentioned, it's difficult when you can't see the code :)), so it feels like it's slightly heavier work than it needs to be :). |
Everything is different; the Markers' shape, Text, Images... It somehow works |
I think what isn't clear, is how/where you are setting those things (shape/text etc), as that's nowhere in the shown code, so feels like the important stuff you keep leaving out, dragging this out somewhat :). I'm a bit wary of spamming the git members here though, so if you want to include that code great, if not, maybe post a minimal example on Stackoverflow or similar. |
I'd prefer to not post my real code here. But all the changing stuff( different data, images, shape,...) happens in the build()-method of the one final MarkerWidget. To give you a glimpse:
|
Hmm I think I give up :D. You're now missing what is. There comes a point.... Just be wary of using ChangeNotifierProvider.value() earlier in your code. Eg https://pub.dev/documentation/provider/latest/provider/ChangeNotifierProvider-class.html "To create a value, use the default constructor. Creating the instance inside build using ChangeNotifierProvider.value will lead to memory leaks and potentially undesired side-effects." Now, this may be fine, it's getting quite complex, and can't see the code. I'm just leading you to the water, I can't make you drink it. Problem as I've mentioned is just posting bits of code all of the time, and never an actual solution, so you only ever get half baked answers (from me anyway). I'll leave it there :D. |
Thank you for your time and your efforts:) I'm just happy to have performant markers now, even though it nags me a bit I don't fully get why it works. Yeah, I know about potential memory leaks with ChangeNotifierProvider.value, but I think they only leak when you instantiate new Notifiers as a value (like ChangeNotifierProvider.value(value: MarkerData()), but here I instantiate them upfront in another place so the value parameter gets an already existing value. Yes, it's a bit hairy, but I don't see another solution to have performant markers now. |
This issue is stale because it has been open 30 days with no activity. Remove stale label or comment or this will be closed in 5 days. |
This issue was closed because it has been stalled for 5 days with no activity. |
@JohnnyRainbow81 "I got it working now! Hooray rocket The MarkerWidgets only rebuild when their data changes and not when User is navigating on the map." |
Hi @Pepslee , Here's my untidy code snippet. I hope it helps you out somehow:
|
As far as I understand flutter, widgets should only rebuild when configuration changes happen.
Maybe this is intentional here because of some internal, non visible magic of the leaflet map implementation. In this case, just let me know if this is wanted. Otherwise - what did I do wrong? My code example shows mostly a c/p version of the official example from https://pub.dev/packages/flutter_map.
The problem is: Rebuilding the FlutterMap also means its children rebuild, in my case, pretty expensive marker widgets, which I didn’t include in the example code (because they re not necessary to prove my point). The performance is quite laggy, so here’s my question:
Is the way it works now intentional or can I avoid the permanent rebuilding or is it a bug in the leaflet framework?
Thank you for your help!
The text was updated successfully, but these errors were encountered: