I need to create a list view that has a few key requirements
Infinite scroll of a fixed number of items (ie looping)
Multiple child item types (images, text, inputs)
Multiple child item heights
"3d" wheel look/feel. 2d perspective changes and shadowing/coloring should suffice
It needs to be iOS and Android compatible in Flutter.
I've tried the List Wheel Scroll View widget (https://api.flutter.dev/flutter/widgets/ListWheelScrollView-class.html) and am currently using Carousel Slider (https://pub.dev/packages/carousel_slider), but neither quite get the job done. List Wheel can't do interactive inputs or mixed child heights and the carousel can't do mixed heights or '3d'.
Has anybody created or come across something that might at least get me going in the right direction?
UPDATE
Currently playing with CustomScrollView with some success. It allows me to have multiple child heights and I ~think~ I'll be able to add some perspective to the children in the scroll listener.
What I can't figure out with CustomScrollView is how to get the looping/infinite scroll.
I liked using the flutter_swiper package a while ago. Not sure if it supports mixed heights, but it has 3D effects. But it doesn't seem maintained, so I would try this null-saefty unofficial fork : flutter_swiper_null_safety
Related
I have a long, scrollable list of widgets, and need to be able to restore the correct position in the list whenever the user switches from portrait to landscape, because the content is mainly text.
For now, I am using scrollable_positioned_list, but it isn't enough in some cases because its position is of course based on its immediate children. But when the child itself contains a bunch of other widgets, you get very imprecise positionning.
What I would want to do is to go down to the individual RenderParagraph or equivalent level, and look at their position in the viewport (using getOffsetToReveal for example) in order to position the scroll correctly.
In more descriptive steps :
I keep track of the "topmost" RenderObject,
The user goes from portait to landscape,
I scroll the list until the equivalent RenderObject is again the "topmost".
But to do that, I would need to get a listing of all RenderObjects currently in a given viewport, and I do not know how.
There also is visitChildElements, but the docs warns that is it potentially performance-intensive.
Thanks in advance. Other ideas around this problem are welcome too !
I have a grid view which is showing the heal status of many different services, and coloring them and/or auto-opening a webpage when the service goes down. The problem is that the elements which are off the screen are not being checked, which is more efficient, but not what is desired in this case.
I guess it's behaving similarly to the RecyclerView in android?
I want to be building the widgets which are checking service health even when they are not visible on the screen.
Currently the services don't start being checked until the moment I scroll them into the screen.
Assuming you are currently using the GridView.builder constructor, I recommend using the "normal" GridView constructor (with a children property). Since GridView.builder only builds the elements currently visible for efficiency reasons, the elements that are not rendered on the screen won't run your back end logic.
For more information, see the official docs:
[GridView.builder] constructor is appropriate for grid views with a large (or infinite) number of children because the builder is called only for those children that are actually visible.
Here you'll find alternatives:
The most commonly used grid layouts are GridView.count, which creates a layout with a fixed number of tiles in the cross axis, and GridView.extent, which creates a layout with tiles that have a maximum cross-axis extent.
I am wondering what is the equivalent of the web api DocumentOrShadowRoot.elementFromPoint() in flutter.
Specifically, I am wondering how I could figure out what is the leaf element/widget instance in a widget hierarchy, given an Offset.
For example, consider the following structure:
For the First Offset marked with a dark circle, I would expect to get some sort of data that can help me figure out the offset is over Container.
For the Second Offset marked with a dark circle, I would expect the stack.
For the last one, it would be the positioned element.
A bit of context
I'm exploring the implementation of a visual editor similar to FIGMA in Flutter. I have experience in implementing such a rendering system with web technologies.
I want to render a selection indicator or outline when a tap/click happens on each element. These elements are nested. Adding multiple nested event handlers triggers all of them. For example, mouse enter and mouse leave when moving the mouse over the Stack or Positioned element would trigger all the parent event handlers as well.
Any help or guidance would be appreciated.
Simple answer to your exact question: No direct equivalent. Possible to implement but not advisable.
You could theoretically implement your own version of elementFromPoint() by looking at how GestureBinding works in Flutter. That would be a deep dive for sure, and you might learn from it, but there is a simpler solution. Even if you implement your own method, then you would still need to resolve conflicts when more than 1 element is found - and this is something Flutter solves out of the box with the gesture arena.
I see that you expect the top-most or deepest child to be reported, something that you can obtain by using the GestureDetector widget. What you're looking for is making your gesture detectors opaque. A GestureDetector has a property called behaviour of type HitTestBehaviour. The default for it is deferToChild. Here are the possible values:
/// How to behave during hit tests.
enum HitTestBehavior {
/// Targets that defer to their children receive events within their bounds
/// only if one of their children is hit by the hit test.
deferToChild,
/// Opaque targets can be hit by hit tests, causing them to both receive
/// events within their bounds and prevent targets visually behind them from
/// also receiving events.
opaque,
/// Translucent targets both receive events within their bounds and permit
/// targets visually behind them to also receive events.
translucent,
}
What follows is slightly related, so consider it a deep dive in your use-case
Since you're going down this path: I also built a WYSIWYG design system, with selection indicators, handles for rotating, resizing, etc. and have one advice: Completely separate your design rendering from your gesture detectors and selection indicators.
I initially put the gesture detectors "around" the design elements - in your example, the gesture detectors would sit in between yellow / blue / green / red. The reason this is a bad idea is that it complicates a few things. In some cases I needed to create touch areas larger than the design elements themselves, in which case I needed to add padding and reposition the GestureDetector parents. In other cases the design elements would become fixed or locked and would not have a GestureDetector parent and Flutter would completely rebuild the contents of the layer since tree comparing got confused. It gets messy fast. So, stack these layers:
Design on bottom, no interactivity.
Selection indicators, resize / rotate handles. Still no interactivity
Gesture detectors for all design elements. If you're lucky, you know the exact size, position, rotation for the design elements you can simply use Positioned. If you have groups of design elements, then your gesture detectors also get grouped and transformed together. If you also have self-sizing design elements (like images), it gets a bit more complicated, but I got around my issues by adding the design element as an invisible child. The way I would do this now is by loading meta-data about the images and knowing them at build time (as opposed to waiting for images to load and produce layout changes).
Selection indicators + resize / rotate handles gesture detectors. They are top-most and also opaque, so they catch everything that hits them.
This setup then allows you to experiment more in the gesture department, it allows you to use colored boxes to debug and in general will make your life easier.
TLDR: Use opaque gesture detectors.
I am migrating game from windows phone to flutter card game. I cannot find the way how to keep the card on the top after dragging.
Stack order is too complex and problematic for such simple action and would involve 4 player active, not active cards, cards on the table, combination sets re-arrangement :( In Windows phone there was a Rectangle with ZIndex which i could set to any rectangle on the screen.
I am missing something similar in flutter. I cannot believe that stack order is only way to solve this because it would make any game development impossible.
I am not using any game engine (maybe thats a problem) but i feel like i do not need it because it is not game-loop based game it is event based - click, drag etc.
Do you know any solution how i can achieve that?
There are 2 options -
1. Stack
Update the position of its children by mutating the List and calling setState or use Positioned.
2. Material
The Material widget has a property named elevation. Set it's value dynamically to achieve the effect
I'm trying to develop a scrollable tile map in Cocos2D which uses an UIPanGestureRecognizer to do the dirty work, but while developing it, stumbled upon some problems for which I would like to ask for an advice.
The basic scrolling management works fine, it's precise and accurate and works by adding the translation recognized by the pan gesture manager to the tiles of the map. The problem is that the map is large and I just draw a small viewport of it, while I want to manage it like it's scrollable without any problem.
What I was thinking about is that, as soon as a whole row or column get out of the visible screen, it is moved to the opposite side, the corresponding texture rects are updated (I'm working entirely with a CCSpriteBatchNode), so that it will continuously update the viewport to make the whole thing work. This seems fine but I've found many problems in dealing with when to move the row/column, how to keep track of this issue (eg when pan changes direction from forth to back) and many little details which make me think that I should find a better approach.
Is there a common solution to my problem? That is: managing a scrollable viewport of a tilemap which should move over the whole map so the to the end user it seems like as if the map is infinite.
Thanks in advance
I solved my issue by developing a viewport in which rows and columns are effectively moved from left side to right side and from top side to bottom side.
This is done automatically when a new column or row enters the viewport and it's made by expanding the drawn viewport over the real one by an amount which is enough to avoid any graphical issue to the user.