support for lazy building widgets within viewport
This commit is contained in:
@@ -0,0 +1,74 @@
|
||||
import 'dart:collection';
|
||||
import 'dart:math';
|
||||
|
||||
import 'package:flutter/material.dart';
|
||||
|
||||
typedef _CellKey = Point<int>;
|
||||
|
||||
class PointData<T> {
|
||||
final Point point;
|
||||
final T data;
|
||||
|
||||
PointData(this.point, this.data);
|
||||
}
|
||||
|
||||
class SpatialHashing<T> {
|
||||
final Size cellSize;
|
||||
final HashMap<Point, T> _pointData = HashMap<Point, T>();
|
||||
final HashMap<_CellKey, List<Point>> _cellMap = HashMap<_CellKey, List<Point>>();
|
||||
|
||||
SpatialHashing({required this.cellSize});
|
||||
|
||||
_CellKey _cellKey(Point point) {
|
||||
int x = (point.x / cellSize.width).floor();
|
||||
int y = (point.y / cellSize.height).floor();
|
||||
return Point(x, y);
|
||||
}
|
||||
|
||||
void add(Point point, T data) {
|
||||
_CellKey cellKey = _cellKey(point);
|
||||
_pointData[point] = data;
|
||||
|
||||
if (!_cellMap.containsKey(cellKey)) {
|
||||
_cellMap[cellKey] = [];
|
||||
}
|
||||
_cellMap[cellKey]!.add(point);
|
||||
}
|
||||
|
||||
void remove(Point point) {
|
||||
final key = _cellKey(point);
|
||||
if (_pointData.containsKey(point)) {
|
||||
_pointData.remove(point); // remove the data
|
||||
|
||||
// cell map must have key then
|
||||
_cellMap[key]!.remove(point); // remove from spatial hash
|
||||
if (_cellMap[key]!.isEmpty) {
|
||||
_cellMap.remove(key);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
List<PointData<T>> getPointsAround(Point point, Offset offset) {
|
||||
_CellKey cellKey = _cellKey(point);
|
||||
List<PointData<T>> results = [];
|
||||
|
||||
// Calculate the range of cells to check
|
||||
int startX = cellKey.x - (offset.dx / cellSize.width).floor();
|
||||
int startY = cellKey.y - (offset.dy / cellSize.height).floor();
|
||||
int endX = cellKey.x + (offset.dx / cellSize.width).ceil();
|
||||
int endY = cellKey.y + (offset.dy / cellSize.height).ceil();
|
||||
|
||||
for (int x = startX; x <= endX; x++) {
|
||||
for (int y = startY; y <= endY; y++) {
|
||||
Point currentCellKey = Point(x, y);
|
||||
if (_cellMap.containsKey(currentCellKey)) {
|
||||
for (Point p in _cellMap[currentCellKey]!) {
|
||||
results.add(PointData(p, _pointData[p] as T));
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
return results;
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user