我正在尝试为我的应用程序实现议程功能,但到目前为止我还没有找到任何可以帮助我实现此目的的库。我已阅读有关日历提供程序和 Google Calendar API 的信息,但在他们的文档中没有找到任何有关仅为我的应用创建 Activity 的内容。
目前,我已经创建了一个数据库来存储具有以下结构的事件:
id - Integer used as primary key for the event;
user_id - Integer used to bound the user;
start_date - Date of the event;
end_date - Date with the end of the event's recurrence.
rec_sunday - Boolean if the event reoccurs on sunday.
rec_monday - Boolean if the event reoccurs on monday.
rec_tuesday - Boolean if the event reoccurs on tuesday.
rec_wednesday - Boolean if the event reoccurs on wednesday.
rec_thursday - Boolean if the event reoccurs on thursday.
rec_friday - Boolean if the event reoccurs on friday.
rec_saturday - Boolean if the event reoccurs on saturday.
recurrence - Boolean if the event has recurrence, so I won't need to check for all others booleans.
现在,我只需要一些逻辑来在 ArrayList 中创建事件以及重复事件及其日期,因此之后我可以使用比较器以日期为基础对它们进行排序。
感谢您的帮助。
更新
感谢Basil Bourque令人惊奇的答案我现在正在使用 ThreeTenABP图书馆。这是一个很棒的库,而且比我想象的更容易使用。
最佳答案
other Answer by Ali使用 iCal4j 可能是可行的方法。
但是要直接回答你的问题......
java.time
java.time框架内置于 Java 8 及更高版本中。这些类取代了旧的麻烦的日期时间类,例如 java.util.Date、.Calendar 和 java.text.SimpleDateFormat。/p>
要了解更多信息,请参阅 Oracle Tutorial 。并在 Stack Overflow 上搜索许多示例和解释。
许多 java.time 功能已向后移植到 ThreeTen-Backport 中的 Java 6 和 7并在ThreeTenABP进一步适配Android .
星期几
java.time.DayOfWeek
枚举在这里会很方便。
EnumSet
是 Set
的一种特殊实现,它在内部使用位图来表示在非常少量内存中以非常快速操作的枚举元素集合。这里的想法是使用 EnumSet
而不是每周 boolean 方法。不需要关于重复的额外 boolean 值,因为您只需查看 EnumSet
是否有任何元素即可;没有元素意味着不会重复。
本地日期
LocalDate
类表示仅日期值,没有时间和时区。
顺便说一句,在 standard date-handling ,一周从星期一开始,到星期日结束。虽然您可能不想以这种方式向用户展示一周,但我建议在内部坚持使用该标准。这种从周一到周日的方法也是 DayOfWeek
枚举中定义的顺序。
你的类(class)
为Event
定义一个类。
public class Event {
Integer id ;
Integer user_id ;
LocalDate start , stop ;
Set< DayOfWeek > recurrence ;
}
如果您愿意,您可以使用空集初始化recurrence
EnumSet。
recurrence = EnumSet.noneOf( DayOfWeek.class );
然后添加项目。从数据库检索数据时,您可以使用 if
语句执行此操作,其中如果行的 SQL BOOLEAN 列值为 TRUE,则调用 .add
方法在这里。
recurrence.add( DayOfWeek.MONDAY );
检查集合的大小以查看此事件是否重复发生。
Boolean isRecurring = ( recurrence.size() > 0 );
要对对象进行排序,请实现 Comparable
只需委托(delegate)给 start
成员的 LocalDate
实现即可。我不记得带有 Comparable
的泛型的确切语法,但这是一个粗略的想法。
public class Event implements Comparable {
…
@Override
public int compareTo( Event otherEvent ) {
return this.start.compareTo( otherEvent.start ) ;
}
填写List
每次出现时,执行类似这样的循环。
一个TemporalAdjuster
操作日期时间对象以生成新的日期时间对象。 TemporalAdjusters
(注意复数)类提供了实现,包括我们需要的 next
和/或 nextOrSame
。 start
可能需要作为一个事件包含在内;我将把这种技巧留给读者作为练习。 ;-)
if( recurrences.size > 0 ) { // If any recurrences to schedule…
List<LocalDate> occurrences = new ArrayList<>();
LocalDate ld = this.start ;
while ( ld.isBefore( this.stop ) ) {
for( DayOfWeek dow , this.recurrence ) {
ld = ld.with( TemporalAdjusters.next( dow ) );
occurrences.add( ld );
…
请注意上面代码中的逻辑,我们测试每个日期早停止日期,不小于或等于。这种半开放方法在日期时间工作中很常见,其中定义时间跨度,开始时包含,结束时排除。
您可能需要对开始和停止之间的时间跨度进行健全性检查。如果发生错误导致间隙过长,则可能会因出现大量 List
而耗尽内存。 Period
类有助于此检查。
if ( Period.between( start , stop ).getYears() > 10 ) { // If over a decade, halt.
…
警告:上面的所有代码都未经测试且从未运行。就在我的头顶上。希望足以帮助您入门。
对于调度,请考虑 Quartz Job Scheduler 。
关于java - 重复事件库,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/38414140/