mirror of
https://github.com/SimpleMobileTools/Simple-Calendar.git
synced 2025-06-05 21:59:17 +02:00
Merge pull request #1377 from Honk2/Events-over-multiple-days
implements Events over multiple days #1241
This commit is contained in:
@ -54,6 +54,7 @@ class SettingsActivity : SimpleActivity() {
|
|||||||
setupWeekNumbers()
|
setupWeekNumbers()
|
||||||
setupShowGrid()
|
setupShowGrid()
|
||||||
setupWeeklyStart()
|
setupWeeklyStart()
|
||||||
|
setupMidnightSpanEvents()
|
||||||
setupVibrate()
|
setupVibrate()
|
||||||
setupReminderSound()
|
setupReminderSound()
|
||||||
setupReminderAudioStream()
|
setupReminderAudioStream()
|
||||||
@ -322,6 +323,14 @@ class SettingsActivity : SimpleActivity() {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private fun setupMidnightSpanEvents() {
|
||||||
|
settings_midnight_span_event.isChecked = config.showMidnightSpanningEventsAtTop
|
||||||
|
settings_midnight_span_events_holder.setOnClickListener {
|
||||||
|
settings_midnight_span_event.toggle()
|
||||||
|
config.showMidnightSpanningEventsAtTop = settings_midnight_span_event.isChecked
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
private fun setupWeekNumbers() {
|
private fun setupWeekNumbers() {
|
||||||
settings_week_numbers.isChecked = config.showWeekNumbers
|
settings_week_numbers.isChecked = config.showWeekNumbers
|
||||||
settings_week_numbers_holder.setOnClickListener {
|
settings_week_numbers_holder.setOnClickListener {
|
||||||
|
@ -398,102 +398,132 @@ class WeekFragment : Fragment(), WeeklyCalendar {
|
|||||||
|
|
||||||
for (event in events) {
|
for (event in events) {
|
||||||
val startDateTime = Formatter.getDateTimeFromTS(event.startTS)
|
val startDateTime = Formatter.getDateTimeFromTS(event.startTS)
|
||||||
|
val startDayCode = Formatter.getDayCodeFromDateTime(startDateTime)
|
||||||
val endDateTime = Formatter.getDateTimeFromTS(event.endTS)
|
val endDateTime = Formatter.getDateTimeFromTS(event.endTS)
|
||||||
if (!event.getIsAllDay() && Formatter.getDayCodeFromDateTime(startDateTime) == Formatter.getDayCodeFromDateTime(endDateTime)) {
|
val endDayCode = Formatter.getDayCodeFromDateTime(endDateTime)
|
||||||
val startMinutes = startDateTime.minuteOfDay
|
|
||||||
val duration = endDateTime.minuteOfDay - startMinutes
|
if (event.getIsAllDay() || ((startDayCode != endDayCode) && config.showMidnightSpanningEventsAtTop)) {
|
||||||
val range = Range(startMinutes, startMinutes + maxOf(1,duration))
|
continue
|
||||||
|
}
|
||||||
|
|
||||||
|
var currentDateTime = startDateTime
|
||||||
|
var currentDayCode = Formatter.getDayCodeFromDateTime(currentDateTime)
|
||||||
|
do {
|
||||||
|
val startMinutes = when (currentDayCode == startDayCode) {
|
||||||
|
true -> (startDateTime.minuteOfDay)
|
||||||
|
else -> 0
|
||||||
|
}
|
||||||
|
val duration = when (currentDayCode == endDayCode) {
|
||||||
|
true -> (endDateTime.minuteOfDay - startMinutes)
|
||||||
|
else -> 1440
|
||||||
|
}
|
||||||
|
val range = Range(startMinutes, startMinutes + duration)
|
||||||
val eventWeekly = EventWeeklyView(event.id!!, range)
|
val eventWeekly = EventWeeklyView(event.id!!, range)
|
||||||
|
|
||||||
val dayCode = Formatter.getDayCodeFromDateTime(startDateTime)
|
if (!eventTimeRanges.containsKey(currentDayCode)) {
|
||||||
if (!eventTimeRanges.containsKey(dayCode)) {
|
eventTimeRanges[currentDayCode] = ArrayList()
|
||||||
eventTimeRanges[dayCode] = ArrayList()
|
|
||||||
}
|
}
|
||||||
|
eventTimeRanges[currentDayCode]?.add(eventWeekly)
|
||||||
|
|
||||||
eventTimeRanges[dayCode]?.add(eventWeekly)
|
currentDateTime = currentDateTime.plusDays(1)
|
||||||
}
|
currentDayCode = Formatter.getDayCodeFromDateTime(currentDateTime)
|
||||||
|
} while(currentDayCode.toInt() <= endDayCode.toInt())
|
||||||
}
|
}
|
||||||
|
|
||||||
for (event in events) {
|
for (event in events) {
|
||||||
val startDateTime = Formatter.getDateTimeFromTS(event.startTS)
|
val startDateTime = Formatter.getDateTimeFromTS(event.startTS)
|
||||||
|
val startDayCode = Formatter.getDayCodeFromDateTime(startDateTime)
|
||||||
val endDateTime = Formatter.getDateTimeFromTS(event.endTS)
|
val endDateTime = Formatter.getDateTimeFromTS(event.endTS)
|
||||||
if (event.getIsAllDay() || Formatter.getDayCodeFromDateTime(startDateTime) != Formatter.getDayCodeFromDateTime(endDateTime)) {
|
val endDayCode = Formatter.getDayCodeFromDateTime(endDateTime)
|
||||||
|
if (event.getIsAllDay() || ((startDayCode != endDayCode) && config.showMidnightSpanningEventsAtTop)) {
|
||||||
addAllDayEvent(event)
|
addAllDayEvent(event)
|
||||||
} else {
|
}
|
||||||
val dayCode = Formatter.getDayCodeFromDateTime(startDateTime)
|
else {
|
||||||
val dayOfWeek = dayColumns.indexOfFirst { it.tag == dayCode }
|
var currentDateTime = startDateTime
|
||||||
if (dayOfWeek == -1 || dayOfWeek >= config.weeklyViewDays) {
|
var currentDayCode = Formatter.getDayCodeFromDateTime(currentDateTime)
|
||||||
continue
|
do {
|
||||||
}
|
val dayOfWeek = dayColumns.indexOfFirst { it.tag == currentDayCode }
|
||||||
|
if (dayOfWeek == -1 || dayOfWeek >= config.weeklyViewDays) {
|
||||||
val startMinutes = startDateTime.minuteOfDay
|
continue
|
||||||
val duration = endDateTime.minuteOfDay - startMinutes
|
|
||||||
val range = Range(startMinutes, startMinutes + maxOf(1, duration))
|
|
||||||
|
|
||||||
var overlappingEvents = 0
|
|
||||||
var currentEventOverlapIndex = 0
|
|
||||||
var foundCurrentEvent = false
|
|
||||||
|
|
||||||
eventTimeRanges[dayCode]!!.forEachIndexed { index, eventWeeklyView ->
|
|
||||||
if (eventWeeklyView.range.touch(range)) {
|
|
||||||
overlappingEvents++
|
|
||||||
|
|
||||||
if (eventWeeklyView.id == event.id) {
|
|
||||||
foundCurrentEvent = true
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!foundCurrentEvent) {
|
|
||||||
currentEventOverlapIndex++
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
val dayColumn = dayColumns[dayOfWeek]
|
|
||||||
(inflater.inflate(R.layout.week_event_marker, null, false) as TextView).apply {
|
|
||||||
var backgroundColor = eventTypeColors.get(event.eventType, primaryColor)
|
|
||||||
var textColor = backgroundColor.getContrastColor()
|
|
||||||
if (dimPastEvents && event.isPastEvent && !isPrintVersion) {
|
|
||||||
backgroundColor = backgroundColor.adjustAlpha(LOWER_ALPHA)
|
|
||||||
textColor = textColor.adjustAlpha(HIGHER_ALPHA)
|
|
||||||
}
|
}
|
||||||
|
|
||||||
background = ColorDrawable(backgroundColor)
|
val startMinutes = when (currentDayCode == startDayCode) {
|
||||||
setTextColor(textColor)
|
true -> (startDateTime.minuteOfDay)
|
||||||
text = event.title
|
else -> 0
|
||||||
contentDescription = text
|
}
|
||||||
dayColumn.addView(this)
|
val duration = when (currentDayCode == endDayCode) {
|
||||||
y = startMinutes * minuteHeight
|
true -> (endDateTime.minuteOfDay - startMinutes)
|
||||||
(layoutParams as RelativeLayout.LayoutParams).apply {
|
else -> 1440
|
||||||
width = dayColumn.width - 1
|
}
|
||||||
width /= Math.max(overlappingEvents, 1)
|
val range = Range(startMinutes, startMinutes + duration)
|
||||||
if (overlappingEvents > 1) {
|
var overlappingEvents = 0
|
||||||
x = width * currentEventOverlapIndex.toFloat()
|
var currentEventOverlapIndex = 0
|
||||||
if (currentEventOverlapIndex != 0) {
|
var foundCurrentEvent = false
|
||||||
x += density
|
|
||||||
|
eventTimeRanges[currentDayCode]!!.forEachIndexed { index, eventWeeklyView ->
|
||||||
|
if (eventWeeklyView.range.touch(range)) {
|
||||||
|
overlappingEvents++
|
||||||
|
|
||||||
|
if (eventWeeklyView.id == event.id) {
|
||||||
|
foundCurrentEvent = true
|
||||||
}
|
}
|
||||||
|
|
||||||
width -= density
|
if (!foundCurrentEvent) {
|
||||||
if (currentEventOverlapIndex + 1 != overlappingEvents) {
|
currentEventOverlapIndex++
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
val dayColumn = dayColumns[dayOfWeek]
|
||||||
|
(inflater.inflate(R.layout.week_event_marker, null, false) as TextView).apply {
|
||||||
|
var backgroundColor = eventTypeColors.get(event.eventType, primaryColor)
|
||||||
|
var textColor = backgroundColor.getContrastColor()
|
||||||
|
if (dimPastEvents && event.isPastEvent && !isPrintVersion) {
|
||||||
|
backgroundColor = backgroundColor.adjustAlpha(LOWER_ALPHA)
|
||||||
|
textColor = textColor.adjustAlpha(HIGHER_ALPHA)
|
||||||
|
}
|
||||||
|
|
||||||
|
background = ColorDrawable(backgroundColor)
|
||||||
|
setTextColor(textColor)
|
||||||
|
text = event.title
|
||||||
|
contentDescription = text
|
||||||
|
dayColumn.addView(this)
|
||||||
|
y = startMinutes * minuteHeight
|
||||||
|
(layoutParams as RelativeLayout.LayoutParams).apply {
|
||||||
|
width = dayColumn.width - 1
|
||||||
|
width /= Math.max(overlappingEvents, 1)
|
||||||
|
if (overlappingEvents > 1) {
|
||||||
|
x = width * currentEventOverlapIndex.toFloat()
|
||||||
if (currentEventOverlapIndex != 0) {
|
if (currentEventOverlapIndex != 0) {
|
||||||
width -= density
|
x += density
|
||||||
|
}
|
||||||
|
|
||||||
|
width -= density
|
||||||
|
if (currentEventOverlapIndex + 1 != overlappingEvents) {
|
||||||
|
if (currentEventOverlapIndex != 0) {
|
||||||
|
width -= density
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
|
||||||
minHeight = if (event.startTS == event.endTS) {
|
minHeight = if (event.startTS == event.endTS) {
|
||||||
minimalHeight
|
minimalHeight
|
||||||
} else {
|
} else {
|
||||||
(duration * minuteHeight).toInt() - 1
|
(duration * minuteHeight).toInt() - 1
|
||||||
|
}
|
||||||
|
}
|
||||||
|
setOnClickListener {
|
||||||
|
Intent(context, EventActivity::class.java).apply {
|
||||||
|
putExtra(EVENT_ID, event.id!!)
|
||||||
|
putExtra(EVENT_OCCURRENCE_TS, event.startTS)
|
||||||
|
startActivity(this)
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
setOnClickListener {
|
|
||||||
Intent(context, EventActivity::class.java).apply {
|
currentDateTime = currentDateTime.plusDays(1)
|
||||||
putExtra(EVENT_ID, event.id!!)
|
currentDayCode = Formatter.getDayCodeFromDateTime(currentDateTime)
|
||||||
putExtra(EVENT_OCCURRENCE_TS, event.startTS)
|
} while(currentDayCode.toInt() <= endDayCode.toInt())
|
||||||
startActivity(this)
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -23,6 +23,10 @@ class Config(context: Context) : BaseConfig(context) {
|
|||||||
get() = prefs.getInt(START_WEEKLY_AT, 7)
|
get() = prefs.getInt(START_WEEKLY_AT, 7)
|
||||||
set(startWeeklyAt) = prefs.edit().putInt(START_WEEKLY_AT, startWeeklyAt).apply()
|
set(startWeeklyAt) = prefs.edit().putInt(START_WEEKLY_AT, startWeeklyAt).apply()
|
||||||
|
|
||||||
|
var showMidnightSpanningEventsAtTop: Boolean
|
||||||
|
get() = prefs.getBoolean(SHOW_MIDNIGHT_SPANNING_EVENTS_AT_TOP, true)
|
||||||
|
set(midnightSpanning) = prefs.edit().putBoolean(SHOW_MIDNIGHT_SPANNING_EVENTS_AT_TOP, midnightSpanning).apply()
|
||||||
|
|
||||||
var vibrateOnReminder: Boolean
|
var vibrateOnReminder: Boolean
|
||||||
get() = prefs.getBoolean(VIBRATE, false)
|
get() = prefs.getBoolean(VIBRATE, false)
|
||||||
set(vibrate) = prefs.edit().putBoolean(VIBRATE, vibrate).apply()
|
set(vibrate) = prefs.edit().putBoolean(VIBRATE, vibrate).apply()
|
||||||
|
@ -45,6 +45,7 @@ const val YEAR = 31536000
|
|||||||
// Shared Preferences
|
// Shared Preferences
|
||||||
const val WEEK_NUMBERS = "week_numbers"
|
const val WEEK_NUMBERS = "week_numbers"
|
||||||
const val START_WEEKLY_AT = "start_weekly_at"
|
const val START_WEEKLY_AT = "start_weekly_at"
|
||||||
|
const val SHOW_MIDNIGHT_SPANNING_EVENTS_AT_TOP = "show_midnight_spanning_events_at_top"
|
||||||
const val VIBRATE = "vibrate"
|
const val VIBRATE = "vibrate"
|
||||||
const val REMINDER_SOUND_URI = "reminder_sound_uri"
|
const val REMINDER_SOUND_URI = "reminder_sound_uri"
|
||||||
const val REMINDER_SOUND_TITLE = "reminder_sound_title"
|
const val REMINDER_SOUND_TITLE = "reminder_sound_title"
|
||||||
|
@ -679,6 +679,28 @@
|
|||||||
|
|
||||||
</RelativeLayout>
|
</RelativeLayout>
|
||||||
|
|
||||||
|
<RelativeLayout
|
||||||
|
android:id="@+id/settings_midnight_span_events_holder"
|
||||||
|
android:layout_width="match_parent"
|
||||||
|
android:layout_height="wrap_content"
|
||||||
|
android:layout_marginTop="@dimen/medium_margin"
|
||||||
|
android:background="?attr/selectableItemBackground"
|
||||||
|
android:paddingStart="@dimen/normal_margin"
|
||||||
|
android:paddingTop="@dimen/activity_margin"
|
||||||
|
android:paddingEnd="@dimen/normal_margin"
|
||||||
|
android:paddingBottom="@dimen/activity_margin">
|
||||||
|
|
||||||
|
<com.simplemobiletools.commons.views.MySwitchCompat
|
||||||
|
android:id="@+id/settings_midnight_span_event"
|
||||||
|
android:layout_width="match_parent"
|
||||||
|
android:layout_height="wrap_content"
|
||||||
|
android:background="@null"
|
||||||
|
android:clickable="false"
|
||||||
|
android:paddingStart="@dimen/medium_margin"
|
||||||
|
android:text="@string/midnight_spanning" />
|
||||||
|
|
||||||
|
</RelativeLayout>
|
||||||
|
|
||||||
<com.simplemobiletools.commons.views.MyTextView
|
<com.simplemobiletools.commons.views.MyTextView
|
||||||
android:id="@+id/monthly_view_label"
|
android:id="@+id/monthly_view_label"
|
||||||
android:layout_width="wrap_content"
|
android:layout_width="wrap_content"
|
||||||
|
Reference in New Issue
Block a user