Files
moxxy/lib/shared/helpers.dart

120 lines
3.0 KiB
Dart

/*
* Add a leading zero, if required, to ensure that an integer is rendered
* as a two "digit" string.
*
* NOTE: This function assumes that 0 <= i <= 99
*/
String padInt(int i) {
if (i <= 9) {
return "0" + i.toString();
}
return i.toString();
}
/*
* A wrapper around List<T>.firstWhere that does not throw but instead just
* returns true if test returns true for an element or false if test never
* returned true.
*/
bool listContains<T>(List<T> list, bool Function(T element) test) {
return firstWhereOrNull<T>(list, test) != null;
}
/*
* A wrapper around List<T>.firstWhere that does not throw but instead just
* return null if test never returned true
*/
T? firstWhereOrNull<T>(List<T> list, bool Function(T element) test) {
try {
return list.firstWhere(test);
} catch(e) {
return null;
}
}
/*
* Format the timestamp of a conversation change into a nice string.
* timestamp and now are both in millisecondsSinceEpoch.
* Ensures that now >= timestamp
*/
String formatConversationTimestamp(int timestamp, int now) {
int difference = now - timestamp;
// NOTE: Just to make sure
assert(difference >= 0);
if (difference >= 60 * Duration.millisecondsPerMinute) {
int hourDifference = (difference / Duration.millisecondsPerHour).floor();
if (hourDifference >= 24) {
DateTime dt = DateTime.fromMillisecondsSinceEpoch(timestamp);
String suffix = difference >= 364.5 * Duration.millisecondsPerDay ? dt.year.toString() : "";
return dt.day.toString() + "." + dt.month.toString() + "." + suffix;
} else {
return hourDifference.toString() + "h";
}
} else if (difference <= Duration.millisecondsPerMinute) {
return "Just now";
}
return (difference / Duration.millisecondsPerMinute).floor().toString() + "min";
}
/*
* Same as formatConversationTimestamp but for messages
*/
String formatMessageTimestamp(int timestamp, int now) {
int difference = now - timestamp;
// NOTE: Just to make sure
assert(difference >= 0);
if (difference >= 15 * Duration.millisecondsPerMinute) {
DateTime dt = DateTime.fromMillisecondsSinceEpoch(timestamp);
return dt.hour.toString() + ":" + padInt(dt.minute);
} else {
if (difference < Duration.millisecondsPerMinute) {
return "Just now";
} else {
return (difference / Duration.millisecondsPerMinute).floor().toString() + "min ago";
}
}
}
enum JidFormatError {
none,
empty,
noLocalpart,
noSeparator,
tooManySeparators,
noDomain
}
/*
* Validate a JID and return why it is invalid
*/
JidFormatError validateJid(String jid) {
if (jid.isEmpty) {
return JidFormatError.empty;
}
if (!jid.contains("@")) {
return JidFormatError.noSeparator;
}
List<String> parts = jid.split("@");
if (parts.length != 2) {
return JidFormatError.tooManySeparators;
}
if (parts[0].isEmpty) {
return JidFormatError.noLocalpart;
}
if (parts[1].isEmpty) {
return JidFormatError.noDomain;
}
return JidFormatError.none;
}