We were making a game in Flutter web, and it fought us in a way a phone build never did.
Hot reload did not just redraw the screen. It broke the state. Score, who was in the session, whether the round was still live — things that have to survive a tweak to a widget. In a normal app you shrug and tap again. In a game that is the whole product.
I am not going to pretend I have a clean diagram of every provider we tried. I remember the feeling: change a colour, reload, and the match was gone.
Player leave, player enter, window reload
Those three were the actual bugs, not “state management” as a slogan.
Someone leaves. Someone comes back. The browser tab refreshes. Flutter web treated those like a fresh start more often than we could live with. The game had to know who was still in the room after a reload. It did not.
You can patch around that for a while. We did. Then you are debugging the framework’s reload behaviour instead of the rules of the game.
Why we left Flutter web
The phone build was not the problem. The web target was. We needed the session to survive the ugly cases: a refresh, a disconnect, a player dropping and joining again.
We shifted the web game to React. I say that a little carefully because I am going from memory of the rewrite, not a post-mortem doc — React, for the web client, because it was easier to keep that session state through a reload. Flutter stayed in the picture for the other surfaces. The web one had to stop resetting the match every time the browser breathed on it.
I would not start a multiplayer-ish web game on Flutter web again without a hard answer to “what happens on refresh.” If the answer is “we lose the room,” that is not a styling issue. That is the wrong target.
The same project also had to run on a TV. That was a different fight, and I wrote that down separately: adapting the Flutter game for Android TV.