You've already forked immich
mirror of
https://github.com/immich-app/immich.git
synced 2025-07-16 07:24:40 +02:00
feat(mobile): sqlite timeline (#19197)
* wip: timeline * more segment extensions * added scrubber * refactor: timeline state * more refactors * fix scrubber segments * added remote thumb & thumbhash provider * feat: merged view * scrub / merged asset fixes * rename stuff & add tile indicators * fix local album timeline query * ignore hidden assets during sync * ignore recovered assets during sync * old scrubber * add video indicator * handle groupBy * handle partner inTimeline * show duration * reduce widget nesting in thumb tile * merge main * chore: extend cacheExtent * ignore touch events on scrub label when not visible * scrub label ignore events and hide immediately * auto reload on sync * refactor image providers * throttle db updates --------- Co-authored-by: shenlong-tanwen <139912620+shalong-tanwen@users.noreply.github.com> Co-authored-by: Alex Tran <alex.tran1502@gmail.com>
This commit is contained in:
@ -11,6 +11,7 @@ enum AssetVisibility {
|
||||
class Asset extends BaseAsset {
|
||||
final String id;
|
||||
final String? localId;
|
||||
final String? thumbHash;
|
||||
final AssetVisibility visibility;
|
||||
|
||||
const Asset({
|
||||
@ -25,9 +26,14 @@ class Asset extends BaseAsset {
|
||||
super.height,
|
||||
super.durationInSeconds,
|
||||
super.isFavorite = false,
|
||||
this.thumbHash,
|
||||
this.visibility = AssetVisibility.timeline,
|
||||
});
|
||||
|
||||
@override
|
||||
AssetState get storage =>
|
||||
localId == null ? AssetState.remote : AssetState.merged;
|
||||
|
||||
@override
|
||||
String toString() {
|
||||
return '''Asset {
|
||||
@ -41,6 +47,7 @@ class Asset extends BaseAsset {
|
||||
durationInSeconds: ${durationInSeconds ?? "<NA>"},
|
||||
localId: ${localId ?? "<NA>"},
|
||||
isFavorite: $isFavorite,
|
||||
thumbHash: ${thumbHash ?? "<NA>"},
|
||||
visibility: $visibility,
|
||||
}''';
|
||||
}
|
||||
@ -52,10 +59,15 @@ class Asset extends BaseAsset {
|
||||
return super == other &&
|
||||
id == other.id &&
|
||||
localId == other.localId &&
|
||||
thumbHash == other.thumbHash &&
|
||||
visibility == other.visibility;
|
||||
}
|
||||
|
||||
@override
|
||||
int get hashCode =>
|
||||
super.hashCode ^ id.hashCode ^ localId.hashCode ^ visibility.hashCode;
|
||||
super.hashCode ^
|
||||
id.hashCode ^
|
||||
localId.hashCode ^
|
||||
thumbHash.hashCode ^
|
||||
visibility.hashCode;
|
||||
}
|
||||
|
@ -9,6 +9,12 @@ enum AssetType {
|
||||
audio,
|
||||
}
|
||||
|
||||
enum AssetState {
|
||||
local,
|
||||
remote,
|
||||
merged,
|
||||
}
|
||||
|
||||
sealed class BaseAsset {
|
||||
final String name;
|
||||
final String? checksum;
|
||||
@ -32,6 +38,10 @@ sealed class BaseAsset {
|
||||
this.isFavorite = false,
|
||||
});
|
||||
|
||||
bool get isImage => type == AssetType.image;
|
||||
bool get isVideo => type == AssetType.video;
|
||||
AssetState get storage;
|
||||
|
||||
@override
|
||||
String toString() {
|
||||
return '''BaseAsset {
|
||||
|
@ -18,6 +18,10 @@ class LocalAsset extends BaseAsset {
|
||||
super.isFavorite = false,
|
||||
});
|
||||
|
||||
@override
|
||||
AssetState get storage =>
|
||||
remoteId == null ? AssetState.local : AssetState.merged;
|
||||
|
||||
@override
|
||||
String toString() {
|
||||
return '''LocalAsset {
|
||||
|
12
mobile/lib/domain/models/setting.model.dart
Normal file
12
mobile/lib/domain/models/setting.model.dart
Normal file
@ -0,0 +1,12 @@
|
||||
import 'package:immich_mobile/domain/models/store.model.dart';
|
||||
|
||||
enum Setting<T> {
|
||||
tilesPerRow<int>(StoreKey.tilesPerRow, 4),
|
||||
groupAssetsBy<int>(StoreKey.groupAssetsBy, 0),
|
||||
showStorageIndicator<bool>(StoreKey.storageIndicator, true);
|
||||
|
||||
const Setting(this.storeKey, this.defaultValue);
|
||||
|
||||
final StoreKey<T> storeKey;
|
||||
final T defaultValue;
|
||||
}
|
40
mobile/lib/domain/models/timeline.model.dart
Normal file
40
mobile/lib/domain/models/timeline.model.dart
Normal file
@ -0,0 +1,40 @@
|
||||
enum GroupAssetsBy {
|
||||
day,
|
||||
month,
|
||||
none;
|
||||
}
|
||||
|
||||
enum HeaderType {
|
||||
none,
|
||||
month,
|
||||
day,
|
||||
monthAndDay;
|
||||
}
|
||||
|
||||
class Bucket {
|
||||
final int assetCount;
|
||||
|
||||
const Bucket({required this.assetCount});
|
||||
|
||||
@override
|
||||
bool operator ==(covariant Bucket other) {
|
||||
return assetCount == other.assetCount;
|
||||
}
|
||||
|
||||
@override
|
||||
int get hashCode => assetCount.hashCode;
|
||||
}
|
||||
|
||||
class TimeBucket extends Bucket {
|
||||
final DateTime date;
|
||||
|
||||
const TimeBucket({required this.date, required super.assetCount});
|
||||
|
||||
@override
|
||||
bool operator ==(covariant TimeBucket other) {
|
||||
return super == other && date == other.date;
|
||||
}
|
||||
|
||||
@override
|
||||
int get hashCode => super.hashCode ^ date.hashCode;
|
||||
}
|
Reference in New Issue
Block a user