From 874056dfcacc63945e9510836d07a627a7babf1c Mon Sep 17 00:00:00 2001 From: tibbi Date: Thu, 14 Mar 2019 22:35:00 +0100 Subject: [PATCH 01/39] show attendees selected from autocomplete differently --- .../calendar/pro/activities/EventActivity.kt | 28 ++++++++++++++----- app/src/main/res/layout/item_attendee.xml | 20 +++++++++++++ 2 files changed, 41 insertions(+), 7 deletions(-) diff --git a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt index 9efb38efc..34a1ee5e3 100644 --- a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt +++ b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt @@ -1156,8 +1156,12 @@ class EventActivity : SimpleActivity() { private fun addAttendee(value: String? = null) { val attendeeHolder = layoutInflater.inflate(R.layout.item_attendee, event_attendees_holder, false) as RelativeLayout - mAttendeeViews.add(attendeeHolder.event_attendee) - attendeeHolder.event_attendee.onTextChangeListener { + val autoCompleteView = attendeeHolder.event_attendee + val selectedAttendeeHolder = attendeeHolder.event_contact_attendee + val selectedAttendeeName = selectedAttendeeHolder.event_contact_name + + mAttendeeViews.add(autoCompleteView) + autoCompleteView.onTextChangeListener { if (mWasContactsPermissionChecked && value == null) { checkNewAttendeeField(value) } else { @@ -1169,17 +1173,27 @@ class EventActivity : SimpleActivity() { } event_attendees_holder.addView(attendeeHolder) - attendeeHolder.event_attendee.setColors(config.textColor, getAdjustedPrimaryColor(), config.backgroundColor) + event_attendees_holder.onGlobalLayout { + selectedAttendeeHolder.layoutParams.height = autoCompleteView.height + } + + autoCompleteView.setColors(config.textColor, getAdjustedPrimaryColor(), config.backgroundColor) + selectedAttendeeName.setColors(config.textColor, getAdjustedPrimaryColor(), config.backgroundColor) if (value != null) { - attendeeHolder.event_attendee.setText(value) + autoCompleteView.setText(value) } val adapter = AutoCompleteTextViewAdapter(this, mAvailableContacts) - attendeeHolder.event_attendee.setAdapter(adapter) - attendeeHolder.event_attendee.setOnItemClickListener { parent, view, position, id -> - val currAttendees = (attendeeHolder.event_attendee.adapter as AutoCompleteTextViewAdapter).resultList + autoCompleteView.setAdapter(adapter) + autoCompleteView.setOnItemClickListener { parent, view, position, id -> + val currAttendees = (autoCompleteView.adapter as AutoCompleteTextViewAdapter).resultList val selectedAttendee = currAttendees[position] + + hideKeyboard(autoCompleteView) + autoCompleteView.beGone() + selectedAttendeeName.text = selectedAttendee.getPublicName() + selectedAttendeeHolder.beVisible() } } diff --git a/app/src/main/res/layout/item_attendee.xml b/app/src/main/res/layout/item_attendee.xml index 1b04b5433..b85562fab 100644 --- a/app/src/main/res/layout/item_attendee.xml +++ b/app/src/main/res/layout/item_attendee.xml @@ -1,6 +1,7 @@ + + + + + From 206e61085e6a8da8baaf5131137dcc94d6017933 Mon Sep 17 00:00:00 2001 From: tibbi Date: Thu, 14 Mar 2019 22:45:25 +0100 Subject: [PATCH 02/39] be more smart about going to next attendee on confirmation --- .../simplemobiletools/calendar/pro/activities/EventActivity.kt | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt index 34a1ee5e3..6c3a11b01 100644 --- a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt +++ b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt @@ -1186,12 +1186,13 @@ class EventActivity : SimpleActivity() { val adapter = AutoCompleteTextViewAdapter(this, mAvailableContacts) autoCompleteView.setAdapter(adapter) + autoCompleteView.imeOptions = EditorInfo.IME_ACTION_NEXT autoCompleteView.setOnItemClickListener { parent, view, position, id -> val currAttendees = (autoCompleteView.adapter as AutoCompleteTextViewAdapter).resultList val selectedAttendee = currAttendees[position] - hideKeyboard(autoCompleteView) autoCompleteView.beGone() + autoCompleteView.focusSearch(View.FOCUS_DOWN)?.requestFocus() selectedAttendeeName.text = selectedAttendee.getPublicName() selectedAttendeeHolder.beVisible() } From 770eab45253829d7c5ab1dd229e56a6ca99c4ce6 Mon Sep 17 00:00:00 2001 From: tibbi Date: Thu, 14 Mar 2019 23:25:18 +0100 Subject: [PATCH 03/39] show an attendee image at his name too --- .../calendar/pro/activities/EventActivity.kt | 10 +++++++ .../adapters/AutoCompleteTextViewAdapter.kt | 20 +------------- .../calendar/pro/models/Attendee.kt | 26 +++++++++++++++++++ app/src/main/res/layout/item_attendee.xml | 10 ++++++- 4 files changed, 46 insertions(+), 20 deletions(-) diff --git a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt index 6c3a11b01..5fb02ec06 100644 --- a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt +++ b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt @@ -4,6 +4,8 @@ import android.app.DatePickerDialog import android.app.TimePickerDialog import android.content.Intent import android.database.Cursor +import android.graphics.drawable.Drawable +import android.graphics.drawable.LayerDrawable import android.net.Uri import android.os.Bundle import android.provider.CalendarContract @@ -12,7 +14,9 @@ import android.text.TextUtils import android.text.method.LinkMovementMethod import android.view.Menu import android.view.MenuItem +import android.view.View import android.view.WindowManager +import android.view.inputmethod.EditorInfo import android.widget.EditText import android.widget.ImageView import android.widget.RelativeLayout @@ -76,6 +80,7 @@ class EventActivity : SimpleActivity() { private var mAttendeeViews = ArrayList() private var mAvailableContacts = ArrayList() + private lateinit var mAttendeePlaceholder: Drawable private lateinit var mEventStartDateTime: DateTime private lateinit var mEventEndDateTime: DateTime private lateinit var mEvent: Event @@ -88,6 +93,8 @@ class EventActivity : SimpleActivity() { val intent = intent ?: return mDialogTheme = getDialogTheme() mWasContactsPermissionChecked = hasPermission(PERMISSION_READ_CONTACTS) + mAttendeePlaceholder = resources.getDrawable(R.drawable.attendee_circular_background) + (mAttendeePlaceholder as LayerDrawable).findDrawableByLayerId(R.id.attendee_circular_background).applyColorFilter(config.primaryColor) val eventId = intent.getLongExtra(EVENT_ID, 0L) Thread { @@ -1159,6 +1166,7 @@ class EventActivity : SimpleActivity() { val autoCompleteView = attendeeHolder.event_attendee val selectedAttendeeHolder = attendeeHolder.event_contact_attendee val selectedAttendeeName = selectedAttendeeHolder.event_contact_name + val selectedAttendeeImage = attendeeHolder.event_contact_image mAttendeeViews.add(autoCompleteView) autoCompleteView.onTextChangeListener { @@ -1195,6 +1203,8 @@ class EventActivity : SimpleActivity() { autoCompleteView.focusSearch(View.FOCUS_DOWN)?.requestFocus() selectedAttendeeName.text = selectedAttendee.getPublicName() selectedAttendeeHolder.beVisible() + selectedAttendeeImage.beVisible() + selectedAttendee.updateImage(applicationContext, selectedAttendeeImage, mAttendeePlaceholder) } } diff --git a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/adapters/AutoCompleteTextViewAdapter.kt b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/adapters/AutoCompleteTextViewAdapter.kt index 34ef234dc..55ed5ffcc 100644 --- a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/adapters/AutoCompleteTextViewAdapter.kt +++ b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/adapters/AutoCompleteTextViewAdapter.kt @@ -6,10 +6,6 @@ import android.view.View import android.view.ViewGroup import android.widget.ArrayAdapter import android.widget.Filter -import com.bumptech.glide.Glide -import com.bumptech.glide.load.engine.DiskCacheStrategy -import com.bumptech.glide.load.resource.drawable.DrawableTransitionOptions -import com.bumptech.glide.request.RequestOptions import com.simplemobiletools.calendar.pro.R import com.simplemobiletools.calendar.pro.activities.SimpleActivity import com.simplemobiletools.calendar.pro.extensions.config @@ -39,21 +35,7 @@ class AutoCompleteTextViewAdapter(val activity: SimpleActivity, val contacts: Ar item_autocomplete_name?.text = contact.name item_autocomplete_email?.text = contact.email - if (contact.photoUri.isEmpty()) { - item_autocomplete_image.setImageDrawable(placeholder) - } else { - val options = RequestOptions() - .diskCacheStrategy(DiskCacheStrategy.RESOURCE) - .error(placeholder) - .centerCrop() - - Glide.with(activity) - .load(contact.photoUri) - .transition(DrawableTransitionOptions.withCrossFade()) - .apply(options) - .apply(RequestOptions.circleCropTransform()) - .into(item_autocomplete_image) - } + contact.updateImage(context, item_autocomplete_image, placeholder) } return listItem diff --git a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/models/Attendee.kt b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/models/Attendee.kt index 74ebfa8d7..23c5d0992 100644 --- a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/models/Attendee.kt +++ b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/models/Attendee.kt @@ -1,5 +1,31 @@ package com.simplemobiletools.calendar.pro.models +import android.content.Context +import android.graphics.drawable.Drawable +import android.widget.ImageView +import com.bumptech.glide.Glide +import com.bumptech.glide.load.engine.DiskCacheStrategy +import com.bumptech.glide.load.resource.drawable.DrawableTransitionOptions +import com.bumptech.glide.request.RequestOptions + data class Attendee(val contactId: Int, var name: String, val email: String, val status: Int, var photoUri: String) { fun getPublicName() = if (name.isNotEmpty()) name else email + + fun updateImage(context: Context, imageView: ImageView, placeholder: Drawable) { + if (photoUri.isEmpty()) { + imageView.setImageDrawable(placeholder) + } else { + val options = RequestOptions() + .diskCacheStrategy(DiskCacheStrategy.RESOURCE) + .error(placeholder) + .centerCrop() + + Glide.with(context) + .load(photoUri) + .transition(DrawableTransitionOptions.withCrossFade()) + .apply(options) + .apply(RequestOptions.circleCropTransform()) + .into(imageView) + } + } } diff --git a/app/src/main/res/layout/item_attendee.xml b/app/src/main/res/layout/item_attendee.xml index b85562fab..3c043439f 100644 --- a/app/src/main/res/layout/item_attendee.xml +++ b/app/src/main/res/layout/item_attendee.xml @@ -30,12 +30,20 @@ android:layout_alignBottom="@+id/event_attendee" android:visibility="gone"> + + From 33a63c4e72a23dd8daae82e830d4ec4ceef25be4 Mon Sep 17 00:00:00 2001 From: tibbi Date: Thu, 14 Mar 2019 23:42:47 +0100 Subject: [PATCH 04/39] show a cross for removing selected contacts --- .../calendar/pro/activities/EventActivity.kt | 8 ++++++-- app/src/main/res/layout/item_attendee.xml | 14 ++++++++++++++ 2 files changed, 20 insertions(+), 2 deletions(-) diff --git a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt index 5fb02ec06..5ef36e208 100644 --- a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt +++ b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt @@ -1167,6 +1167,7 @@ class EventActivity : SimpleActivity() { val selectedAttendeeHolder = attendeeHolder.event_contact_attendee val selectedAttendeeName = selectedAttendeeHolder.event_contact_name val selectedAttendeeImage = attendeeHolder.event_contact_image + val selectedAttendeeDismiss = attendeeHolder.event_contact_dismiss mAttendeeViews.add(autoCompleteView) autoCompleteView.onTextChangeListener { @@ -1185,8 +1186,10 @@ class EventActivity : SimpleActivity() { selectedAttendeeHolder.layoutParams.height = autoCompleteView.height } - autoCompleteView.setColors(config.textColor, getAdjustedPrimaryColor(), config.backgroundColor) - selectedAttendeeName.setColors(config.textColor, getAdjustedPrimaryColor(), config.backgroundColor) + val textColor = config.textColor + autoCompleteView.setColors(textColor, getAdjustedPrimaryColor(), config.backgroundColor) + selectedAttendeeName.setColors(textColor, getAdjustedPrimaryColor(), config.backgroundColor) + selectedAttendeeDismiss.applyColorFilter(textColor) if (value != null) { autoCompleteView.setText(value) @@ -1205,6 +1208,7 @@ class EventActivity : SimpleActivity() { selectedAttendeeHolder.beVisible() selectedAttendeeImage.beVisible() selectedAttendee.updateImage(applicationContext, selectedAttendeeImage, mAttendeePlaceholder) + selectedAttendeeDismiss.beVisible() } } diff --git a/app/src/main/res/layout/item_attendee.xml b/app/src/main/res/layout/item_attendee.xml index 3c043439f..a78573caf 100644 --- a/app/src/main/res/layout/item_attendee.xml +++ b/app/src/main/res/layout/item_attendee.xml @@ -43,10 +43,24 @@ android:layout_height="wrap_content" android:layout_centerVertical="true" android:layout_marginStart="@dimen/medium_margin" + android:layout_toStartOf="@+id/event_contact_dismiss" android:layout_toEndOf="@+id/event_contact_image" + android:ellipsize="end" android:lines="1" android:textSize="@dimen/bigger_text_size" tools:text="Simple Mobile"/> + + From b26bd7a20ef3b0bb0e011e20ddbd3057f3677dcf Mon Sep 17 00:00:00 2001 From: tibbi Date: Fri, 15 Mar 2019 10:10:00 +0100 Subject: [PATCH 05/39] remove the selected attendee on pressing Dismiss --- .../calendar/pro/activities/EventActivity.kt | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt index 5ef36e208..70595544a 100644 --- a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt +++ b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt @@ -1195,6 +1195,10 @@ class EventActivity : SimpleActivity() { autoCompleteView.setText(value) } + selectedAttendeeDismiss.setOnClickListener { + attendeeHolder.beGone() + } + val adapter = AutoCompleteTextViewAdapter(this, mAvailableContacts) autoCompleteView.setAdapter(adapter) autoCompleteView.imeOptions = EditorInfo.IME_ACTION_NEXT From a5f5e4783ecfcce432f46c679301f7a61a9960d7 Mon Sep 17 00:00:00 2001 From: tibbi Date: Fri, 15 Mar 2019 10:35:58 +0100 Subject: [PATCH 06/39] some attendee related improvements --- .../calendar/pro/activities/EventActivity.kt | 24 +++++++++++++------ .../calendar/pro/models/Attendee.kt | 2 +- 2 files changed, 18 insertions(+), 8 deletions(-) diff --git a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt index 70595544a..7990ab93d 100644 --- a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt +++ b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt @@ -17,7 +17,6 @@ import android.view.MenuItem import android.view.View import android.view.WindowManager import android.view.inputmethod.EditorInfo -import android.widget.EditText import android.widget.ImageView import android.widget.RelativeLayout import androidx.core.app.NotificationManagerCompat @@ -35,6 +34,7 @@ import com.simplemobiletools.commons.dialogs.RadioGroupDialog import com.simplemobiletools.commons.extensions.* import com.simplemobiletools.commons.helpers.* import com.simplemobiletools.commons.models.RadioItem +import com.simplemobiletools.commons.views.MyAutoCompleteTextView import kotlinx.android.synthetic.main.activity_event.* import kotlinx.android.synthetic.main.activity_event.view.* import kotlinx.android.synthetic.main.item_attendee.view.* @@ -77,8 +77,9 @@ class EventActivity : SimpleActivity() { private var mWasActivityInitialized = false private var mWasContactsPermissionChecked = false private var mAttendees = ArrayList() - private var mAttendeeViews = ArrayList() + private var mAttendeeAutoCompleteViews = ArrayList() private var mAvailableContacts = ArrayList() + private var mSelectedContacts = ArrayList() private lateinit var mAttendeePlaceholder: Drawable private lateinit var mEventStartDateTime: DateTime @@ -1169,7 +1170,7 @@ class EventActivity : SimpleActivity() { val selectedAttendeeImage = attendeeHolder.event_contact_image val selectedAttendeeDismiss = attendeeHolder.event_contact_dismiss - mAttendeeViews.add(autoCompleteView) + mAttendeeAutoCompleteViews.add(autoCompleteView) autoCompleteView.onTextChangeListener { if (mWasContactsPermissionChecked && value == null) { checkNewAttendeeField(value) @@ -1197,6 +1198,7 @@ class EventActivity : SimpleActivity() { selectedAttendeeDismiss.setOnClickListener { attendeeHolder.beGone() + mSelectedContacts = mSelectedContacts.filter { it.contactId == selectedAttendeeDismiss.tag }.toMutableList() as ArrayList } val adapter = AutoCompleteTextViewAdapter(this, mAvailableContacts) @@ -1205,6 +1207,7 @@ class EventActivity : SimpleActivity() { autoCompleteView.setOnItemClickListener { parent, view, position, id -> val currAttendees = (autoCompleteView.adapter as AutoCompleteTextViewAdapter).resultList val selectedAttendee = currAttendees[position] + mSelectedContacts.add(selectedAttendee) autoCompleteView.beGone() autoCompleteView.focusSearch(View.FOCUS_DOWN)?.requestFocus() @@ -1213,21 +1216,28 @@ class EventActivity : SimpleActivity() { selectedAttendeeImage.beVisible() selectedAttendee.updateImage(applicationContext, selectedAttendeeImage, mAttendeePlaceholder) selectedAttendeeDismiss.beVisible() + selectedAttendeeDismiss.tag = selectedAttendee.contactId } } private fun checkNewAttendeeField(value: String?) { - if (value == null && mAttendeeViews.none { it.value.isEmpty() }) { + if (value == null && mAttendeeAutoCompleteViews.none { it.value.isEmpty() }) { addAttendee() } } private fun getAllAttendees(): String { - val attendeeEmails = mAttendeeViews.map { it.value }.filter { it.isNotEmpty() }.toMutableList() as ArrayList - val attendees = ArrayList() - attendeeEmails.mapTo(attendees) { + var attendees = ArrayList() + mSelectedContacts.forEach { + it.status = CalendarContract.Attendees.ATTENDEE_STATUS_INVITED + attendees.add(it) + } + + val customEmails = mAttendeeAutoCompleteViews.filter { it.isVisible() }.map { it.value }.filter { it.isNotEmpty() }.toMutableList() as ArrayList + customEmails.mapTo(attendees) { Attendee(0, "", it, CalendarContract.Attendees.ATTENDEE_STATUS_INVITED, "") } + attendees = attendees.distinctBy { it.email }.toMutableList() as ArrayList return Gson().toJson(attendees) } diff --git a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/models/Attendee.kt b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/models/Attendee.kt index 23c5d0992..2468b34a9 100644 --- a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/models/Attendee.kt +++ b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/models/Attendee.kt @@ -8,7 +8,7 @@ import com.bumptech.glide.load.engine.DiskCacheStrategy import com.bumptech.glide.load.resource.drawable.DrawableTransitionOptions import com.bumptech.glide.request.RequestOptions -data class Attendee(val contactId: Int, var name: String, val email: String, val status: Int, var photoUri: String) { +data class Attendee(val contactId: Int, var name: String, val email: String, var status: Int, var photoUri: String) { fun getPublicName() = if (name.isNotEmpty()) name else email fun updateImage(context: Context, imageView: ImageView, placeholder: Drawable) { From 1ac25c4dad6254be0031597fdf8f8e27656fc77e Mon Sep 17 00:00:00 2001 From: tibbi Date: Fri, 15 Mar 2019 11:28:54 +0100 Subject: [PATCH 07/39] properly handle showing existing attendees at existing events --- .../calendar/pro/activities/EventActivity.kt | 49 ++++++++++--------- app/src/main/res/layout/item_attendee.xml | 2 +- 2 files changed, 27 insertions(+), 24 deletions(-) diff --git a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt index 7990ab93d..126ac72ef 100644 --- a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt +++ b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt @@ -35,6 +35,7 @@ import com.simplemobiletools.commons.extensions.* import com.simplemobiletools.commons.helpers.* import com.simplemobiletools.commons.models.RadioItem import com.simplemobiletools.commons.views.MyAutoCompleteTextView +import com.simplemobiletools.commons.views.MyTextView import kotlinx.android.synthetic.main.activity_event.* import kotlinx.android.synthetic.main.activity_event.view.* import kotlinx.android.synthetic.main.item_attendee.view.* @@ -1148,7 +1149,7 @@ class EventActivity : SimpleActivity() { private fun updateAttendees() { mAttendees.forEach { - addAttendee(it.getPublicName()) + addAttendee(it) } addAttendee() @@ -1162,7 +1163,7 @@ class EventActivity : SimpleActivity() { } } - private fun addAttendee(value: String? = null) { + private fun addAttendee(attendee: Attendee? = null) { val attendeeHolder = layoutInflater.inflate(R.layout.item_attendee, event_attendees_holder, false) as RelativeLayout val autoCompleteView = attendeeHolder.event_attendee val selectedAttendeeHolder = attendeeHolder.event_contact_attendee @@ -1172,30 +1173,23 @@ class EventActivity : SimpleActivity() { mAttendeeAutoCompleteViews.add(autoCompleteView) autoCompleteView.onTextChangeListener { - if (mWasContactsPermissionChecked && value == null) { - checkNewAttendeeField(value) + if (mWasContactsPermissionChecked) { + checkNewAttendeeField() } else { handlePermission(PERMISSION_READ_CONTACTS) { - checkNewAttendeeField(value) + checkNewAttendeeField() mWasContactsPermissionChecked = true } } } event_attendees_holder.addView(attendeeHolder) - event_attendees_holder.onGlobalLayout { - selectedAttendeeHolder.layoutParams.height = autoCompleteView.height - } val textColor = config.textColor autoCompleteView.setColors(textColor, getAdjustedPrimaryColor(), config.backgroundColor) selectedAttendeeName.setColors(textColor, getAdjustedPrimaryColor(), config.backgroundColor) selectedAttendeeDismiss.applyColorFilter(textColor) - if (value != null) { - autoCompleteView.setText(value) - } - selectedAttendeeDismiss.setOnClickListener { attendeeHolder.beGone() mSelectedContacts = mSelectedContacts.filter { it.contactId == selectedAttendeeDismiss.tag }.toMutableList() as ArrayList @@ -1207,21 +1201,30 @@ class EventActivity : SimpleActivity() { autoCompleteView.setOnItemClickListener { parent, view, position, id -> val currAttendees = (autoCompleteView.adapter as AutoCompleteTextViewAdapter).resultList val selectedAttendee = currAttendees[position] - mSelectedContacts.add(selectedAttendee) + addSelectedAttendee(selectedAttendee, autoCompleteView, selectedAttendeeHolder, selectedAttendeeImage, selectedAttendeeName, selectedAttendeeDismiss) + } - autoCompleteView.beGone() - autoCompleteView.focusSearch(View.FOCUS_DOWN)?.requestFocus() - selectedAttendeeName.text = selectedAttendee.getPublicName() - selectedAttendeeHolder.beVisible() - selectedAttendeeImage.beVisible() - selectedAttendee.updateImage(applicationContext, selectedAttendeeImage, mAttendeePlaceholder) - selectedAttendeeDismiss.beVisible() - selectedAttendeeDismiss.tag = selectedAttendee.contactId + if (attendee != null) { + addSelectedAttendee(attendee, autoCompleteView, selectedAttendeeHolder, selectedAttendeeImage, selectedAttendeeName, selectedAttendeeDismiss) } } - private fun checkNewAttendeeField(value: String?) { - if (value == null && mAttendeeAutoCompleteViews.none { it.value.isEmpty() }) { + private fun addSelectedAttendee(attendee: Attendee, autoCompleteView: MyAutoCompleteTextView, selectedAttendeeHolder: RelativeLayout, selectedAttendeeImage: ImageView, + selectedAttendeeName: MyTextView, selectedAttendeeDismiss: ImageView) { + mSelectedContacts.add(attendee) + + autoCompleteView.beGone() + autoCompleteView.focusSearch(View.FOCUS_DOWN)?.requestFocus() + selectedAttendeeName.text = attendee.getPublicName() + selectedAttendeeHolder.beVisible() + selectedAttendeeImage.beVisible() + attendee.updateImage(applicationContext, selectedAttendeeImage, mAttendeePlaceholder) + selectedAttendeeDismiss.beVisible() + selectedAttendeeDismiss.tag = attendee.contactId + } + + private fun checkNewAttendeeField() { + if (mAttendeeAutoCompleteViews.none { it.isVisible() && it.value.isEmpty() }) { addAttendee() } } diff --git a/app/src/main/res/layout/item_attendee.xml b/app/src/main/res/layout/item_attendee.xml index a78573caf..e1d294a2b 100644 --- a/app/src/main/res/layout/item_attendee.xml +++ b/app/src/main/res/layout/item_attendee.xml @@ -25,7 +25,7 @@ From eda6c792b7318b32734004d0a0fefce40404614c Mon Sep 17 00:00:00 2001 From: tibbi Date: Fri, 15 Mar 2019 11:54:44 +0100 Subject: [PATCH 08/39] show existing event attendee photos, if available --- .../calendar/pro/activities/EventActivity.kt | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt index 126ac72ef..67b782457 100644 --- a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt +++ b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt @@ -1149,7 +1149,12 @@ class EventActivity : SimpleActivity() { private fun updateAttendees() { mAttendees.forEach { - addAttendee(it) + val attendee = it + val deviceContact = mAvailableContacts.firstOrNull { it.email.isNotEmpty() && it.email == attendee.email && it.photoUri.isNotEmpty() } + if (deviceContact != null) { + attendee.photoUri = deviceContact.photoUri + } + addAttendee(attendee) } addAttendee() From d347b05b6724c9060bacbba1abf5d760bf2c205e Mon Sep 17 00:00:00 2001 From: FTno <16176811+FTno@users.noreply.github.com> Date: Sun, 17 Mar 2019 18:10:51 +0100 Subject: [PATCH 09/39] Update strings.xml Norwegian (nb) translation update --- app/src/main/res/values-nb/strings.xml | 14 +++++++------- 1 file changed, 7 insertions(+), 7 deletions(-) diff --git a/app/src/main/res/values-nb/strings.xml b/app/src/main/res/values-nb/strings.xml index 61e702c6e..5bd496760 100644 --- a/app/src/main/res/values-nb/strings.xml +++ b/app/src/main/res/values-nb/strings.xml @@ -10,7 +10,7 @@ Enkel hendelsesliste Ser ut som du ikke har noen kommende hendelser. Gå til idag - Go to date + Gå til dato Månedskalender @@ -174,12 +174,12 @@ Standardpåminnelse 3 View to open from the event list widget Last view - New events - Default start time - Next full hour - Default duration - Last used one - Other time + Nye hendelser + Standard starttid + Neste fulle time + Standard varighet + Den sist brukte + Annen tid CalDAV From 7d0e46705f56a72191bb45fc1e7d4794ca286e8e Mon Sep 17 00:00:00 2001 From: tibbi Date: Tue, 19 Mar 2019 14:49:05 +0100 Subject: [PATCH 10/39] add an image showing the attendees status at event details --- .../calendar/pro/activities/EventActivity.kt | 25 +++++++++++++++--- .../main/res/drawable-hdpi/ic_check_green.png | Bin 0 -> 600 bytes .../main/res/drawable-hdpi/ic_cross_red.png | Bin 0 -> 675 bytes .../res/drawable-hdpi/ic_question_yellow.png | Bin 0 -> 622 bytes .../res/drawable-xhdpi/ic_check_green.png | Bin 0 -> 617 bytes .../main/res/drawable-xhdpi/ic_cross_red.png | Bin 0 -> 774 bytes .../res/drawable-xhdpi/ic_question_yellow.png | Bin 0 -> 759 bytes .../res/drawable-xxhdpi/ic_check_green.png | Bin 0 -> 1256 bytes .../main/res/drawable-xxhdpi/ic_cross_red.png | Bin 0 -> 1409 bytes .../drawable-xxhdpi/ic_question_yellow.png | Bin 0 -> 1265 bytes .../res/drawable-xxxhdpi/ic_check_green.png | Bin 0 -> 1019 bytes .../res/drawable-xxxhdpi/ic_cross_red.png | Bin 0 -> 1241 bytes .../drawable-xxxhdpi/ic_question_yellow.png | Bin 0 -> 1272 bytes .../attendee_status_circular_background.xml | 8 ++++++ app/src/main/res/layout/item_attendee.xml | 14 +++++++++- app/src/main/res/values/dimens.xml | 1 + 16 files changed, 43 insertions(+), 5 deletions(-) create mode 100644 app/src/main/res/drawable-hdpi/ic_check_green.png create mode 100644 app/src/main/res/drawable-hdpi/ic_cross_red.png create mode 100644 app/src/main/res/drawable-hdpi/ic_question_yellow.png create mode 100644 app/src/main/res/drawable-xhdpi/ic_check_green.png create mode 100644 app/src/main/res/drawable-xhdpi/ic_cross_red.png create mode 100644 app/src/main/res/drawable-xhdpi/ic_question_yellow.png create mode 100644 app/src/main/res/drawable-xxhdpi/ic_check_green.png create mode 100644 app/src/main/res/drawable-xxhdpi/ic_cross_red.png create mode 100644 app/src/main/res/drawable-xxhdpi/ic_question_yellow.png create mode 100644 app/src/main/res/drawable-xxxhdpi/ic_check_green.png create mode 100644 app/src/main/res/drawable-xxxhdpi/ic_cross_red.png create mode 100644 app/src/main/res/drawable-xxxhdpi/ic_question_yellow.png create mode 100644 app/src/main/res/drawable/attendee_status_circular_background.xml diff --git a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt index 67b782457..49d89139d 100644 --- a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt +++ b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt @@ -1173,7 +1173,6 @@ class EventActivity : SimpleActivity() { val autoCompleteView = attendeeHolder.event_attendee val selectedAttendeeHolder = attendeeHolder.event_contact_attendee val selectedAttendeeName = selectedAttendeeHolder.event_contact_name - val selectedAttendeeImage = attendeeHolder.event_contact_image val selectedAttendeeDismiss = attendeeHolder.event_contact_dismiss mAttendeeAutoCompleteViews.add(autoCompleteView) @@ -1206,23 +1205,41 @@ class EventActivity : SimpleActivity() { autoCompleteView.setOnItemClickListener { parent, view, position, id -> val currAttendees = (autoCompleteView.adapter as AutoCompleteTextViewAdapter).resultList val selectedAttendee = currAttendees[position] - addSelectedAttendee(selectedAttendee, autoCompleteView, selectedAttendeeHolder, selectedAttendeeImage, selectedAttendeeName, selectedAttendeeDismiss) + addSelectedAttendee(selectedAttendee, autoCompleteView, selectedAttendeeHolder, selectedAttendeeName, selectedAttendeeDismiss) } if (attendee != null) { - addSelectedAttendee(attendee, autoCompleteView, selectedAttendeeHolder, selectedAttendeeImage, selectedAttendeeName, selectedAttendeeDismiss) + addSelectedAttendee(attendee, autoCompleteView, selectedAttendeeHolder, selectedAttendeeName, selectedAttendeeDismiss) } } - private fun addSelectedAttendee(attendee: Attendee, autoCompleteView: MyAutoCompleteTextView, selectedAttendeeHolder: RelativeLayout, selectedAttendeeImage: ImageView, + private fun addSelectedAttendee(attendee: Attendee, autoCompleteView: MyAutoCompleteTextView, selectedAttendeeHolder: RelativeLayout, selectedAttendeeName: MyTextView, selectedAttendeeDismiss: ImageView) { mSelectedContacts.add(attendee) + val selectedAttendeeImage = selectedAttendeeHolder.event_contact_image + val selectedAttendeeStatusImage = selectedAttendeeHolder.event_contact_status_image + val showAttendeeStatus = attendee.status == CalendarContract.Attendees.ATTENDEE_STATUS_ACCEPTED || + attendee.status == CalendarContract.Attendees.ATTENDEE_STATUS_DECLINED || + attendee.status == CalendarContract.Attendees.ATTENDEE_STATUS_TENTATIVE + + val attendeeStatusImage = resources.getDrawable(when (attendee.status) { + CalendarContract.Attendees.ATTENDEE_STATUS_ACCEPTED -> R.drawable.ic_check_green + CalendarContract.Attendees.ATTENDEE_STATUS_DECLINED -> R.drawable.ic_cross_red + else -> R.drawable.ic_question_yellow + }) + + val attendeeStatusBackground = resources.getDrawable(R.drawable.attendee_status_circular_background) + (attendeeStatusBackground as LayerDrawable).findDrawableByLayerId(R.id.attendee_status_circular_background).applyColorFilter(config.backgroundColor) + selectedAttendeeStatusImage.background = attendeeStatusBackground + autoCompleteView.beGone() autoCompleteView.focusSearch(View.FOCUS_DOWN)?.requestFocus() selectedAttendeeName.text = attendee.getPublicName() selectedAttendeeHolder.beVisible() selectedAttendeeImage.beVisible() + selectedAttendeeStatusImage.beVisibleIf(showAttendeeStatus) + selectedAttendeeStatusImage.setImageDrawable(attendeeStatusImage) attendee.updateImage(applicationContext, selectedAttendeeImage, mAttendeePlaceholder) selectedAttendeeDismiss.beVisible() selectedAttendeeDismiss.tag = attendee.contactId diff --git a/app/src/main/res/drawable-hdpi/ic_check_green.png b/app/src/main/res/drawable-hdpi/ic_check_green.png new file mode 100644 index 0000000000000000000000000000000000000000..cb997b53e574b48d3443fd95f225731932306bdd GIT binary patch literal 600 zcmV-e0;m0nP)Tl+SJwQ543%a|UP#e+r2`t?JN<1R^5nemR9Tux7l(MO}2(Zrr>3+(IGghs|#Ha&6I2y)$@)k}$pTMXZ81x4=q++ij@_}j)<6lJ1run mKz2;AvO|cSa7>rI*nR>7bO~w+5(_r~0000Llub(;Q51%sbMGV?6^TwF7||-CAX$il)qrcEQ0Uq} z5v0E$zo3YJ!gWC?xGo5aADbbFE`pZO_<^a^3dzizF2+e?l5X0wn|sfF&bjY9=L#L6 zrIM-E>jkXcRMiy`$pfgWCn84#!EP>{K9Eu=Y(FRMAJ@g=oN=5_DzYJv>?{JH&=A%A z(Dy%1?(AH2fvQ_u%WCZxV5}FQN8CsdyvuEGpR_>N#p0YvB)$S;sv1=g>3LdJK@~9u z;3jM~*C%&&E<{TuQ+<5=jL3UcrG9lq^ZA+V{Cu4J3i42?@ayi5@uelK|oZnbX{2_}}8L4@1$a{!VF@8n@`@AxC+%Szhl!WYZpvjugn>+kskOB($cr&~)3q9JTFap8Mis-5)W`_7 zukUZ^7*+K;7h`v-XJ-s%vy4nnbANf+(yd3n=ZMG=@U|TiyOVNVrqI(^VRB4J4A``Bd9nI-gn!XUtjg#R-l zal-!&ZA-D-_V!8GY_6la7i-ol6dI`Rh0W%A41tdK2>$(H`wfWCFFNk+&-(xX002ov JPDHLkV1nq6JC6VW literal 0 HcmV?d00001 diff --git a/app/src/main/res/drawable-hdpi/ic_question_yellow.png b/app/src/main/res/drawable-hdpi/ic_question_yellow.png new file mode 100644 index 0000000000000000000000000000000000000000..923e656dd6e1719c50c83844d645e1f39fee638b GIT binary patch literal 622 zcmV-!0+IcRP)Tl*?*UQ51&1wa;l!(=@%PO{7GqEmcYef>1HwK#>*; zikE@V2k-?7oo62CYXmwd2!h&99EceNgbp&03`7V*QlvGPCg-F%%Rw$pb3qW-aPNP8 zd;NRuy@b9{O&H46ILa2t8W3x5WkE9tDMG=tNW$;UlS`1|&I*p~0vo`1{~_)0fCF6J zmT)pR0MgT)yNJ98!T?%xInU;3<_iE=(Fk^I1qnEvlp?B|GMoI`1+^>r+=2MVC)D>3 zp<26KOE7@*avdu?cL8(tfrOJeQB4?1XK#V00P1?w_dcMxxmd4(iAJzv%b105ciAk=W3II<>95mX!{aDhcDu#huveF`SC<%wx`&?CTOFF3 z?Aw$z!^Jxp8CrAk4!@wK3UXxzYbn|;b!abB%sW<$fISp%9GZK+Q4$4>yp?%%=8OpQ`zY=jib8-{!d85?8#(LDgH z#f4Glc?c;(D3}HghDv-zOBJ+K0UgERfKV`PL=rx(ZUe=Ef?bbB`iMsQ2z9+-kRq;b zizIvlAmL;V)y;mG*cK)l!9*j7Z4E+HH#-yH|BsO_>>mf)A4}cW$4R?}aR2}S07*qo IM6N<$f@_8mX8-^I literal 0 HcmV?d00001 diff --git a/app/src/main/res/drawable-xhdpi/ic_check_green.png b/app/src/main/res/drawable-xhdpi/ic_check_green.png new file mode 100644 index 0000000000000000000000000000000000000000..d5e90a672788fe465a26b33169de29e00d891ef8 GIT binary patch literal 617 zcmV-v0+#)WP)8twIy+B!aqPH0YsrlgZFgcJr$5&O26BEC;5EOJ@=h^uFyk? zqr{{$5s0fXF;QZ`tQX3v;EJ_wqxSb8y_&x2#*l|Tu76&i0%sf81Wd0a01G6cv6Wg# zmHQg3oopvUh;a_EX{YTAj1+XH?1+nk;7RtV;g_2Um9m35FZsh7!DGNMli+z7-u37H)>35 zRPed^D50s)ZCs6s8LvY}4hIk=X1Htrk-|OAcGUi&P^Nxe?+MQg1_zploAnpPd#qXiV~jl?qi|j%bJ}Y12skRZMy$Ox2!%t;%|{7_gDobH zfdh!O?t_h1DOdRM^(WQKD$_I50F?5jq2NHX(Y#@iydMco-R-25FFghhkW8Q*+X|(;t#;U6?3 zl^D8aWh-ko#DGLb_y_Hdgcu?r!G!oKEk!91OlS-QDttPafSouWRr_xCIeuQBbC2(} zqJnm2W>Y^R!X&30lOq3X;JD!S0eGHtiee<{vKHQ8?c9B9f`zhiNSF^ zKBd9ue}n^I!E~V#4eXvPk!5Gnbtc2Z{e5-V!vn_Qp(|I3EFa9yHa!^xbba30^Iz#S zU)R?7w!Y5qe7+()y|u-UREm?$O~kTn1Etynx;_t}c4lTmq2}f+j%m3u3>$uPLqjym ztC11>fq*CcVs8)4@26{cn5NE7S4!^kGOX$0aEzi+47RlJdTb1TFv#`U8Q(WHT$R)S z2hj9zIHoBW@+v>r(!!gG30{OkE|VJJcB^2hE?YH;U*zMY&bS@^ONNofL}2IZ#3wI)?e z1X7xr&8`5JD_~jt+}^g~K3~a#)@Wjx+3bqen@r{qS#(COGZ`-S_fd6qyc`(toR(sf z^wt(4;%v`iZ!($F0P?0eCnD)WtRWI1+TTyd;2_Q2-Jaz;O+xMMMEm+sNr;cAjP> z24GimXPSM8EKoFEWn>|;aA%r*#pf}U`Ku`CfBd%m0evWX#3ZG)x`*(PR zedqhmJ@>qOo?r))C%zQ)5 z{y@jp0FbpcSSOBQw;V^p|NilhP1+y+Pi%t~J+Wvr9cE%4{*7-l&JfYaHA zbG9`rb2mDJ`)<eBplllGZ_;Cvg1|R%1iq0KvQj zqNRxI*c$5V_hg_T(0u``uBKR6RHAiB2I}YX_F5io#HtULkd=-W{Lu0Zme31Jo&T&^@@!G<-9_=fN5GxpDeVd)qH3tu>mnrvu*@}b?xRe&6H~Yo(*QUfr*S&Y>?FR3 z5(AJdiwF+JQL1N;GRGS{-gMipyLW$^$p5RGNaj>4VPuvJ-;tTuIU+bbjuOql2;M+1 p1`UjO114J>3j9^1uou5A{{Rkc{>nCpY|sDz002ovPDHLkV1l;)VetR} literal 0 HcmV?d00001 diff --git a/app/src/main/res/drawable-xxhdpi/ic_check_green.png b/app/src/main/res/drawable-xxhdpi/ic_check_green.png new file mode 100644 index 0000000000000000000000000000000000000000..3c2c589fc3e29ae3c1d2c08eab97bf6dfe227ecd GIT binary patch literal 1256 zcmVP)Y}=8}}l}1wnd%6IG5sq396k{bifGd%Nd$Zr6nR zhpx35$KFKgRJ28qsuod%qAJKsgmLSeuW$5RfBsg4`tS80aBHscBcS2$tWCZ=u zm%_k}&u&atP3ZES%Ln)E-~Y1+mjF{EGDTQb?&KF1uHL$IE3^KkvniQI_XiRAYAeFK zgox1P?5m4)f6?{Vli!|HZ1{=^`|tH15?g;=gfI7i$OfqLhnkgZa?;b`5JHJRQC zM7ZQ=-IWSk@u7d{TAMNU5w+XETf$n4h#*10W~?=5i_vEw$TP;VH}{&1^(`|~GbElQ zSX@{{RRInf$KLE4>T^qk!p6Ob(z%ypRF%whhQ!~KJb#uV8Bek}zeY;w3=%Jx-iN&r zkPC{o>?N7G>>Lv#39{)dzVDMwdn_#m0T#?H7kVG|Mocsp?GU7Ary00f6lIDJKgCOX zs8u3vgwBsUInaC{*h|50Pc#?p2nB_*>e{p;6lI!>Cz;L60^l~fw4Z9D<#02`sR;5D zz6~7<1y#HD&MB8^HZxoDO#7)eVn<_$**K?T^kfJ)Uu!bfw`8U>OpGM((jEX2H$vCh zuFX7Cj`Jaq?pl)Bp-k%_-64b+T01gx**Ov;lXw}gDw!(z5DN){Zo(+PoM*M*6KM#) zVO0T&G9^YP$)>YFrA%TicXL&k2%FNUZ*0&XZFDAXG!=q%=*%Fzqvt1l%KSHQ3RF!AS@WA+1 z#>y?m7@A|vbeukp+voz|WjvDcWQBaSlBpcNl`-R()f6yMLCP`2j>c#|)kegPpjLU6 z&XO3JWG*{bA=9fe&%B*XB}_PGHRZH_(>@&Kudl5vFzK*6?YYZpk?ASAkD)6i4zWUt+O`P5r#8-p> literal 0 HcmV?d00001 diff --git a/app/src/main/res/drawable-xxhdpi/ic_cross_red.png b/app/src/main/res/drawable-xxhdpi/ic_cross_red.png new file mode 100644 index 0000000000000000000000000000000000000000..5651f41ca8dfd77170f889d939de6df1e0ed21ec GIT binary patch literal 1409 zcmV-{1%CR8P)n5*^AKwN9x zj!0EO6hvz+A{OvSiF_8Fn3z2jpykog4#zYvYxoLisR_jXvMTU{VcR!4u3cNM8qmVX zNDG0$PXZSK^@hOY#no_=RO*YP*RQXZ|EzGfFf!7j0)a_^OK$-TfD*W*0)feek&%kb zmt<&pbhKm7G=I#2dF!I#_d47DvY5V-3^=BFIY(2eq1I^EJ-lPr#m;2VT9N`3x>gs9&h6pq^ zme>pYtwcVFPE72moZ$r^Ua_EUv-9EwnVlV+begrAV7L^lfB(twCj@I+CoGKG&Z74bKlHtTNc*C zhosim0q})FbPNp!$+e_Dm1~p-_NG8X1MU6&G<9`> z2+rOf>mKxZ(G-kCXz%YQ9F4wi-yK)bqkt0!X+f5{U?f8OzyRUS&H|{_nHkoeKF#ip zBAW7Ge4$Xm#xpaOa>7KZbJb{y2>x)G*zhox-_OSUJa#h4N+N-sN)e1iSV<(ZU_=T5 zG{j=n_hY5bnOf_?S{k@76rwGjEy$O1bGUnZyquk7V_^Y1nH_s-ps6%y7*s{WRdq%p z_;Y(IPoHbs1u%!8saQG>)jUOnx=@I4G>YN#75^a6)I_MY6)7+6Dn$W{wHoECX?11> zC!K!vLup0oW?04uX+Mx z+a|NUjg!fceEAZ`wmH(=jO4(VI?)>VRl{$pYjQFva65NZsnAQVud^~eUC4|-9HuoM zC*0BDNr8yqtFNam9;Y$a`||YVtIxy661d$pIhj-dN~v4GqY6!}NpEhF-r54d2n1;B z@6TptpV1=^%8S0uXV2K%+3}+8Q4YhwBdpdM?KrF?5^Px(&Aq)uy1NTbUng2?GTYl& z)6?v(tq~m@B;47FC{=7TN()12?NCCog+eP+0T?2*L$o=Df&>g;fKY^l%p$^(~4XjA;W2 z@Uim0Zcqe+$lqvg6VabY!->0f0h!d%IBxVXm}5Xou&b#MHt^Xj$SJJFGtzWASv8QE zKi-0Nzd<+zs314vIOyaI`pF!mGoHC2f@+STHnt+RRqEzRV>pMhj>x(%W>*9<^T%5- z?n&U|Kv>sBKS<(S8%IBWib-c6=Xei8HWH1X+BRVA?!np|N3617XAx_t7|I7^Qb*%B zk*^RwEcF-6^F^|wmvL`QmLIKx$X248@W5VVO_V?f!}r*k&kBdnKOAoKaDJFdebZ@j z7q8-uRRQBQhC4P%_SY-ubeUBz9P;MrvR(k0^l(>x0+-Ag<7%8+f8gAhtb)WZ_vRg( zn|Cm7&Ip(#!#K=;fQ9mK<4-7gzL-xlDn7LFzC_!~?#@^kFwK)y~`hJq!wQ=;_ z2cVa`QPwpPet$nI-iice4a3jG^m`&F7QEh=lY=OF%6{d&X+I30wssI19Ki0}gxD5h zSy-K$hzt&3ZR_y2H=n}27r4ro`l*LGIS8PP8EU|Az)O0;(o=u={!45vp}h$t8ZLQP zqG9a*1hRf@QH+P>fsARxaKMXHP~-# zt;W62Mrf}p^R6JHHTus-{f9nztr>ggHbkU07yzZm70Q|dCh7vpZl?CmdF@1Bdp6!dgq~MpMQXouQ9~yh_-qONwoP?)_?hf z*S9fq9?k9l1O`BJo0vK8vE^mb!(C+6Zv@t0!E*0UllgAMXN!C^h}E&N7Mxkadf!q3 z`C|5Y1~~=jTB5B|8st=AHS1pv*5Vlq=Uy3(;T+cDnL?8fNSaP3QPvUQ>?^=Ii?WUs zm(+EZ(w_8Os-!fs6Wyp-QzekvO6eC+D_%C#rTQ)#d|*{w$5f2)a;{_iA^%4gR(`O5 b|4Q#4INIZ)#m@&f00000NkvXXu0mjf?h;{u literal 0 HcmV?d00001 diff --git a/app/src/main/res/drawable-xxxhdpi/ic_check_green.png b/app/src/main/res/drawable-xxxhdpi/ic_check_green.png new file mode 100644 index 0000000000000000000000000000000000000000..707b53598acb74b9913af15f7e42356b34d9ad6e GIT binary patch literal 1019 zcmVgZy1BgjP zK~!ko<(j=u+fWd|fBr~{B1%PBD5@gdRw$7=5h|8;LjD67n2?w%gjo1n7-}Jl4Rx!8 zI-^cyK@bK8Km`#gszijKP(D%@O#nS&$Pus&q=6N2&6>JVyzjfEdq7LTATR}dyyGV_SN0%EmCfzLpc z)<^*u2Ns*Piqs_hd*E9O!D}fpV(P|nOBI-0nvMap_i&ZFxYmrR8~J-HFu63Xi2#fe ztQ3HRsT-MkgX9MADPZpr;1TcK6AaB;Ks>lcIAqAwjkIqCgxl;9E_qeUog|NdJ$@v& zX%rLP)q!0r24+JD@5IDxT?>fs{P(aBmx?81<<=U1aPJdR)ef5v!|L0%&B4zDth_~^ z)<+~7sdlB9vtz5S8>3-?&t-G`*x13ku(-4eXvu!J5>dhWrD6ebFtZ+80XO{l$vFUO zMCHxf*Yqd*Q53~(g$`3UY{$U{!wBCXpaPecz~2Fa@cl+2N(|A0xg8ESRm1+@Bj(fRr&}7erIF1Rqy~k zvY$~`g{zjqpPihw3chljKB_n1^!SvWja~M$Ic(bw6+CdHiiG_|J@{NU$Kn1V*fzcK zUL;8h13bXCOu5W=OD_LhvbUKbm(2lic5+rx#*ZZefCos+lxvl@_vna9>}d=&^6$j$ zSBZe&0aiRMpr{I3q8}}(HKjy=@D&SWz3xV$5wxU#B?5*A$SUcDRXa8D?xl0SzGVqT zq3d}UAaVNZlv1fw&M2$`=f5v_(h;TeStmfy@bji_e07#}jyiQu#}WXUtqj*!*EcNT zNPzGTb0sHU7in7bE=p{!Z2@5At)Sowg1MZLiRQw1qo=%L!pd7g!UK#u4H5TIVo_*z zCnW-eF9_C~l{ryo8SyiNml6TML%9J`>EhhTl+z2V*?M23dS545k%NGrH+AFF4U5+p zGy_cdDYH11P(=AJJ`jIM_<~^bu8q3Nj7^o-i^XEaDi0_%%j-4s0WomM@63v#JT&}} zSF5S+xi}d1ZGJ@ zK~!ko<(j`v8(9>_e=}nbU zf>fI((vl`5AyF_9!qH-{6O4m{4Ys%70%P#Z*q%FqXiww9bI*L=J?Gqe{)~bI$)?j9 zFb2#4kHl{Z7#5EdfK6Z>cqx8&Ov|eIeYfHRv;xcmPl4aNRI>ss1FuZWYWxraVz(ay ztALIisRE0@TBlY~It2d<@LVGBRzwy|%X%S|KsKF@082hxr5o3JW?EL+H-T(AJuU)J z=f_GFNST(k?e>uB0e%k1TmyK-J2L`9=N1qP|K?`MylGkMZ4(e~li_B`L@Rev90K<1 zHMxyfOvEn-cB>dz@&aG0R;8mmIXa?JDtX1klB)&8IsccNmT$Qn2iYtGrpc{DLeAEf z%jDm^qf#o7c<{hW@2~cILb-Iqmfd#$TQ0}m#s-J^JdxpHjHxLG?%qXF6yM;#WHL1B zb)tsB=);F@B&tBF-BTFF02Y4#>TE(-nzU-~pnB!GLL^>8@e8Dlng0VAd;e zL%qEi)6)!1Of-==Di%8?;RfEree714wG(*S*3}q^_$DC%Ja){A2;P%!%>VV%C+a5` zOM7E65;HTz90FS+_;bflMJ3f)k`jq9Ix~YYHH8`uw`GX{zypk_qWtSvLcP6=B$F7) zq$i1hzyr*ML=D@OXu8fwG6_Kb!w2fe$4w*vB11#uH#dU-5AZ0|tp(a4vG@8l;b@e@ zTrLRk=N3r$)#5~=QYu}^ZzO^TNU65ghZGW*V~)zt zImo6e+I)e4kBp2Ezkk0eCM1(s4~br-bns^Z+c!9f9*s7iPJ#sBn0B-&FGGGT(C!V} z@`#l~VqFDxf&}kc0d9aWTOD?xz|ki?21q0J-}aq$oRK*A{Mk#z z;@LpNo=U8>V+FhP#A1w!3QSh+bX+cT^8GvYTFq_u*RFKtL@+Nn<{X;F@Z{wA3+>>$ zJ;yJTP{U!2WRk(LF;q=+TDD-H;^ciuTc_#e z!daD8(uFYN1{dFyJWP-Qr^w67X zHF9cM4~Rbe{LSgCGw(ENa&_PvGNo~x&Ug|KB!1o@pUs`(o#snEWrfpe%(mBqKmDM) zqoQ6YjsQSU*1cgaN zK~!ko)tb+58&wd;Kkx0@P91_1tWpTVRUxUYHdLZXl_H?2h{^$oAV{22!6k>>Dmdhi z@Bt~e9DL!B0~aD8iZ~Rh2_O`TTk)eMsA-})2#Fsdb!_s(_If$w#d5=L{MKH(?p*e; z>v`XK^PPD!Z!GXZ?98MA#DIQaP(9;7RDH4rECMNDK|RwVlCbJsThsws0H=WoV7x{( zNnjedE+PrLDF&$B9tCEAApS@m7z1X#dPR5y{}S+}KJZ`#K5avWMI`aHuLjte$uKZg zohlM2RncYumJYQpiAZ9zZUgMhTmKuTtpHpH5*`OCi{W!wJEl> zjkUB&ap^Ahy)1Ti69kAy!idfe%$^uV?@>fs$cv=|B9cgXHoyz`(ngNrcRx}5`8JfQ zBoiqy`+6`3Pa!+n>o!6hK%3=*bq0U}#ica)%X46ryfMg-1YaM*?1`0iRgq_$=pt>x9a!2=ZLu2H;`*3HRNPI+&C zp09eUmU5fyd^U$)lD|ApDf_R^r{fCa|0$$S*iD_?-}!tVYjMSu+h$)cX8%cKXUDF= z_p%gIH+O^FC0301F+#7M)1^{)@5HY3z^D%RQYPyTzWoqw7e@#VpDlw2kewX_htJY> zaRkwR$eEIhE0i)>T`G;+F1T1v}^5 z-ipJI5qfhNA!SYaO?Bz?WJAFJ^$*)0e*t;tW<@^z1fjQHK?DM|F0m$6!|p$A3I%pP zz3K|y=!p?}`$9e70Tv~@*L?m5?0gE_rMfiwdI^r4M;Nl+Wm1yeyGnnlv!0>&!>`WZ zdt(GIynqnGkEIqG;(_ALJ1!At5`6VVzrdG0koMgJzy0Bw>qRK&=Td2@TC=3T6xwj6 z&(Ur_mr069!rF_XXmJk+xT}~-e}1KZ6cDeC4d?(jPdZu*xo>- zG7-<>;UfP5@BXY~YosoXzN&YH%@03v?&dyt&kqA$t{i~ecND4@$rj%Ib0q@xZ`@HdR i{@KIDm + + + + + + + diff --git a/app/src/main/res/layout/item_attendee.xml b/app/src/main/res/layout/item_attendee.xml index e1d294a2b..8be5afdfd 100644 --- a/app/src/main/res/layout/item_attendee.xml +++ b/app/src/main/res/layout/item_attendee.xml @@ -37,6 +37,18 @@ android:layout_margin="@dimen/tiny_margin" android:adjustViewBounds="true"/> + + + tools:text="Simple Mobile Tools"/> 100dp 40dp + 16dp From ed7e90e17d3d08d27644aa690a4b0e83996f5b8e Mon Sep 17 00:00:00 2001 From: tibbi Date: Tue, 19 Mar 2019 15:01:59 +0100 Subject: [PATCH 11/39] sort attendees by status in a specific way --- .../calendar/pro/activities/EventActivity.kt | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt index 49d89139d..c7ce708de 100644 --- a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt +++ b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt @@ -1148,6 +1148,13 @@ class EventActivity : SimpleActivity() { } private fun updateAttendees() { + mAttendees.sortWith(compareBy + { it.status == CalendarContract.Attendees.ATTENDEE_STATUS_ACCEPTED }.thenBy + { it.status == CalendarContract.Attendees.ATTENDEE_STATUS_DECLINED }.thenBy + { it.status == CalendarContract.Attendees.ATTENDEE_STATUS_TENTATIVE }.thenBy + { it.status }) + mAttendees.reverse() + mAttendees.forEach { val attendee = it val deviceContact = mAvailableContacts.firstOrNull { it.email.isNotEmpty() && it.email == attendee.email && it.photoUri.isNotEmpty() } From 2907023b372db683d6bca0917c54e002a52948b2 Mon Sep 17 00:00:00 2001 From: tibbi Date: Tue, 19 Mar 2019 20:58:34 +0100 Subject: [PATCH 12/39] fixing an illegal offset exception caused by daylight savings --- .../calendar/pro/activities/EventActivity.kt | 23 +++++++++++-------- 1 file changed, 14 insertions(+), 9 deletions(-) diff --git a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt index c7ce708de..619075b48 100644 --- a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt +++ b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt @@ -1100,17 +1100,22 @@ class EventActivity : SimpleActivity() { } private fun timeSet(hours: Int, minutes: Int, isStart: Boolean) { - if (isStart) { - val diff = mEventEndDateTime.seconds() - mEventStartDateTime.seconds() + try { + if (isStart) { + val diff = mEventEndDateTime.seconds() - mEventStartDateTime.seconds() - mEventStartDateTime = mEventStartDateTime.withHourOfDay(hours).withMinuteOfHour(minutes) - updateStartTimeText() + mEventStartDateTime = mEventStartDateTime.withHourOfDay(hours).withMinuteOfHour(minutes) + updateStartTimeText() - mEventEndDateTime = mEventStartDateTime.plusSeconds(diff.toInt()) - updateEndTexts() - } else { - mEventEndDateTime = mEventEndDateTime.withHourOfDay(hours).withMinuteOfHour(minutes) - updateEndTimeText() + mEventEndDateTime = mEventStartDateTime.plusSeconds(diff.toInt()) + updateEndTexts() + } else { + mEventEndDateTime = mEventEndDateTime.withHourOfDay(hours).withMinuteOfHour(minutes) + updateEndTimeText() + } + } catch (e: Exception) { + timeSet(hours + 1, minutes, isStart) + return } } From b99fba72b2cec4a6e6a7e6248a19ea0ed969053d Mon Sep 17 00:00:00 2001 From: tibbi Date: Tue, 19 Mar 2019 22:08:24 +0100 Subject: [PATCH 13/39] use full alpha at event details screen images, not reduced one --- app/src/main/res/layout/activity_event.xml | 9 --------- 1 file changed, 9 deletions(-) diff --git a/app/src/main/res/layout/activity_event.xml b/app/src/main/res/layout/activity_event.xml index 7b1bfe893..fdb31df3a 100644 --- a/app/src/main/res/layout/activity_event.xml +++ b/app/src/main/res/layout/activity_event.xml @@ -92,7 +92,6 @@ android:layout_alignBottom="@+id/event_all_day" android:layout_marginStart="@dimen/normal_margin" android:layout_marginLeft="@dimen/normal_margin" - android:alpha="0.8" android:padding="@dimen/medium_margin" android:src="@drawable/ic_clock"/> @@ -177,7 +176,6 @@ android:layout_alignTop="@+id/event_reminder_1" android:layout_alignBottom="@+id/event_reminder_1" android:layout_marginStart="@dimen/normal_margin" - android:alpha="0.8" android:padding="@dimen/medium_margin" android:src="@drawable/ic_bell"/> @@ -205,7 +203,6 @@ android:layout_alignBottom="@+id/event_reminder_1" android:layout_alignParentEnd="true" android:layout_marginStart="@dimen/small_margin" - android:alpha="0.8" android:background="?attr/selectableItemBackground" android:padding="@dimen/activity_margin" android:src="@drawable/ic_bell"/> @@ -236,7 +233,6 @@ android:layout_alignBottom="@+id/event_reminder_2" android:layout_alignParentEnd="true" android:layout_marginStart="@dimen/small_margin" - android:alpha="0.8" android:background="?attr/selectableItemBackground" android:padding="@dimen/activity_margin" android:src="@drawable/ic_bell"/> @@ -267,7 +263,6 @@ android:layout_alignBottom="@+id/event_reminder_3" android:layout_alignParentEnd="true" android:layout_marginStart="@dimen/small_margin" - android:alpha="0.8" android:background="?attr/selectableItemBackground" android:padding="@dimen/activity_margin" android:src="@drawable/ic_bell"/> @@ -290,7 +285,6 @@ android:layout_alignTop="@+id/event_repetition" android:layout_alignBottom="@+id/event_repetition" android:layout_marginStart="@dimen/normal_margin" - android:alpha="0.8" android:padding="@dimen/medium_margin" android:src="@drawable/ic_repeat"/> @@ -387,7 +381,6 @@ android:layout_alignTop="@+id/event_attendees_holder" android:layout_marginStart="@dimen/normal_margin" android:layout_marginTop="@dimen/small_margin" - android:alpha="0.8" android:padding="@dimen/medium_margin" android:src="@drawable/ic_people"/> @@ -417,7 +410,6 @@ android:layout_alignTop="@+id/event_caldav_calendar_holder" android:layout_alignBottom="@+id/event_caldav_calendar_holder" android:layout_marginStart="@dimen/normal_margin" - android:alpha="0.8" android:padding="@dimen/medium_margin" android:src="@drawable/ic_calendar" android:visibility="gone"/> @@ -487,7 +479,6 @@ android:layout_alignTop="@+id/event_type_holder" android:layout_alignBottom="@+id/event_type_holder" android:layout_marginStart="@dimen/normal_margin" - android:alpha="0.8" android:padding="@dimen/medium_margin" android:src="@drawable/ic_color"/> From e79871daabcc1853b6b6fcf3db14d417d48ba447 Mon Sep 17 00:00:00 2001 From: tibbi Date: Tue, 19 Mar 2019 22:29:59 +0100 Subject: [PATCH 14/39] adding some new attendance related strings --- app/src/main/res/values-ar/strings.xml | 5 +++++ app/src/main/res/values-az/strings.xml | 5 +++++ app/src/main/res/values-br/strings.xml | 5 +++++ app/src/main/res/values-cs/strings.xml | 5 +++++ app/src/main/res/values-da/strings.xml | 5 +++++ app/src/main/res/values-de/strings.xml | 5 +++++ app/src/main/res/values-el/strings.xml | 5 +++++ app/src/main/res/values-es/strings.xml | 5 +++++ app/src/main/res/values-fr/strings.xml | 5 +++++ app/src/main/res/values-gl/strings.xml | 5 +++++ app/src/main/res/values-hi-rIN/strings.xml | 5 +++++ app/src/main/res/values-hr/strings.xml | 5 +++++ app/src/main/res/values-hu/strings.xml | 5 +++++ app/src/main/res/values-it/strings.xml | 5 +++++ app/src/main/res/values-iw/strings.xml | 5 +++++ app/src/main/res/values-ja/strings.xml | 5 +++++ app/src/main/res/values-ko/strings.xml | 5 +++++ app/src/main/res/values-lt/strings.xml | 5 +++++ app/src/main/res/values-nb/strings.xml | 5 +++++ app/src/main/res/values-nl/strings.xml | 5 +++++ app/src/main/res/values-no/strings.xml | 5 +++++ app/src/main/res/values-pl/strings.xml | 5 +++++ app/src/main/res/values-pt-rBR/strings.xml | 5 +++++ app/src/main/res/values-pt/strings.xml | 5 +++++ app/src/main/res/values-ru/strings.xml | 5 +++++ app/src/main/res/values-sk/strings.xml | 5 +++++ app/src/main/res/values-sv/strings.xml | 5 +++++ app/src/main/res/values-tr/strings.xml | 5 +++++ app/src/main/res/values-zh-rTW/strings.xml | 5 +++++ app/src/main/res/values/strings.xml | 5 +++++ 30 files changed, 150 insertions(+) diff --git a/app/src/main/res/values-ar/strings.xml b/app/src/main/res/values-ar/strings.xml index 6526b5710..546509269 100644 --- a/app/src/main/res/values-ar/strings.xml +++ b/app/src/main/res/values-ar/strings.xml @@ -100,6 +100,11 @@ Add another attendee + My status: + Going + Not going + Maybe going + Invited إستيراد الأحداث diff --git a/app/src/main/res/values-az/strings.xml b/app/src/main/res/values-az/strings.xml index 6c7a3188d..10b3a5784 100644 --- a/app/src/main/res/values-az/strings.xml +++ b/app/src/main/res/values-az/strings.xml @@ -100,6 +100,11 @@ Add another attendee + My status: + Going + Not going + Maybe going + Invited Hadisələri daxil et diff --git a/app/src/main/res/values-br/strings.xml b/app/src/main/res/values-br/strings.xml index 4dc3ed6d6..ee8eabd61 100644 --- a/app/src/main/res/values-br/strings.xml +++ b/app/src/main/res/values-br/strings.xml @@ -100,6 +100,11 @@ Add another attendee + My status: + Going + Not going + Maybe going + Invited Enporzhiañ darvoudoù diff --git a/app/src/main/res/values-cs/strings.xml b/app/src/main/res/values-cs/strings.xml index 3e70a3faf..b100531b3 100644 --- a/app/src/main/res/values-cs/strings.xml +++ b/app/src/main/res/values-cs/strings.xml @@ -100,6 +100,11 @@ Add another attendee + My status: + Going + Not going + Maybe going + Invited Import událostí diff --git a/app/src/main/res/values-da/strings.xml b/app/src/main/res/values-da/strings.xml index 0980297f7..6021f4ab1 100644 --- a/app/src/main/res/values-da/strings.xml +++ b/app/src/main/res/values-da/strings.xml @@ -100,6 +100,11 @@ Tilføj en anden deltager + My status: + Going + Not going + Maybe going + Invited Importer begivenheder diff --git a/app/src/main/res/values-de/strings.xml b/app/src/main/res/values-de/strings.xml index d00356a86..e8fefb40b 100644 --- a/app/src/main/res/values-de/strings.xml +++ b/app/src/main/res/values-de/strings.xml @@ -100,6 +100,11 @@ Add another attendee + My status: + Going + Not going + Maybe going + Invited Termine importieren diff --git a/app/src/main/res/values-el/strings.xml b/app/src/main/res/values-el/strings.xml index ff658773b..361213556 100644 --- a/app/src/main/res/values-el/strings.xml +++ b/app/src/main/res/values-el/strings.xml @@ -100,6 +100,11 @@ Προσθήκη άλλης συμμετοχής + My status: + Going + Not going + Maybe going + Invited Εισαγωγή εκδηλώσεων diff --git a/app/src/main/res/values-es/strings.xml b/app/src/main/res/values-es/strings.xml index 5094cdd06..b0c3c3587 100644 --- a/app/src/main/res/values-es/strings.xml +++ b/app/src/main/res/values-es/strings.xml @@ -100,6 +100,11 @@ Add another attendee + My status: + Going + Not going + Maybe going + Invited Importar eventos diff --git a/app/src/main/res/values-fr/strings.xml b/app/src/main/res/values-fr/strings.xml index 061ab69bf..3e1388849 100644 --- a/app/src/main/res/values-fr/strings.xml +++ b/app/src/main/res/values-fr/strings.xml @@ -100,6 +100,11 @@ Add another attendee + My status: + Going + Not going + Maybe going + Invited Importer des événements diff --git a/app/src/main/res/values-gl/strings.xml b/app/src/main/res/values-gl/strings.xml index aa4cd2dfc..768a6a1da 100644 --- a/app/src/main/res/values-gl/strings.xml +++ b/app/src/main/res/values-gl/strings.xml @@ -100,6 +100,11 @@ Add another attendee + My status: + Going + Not going + Maybe going + Invited Importar eventos diff --git a/app/src/main/res/values-hi-rIN/strings.xml b/app/src/main/res/values-hi-rIN/strings.xml index 2f910dd7b..2c410f3a1 100644 --- a/app/src/main/res/values-hi-rIN/strings.xml +++ b/app/src/main/res/values-hi-rIN/strings.xml @@ -101,6 +101,11 @@ Add another attendee + My status: + Going + Not going + Maybe going + Invited Import events diff --git a/app/src/main/res/values-hr/strings.xml b/app/src/main/res/values-hr/strings.xml index b00c1ed47..81f44dd5c 100644 --- a/app/src/main/res/values-hr/strings.xml +++ b/app/src/main/res/values-hr/strings.xml @@ -100,6 +100,11 @@ Add another attendee + My status: + Going + Not going + Maybe going + Invited Uvezi događaje diff --git a/app/src/main/res/values-hu/strings.xml b/app/src/main/res/values-hu/strings.xml index 6ba16b8b4..999a3361e 100644 --- a/app/src/main/res/values-hu/strings.xml +++ b/app/src/main/res/values-hu/strings.xml @@ -100,6 +100,11 @@ Add another attendee + My status: + Going + Not going + Maybe going + Invited Import events diff --git a/app/src/main/res/values-it/strings.xml b/app/src/main/res/values-it/strings.xml index a74e2503a..146df7adb 100644 --- a/app/src/main/res/values-it/strings.xml +++ b/app/src/main/res/values-it/strings.xml @@ -100,6 +100,11 @@ Aggiungi un partecipante + My status: + Going + Not going + Maybe going + Invited Importa eventi diff --git a/app/src/main/res/values-iw/strings.xml b/app/src/main/res/values-iw/strings.xml index 2deca09aa..1b8ebbb1e 100644 --- a/app/src/main/res/values-iw/strings.xml +++ b/app/src/main/res/values-iw/strings.xml @@ -101,6 +101,11 @@ Add another attendee + My status: + Going + Not going + Maybe going + Invited ייבוא אירועים diff --git a/app/src/main/res/values-ja/strings.xml b/app/src/main/res/values-ja/strings.xml index 48e37bb40..b06e871c8 100644 --- a/app/src/main/res/values-ja/strings.xml +++ b/app/src/main/res/values-ja/strings.xml @@ -100,6 +100,11 @@ Add another attendee + My status: + Going + Not going + Maybe going + Invited 予定をインポート diff --git a/app/src/main/res/values-ko/strings.xml b/app/src/main/res/values-ko/strings.xml index dcc3cf051..72ee8d37d 100644 --- a/app/src/main/res/values-ko/strings.xml +++ b/app/src/main/res/values-ko/strings.xml @@ -100,6 +100,11 @@ Add another attendee + My status: + Going + Not going + Maybe going + Invited 이벤트들 가져 오기 diff --git a/app/src/main/res/values-lt/strings.xml b/app/src/main/res/values-lt/strings.xml index 6565d1c17..27d067f32 100644 --- a/app/src/main/res/values-lt/strings.xml +++ b/app/src/main/res/values-lt/strings.xml @@ -100,6 +100,11 @@ Add another attendee + My status: + Going + Not going + Maybe going + Invited Importuoti įvykius diff --git a/app/src/main/res/values-nb/strings.xml b/app/src/main/res/values-nb/strings.xml index 5bd496760..d4ed11fd9 100644 --- a/app/src/main/res/values-nb/strings.xml +++ b/app/src/main/res/values-nb/strings.xml @@ -100,6 +100,11 @@ Add another attendee + My status: + Going + Not going + Maybe going + Invited Importer hendelser diff --git a/app/src/main/res/values-nl/strings.xml b/app/src/main/res/values-nl/strings.xml index 90b682ce3..7001fedd9 100644 --- a/app/src/main/res/values-nl/strings.xml +++ b/app/src/main/res/values-nl/strings.xml @@ -100,6 +100,11 @@ Persoon uitnodigen + My status: + Going + Not going + Maybe going + Invited Afspraken importeren diff --git a/app/src/main/res/values-no/strings.xml b/app/src/main/res/values-no/strings.xml index bc2d43845..4622f4556 100644 --- a/app/src/main/res/values-no/strings.xml +++ b/app/src/main/res/values-no/strings.xml @@ -100,6 +100,11 @@ Add another attendee + My status: + Going + Not going + Maybe going + Invited Importer hendelser diff --git a/app/src/main/res/values-pl/strings.xml b/app/src/main/res/values-pl/strings.xml index d42131618..d1a7627c1 100644 --- a/app/src/main/res/values-pl/strings.xml +++ b/app/src/main/res/values-pl/strings.xml @@ -100,6 +100,11 @@ Add another attendee + My status: + Going + Not going + Maybe going + Invited Importuj wydarzenia diff --git a/app/src/main/res/values-pt-rBR/strings.xml b/app/src/main/res/values-pt-rBR/strings.xml index 23d15b340..30daae394 100644 --- a/app/src/main/res/values-pt-rBR/strings.xml +++ b/app/src/main/res/values-pt-rBR/strings.xml @@ -100,6 +100,11 @@ Add another attendee + My status: + Going + Not going + Maybe going + Invited Importar eventos diff --git a/app/src/main/res/values-pt/strings.xml b/app/src/main/res/values-pt/strings.xml index 7c94ba846..7ba01a3db 100644 --- a/app/src/main/res/values-pt/strings.xml +++ b/app/src/main/res/values-pt/strings.xml @@ -100,6 +100,11 @@ Add another attendee + My status: + Going + Not going + Maybe going + Invited Importar eventos diff --git a/app/src/main/res/values-ru/strings.xml b/app/src/main/res/values-ru/strings.xml index b4b8a2036..0123d00d3 100644 --- a/app/src/main/res/values-ru/strings.xml +++ b/app/src/main/res/values-ru/strings.xml @@ -100,6 +100,11 @@ Добавить участника + My status: + Going + Not going + Maybe going + Invited Импорт событий diff --git a/app/src/main/res/values-sk/strings.xml b/app/src/main/res/values-sk/strings.xml index 5bfab56f0..797a8bf12 100644 --- a/app/src/main/res/values-sk/strings.xml +++ b/app/src/main/res/values-sk/strings.xml @@ -100,6 +100,11 @@ Pridať ďalšieho účastníka + Môj stav: + Zúčastním sa + Nezúčastním sa + Možno sa zúčastním + Pozvaný Importovať udalosti diff --git a/app/src/main/res/values-sv/strings.xml b/app/src/main/res/values-sv/strings.xml index d706923a5..5b72b6fb2 100644 --- a/app/src/main/res/values-sv/strings.xml +++ b/app/src/main/res/values-sv/strings.xml @@ -100,6 +100,11 @@ Add another attendee + My status: + Going + Not going + Maybe going + Invited Importera händelser diff --git a/app/src/main/res/values-tr/strings.xml b/app/src/main/res/values-tr/strings.xml index 8974088ad..680d14a2a 100644 --- a/app/src/main/res/values-tr/strings.xml +++ b/app/src/main/res/values-tr/strings.xml @@ -100,6 +100,11 @@ Add another attendee + My status: + Going + Not going + Maybe going + Invited Etkinlikleri içe aktar diff --git a/app/src/main/res/values-zh-rTW/strings.xml b/app/src/main/res/values-zh-rTW/strings.xml index b0ff0501f..7418edf57 100644 --- a/app/src/main/res/values-zh-rTW/strings.xml +++ b/app/src/main/res/values-zh-rTW/strings.xml @@ -100,6 +100,11 @@ Add another attendee + My status: + Going + Not going + Maybe going + Invited 匯入活動 diff --git a/app/src/main/res/values/strings.xml b/app/src/main/res/values/strings.xml index d76ea886e..2df13500b 100644 --- a/app/src/main/res/values/strings.xml +++ b/app/src/main/res/values/strings.xml @@ -100,6 +100,11 @@ Add another attendee + My status: + Going + Not going + Maybe going + Invited Import events From 638ccdb82c5432671dd205c0c52b54c7da4bfad6 Mon Sep 17 00:00:00 2001 From: spkprs Date: Tue, 19 Mar 2019 23:52:29 +0200 Subject: [PATCH 15/39] Update strings.xml --- app/src/main/res/values-el/strings.xml | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/app/src/main/res/values-el/strings.xml b/app/src/main/res/values-el/strings.xml index 361213556..b2c01970f 100644 --- a/app/src/main/res/values-el/strings.xml +++ b/app/src/main/res/values-el/strings.xml @@ -100,11 +100,11 @@ Προσθήκη άλλης συμμετοχής - My status: - Going - Not going - Maybe going - Invited + Η κατάσταση μου: + Πηγαίνω + Δεν πηγαίνω + Ίσως πάω + Καλεσμένος Εισαγωγή εκδηλώσεων From 898a5bd5270e4bbe208ef3b5db56d79363ad8162 Mon Sep 17 00:00:00 2001 From: Guillaume Date: Tue, 19 Mar 2019 23:26:46 +0100 Subject: [PATCH 16/39] Dutch --- app/src/main/res/values-nl/strings.xml | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/app/src/main/res/values-nl/strings.xml b/app/src/main/res/values-nl/strings.xml index 7001fedd9..4ae29e6eb 100644 --- a/app/src/main/res/values-nl/strings.xml +++ b/app/src/main/res/values-nl/strings.xml @@ -100,11 +100,11 @@ Persoon uitnodigen - My status: - Going - Not going - Maybe going - Invited + Mijn status: + Aanwezig + Niet aanwezig + Misschien + Uitgenodigd Afspraken importeren From 660278ce611eef8c835ac3d988931f8767a4ef9f Mon Sep 17 00:00:00 2001 From: tibbi Date: Tue, 19 Mar 2019 23:26:59 +0100 Subject: [PATCH 17/39] show my attendance status in a special way --- .../calendar/pro/activities/EventActivity.kt | 19 +++++++++++++++++-- .../calendar/pro/helpers/Constants.kt | 1 + app/src/main/res/layout/item_attendee.xml | 13 +++++++++++++ 3 files changed, 31 insertions(+), 2 deletions(-) diff --git a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt index 619075b48..87f3bbe3c 100644 --- a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt +++ b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt @@ -1160,9 +1160,15 @@ class EventActivity : SimpleActivity() { { it.status }) mAttendees.reverse() + val currentCalendar = calDAVHelper.getCalDAVCalendars("", true).firstOrNull { it.id == mEventCalendarId } + mAttendees.forEach { val attendee = it val deviceContact = mAvailableContacts.firstOrNull { it.email.isNotEmpty() && it.email == attendee.email && it.photoUri.isNotEmpty() } + if (attendee.email == currentCalendar?.accountName) { + attendee.name = ATTENDEE_ME + } + if (deviceContact != null) { attendee.photoUri = deviceContact.photoUri } @@ -1244,17 +1250,26 @@ class EventActivity : SimpleActivity() { val attendeeStatusBackground = resources.getDrawable(R.drawable.attendee_status_circular_background) (attendeeStatusBackground as LayerDrawable).findDrawableByLayerId(R.id.attendee_status_circular_background).applyColorFilter(config.backgroundColor) selectedAttendeeStatusImage.background = attendeeStatusBackground + val isMe = attendee.name == ATTENDEE_ME autoCompleteView.beGone() autoCompleteView.focusSearch(View.FOCUS_DOWN)?.requestFocus() - selectedAttendeeName.text = attendee.getPublicName() + selectedAttendeeName.text = if (isMe) getString(R.string.my_status) else attendee.getPublicName() selectedAttendeeHolder.beVisible() selectedAttendeeImage.beVisible() selectedAttendeeStatusImage.beVisibleIf(showAttendeeStatus) selectedAttendeeStatusImage.setImageDrawable(attendeeStatusImage) attendee.updateImage(applicationContext, selectedAttendeeImage, mAttendeePlaceholder) - selectedAttendeeDismiss.beVisible() + selectedAttendeeDismiss.beGoneIf(isMe) selectedAttendeeDismiss.tag = attendee.contactId + + selectedAttendeeHolder.event_contact_me_status.beVisibleIf(isMe) + selectedAttendeeHolder.event_contact_me_status.text = getString(when (attendee.status) { + CalendarContract.Attendees.ATTENDEE_STATUS_ACCEPTED -> R.string.going + CalendarContract.Attendees.ATTENDEE_STATUS_DECLINED -> R.string.not_going + CalendarContract.Attendees.ATTENDEE_STATUS_TENTATIVE -> R.string.maybe_going + else -> R.string.invited + }) } private fun checkNewAttendeeField() { diff --git a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/helpers/Constants.kt b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/helpers/Constants.kt index 4878387c7..7a969ed77 100644 --- a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/helpers/Constants.kt +++ b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/helpers/Constants.kt @@ -16,6 +16,7 @@ const val WEEK_START_DATE_TIME = "week_start_date_time" const val CALDAV = "Caldav" const val VIEW_TO_OPEN = "view_to_open" const val SHORTCUT_NEW_EVENT = "shortcut_new_event" +const val ATTENDEE_ME = "attendee_me" const val REGULAR_EVENT_TYPE_ID = 1L const val CHOPPED_LIST_DEFAULT_SIZE = 100 diff --git a/app/src/main/res/layout/item_attendee.xml b/app/src/main/res/layout/item_attendee.xml index 8be5afdfd..8c5bd897e 100644 --- a/app/src/main/res/layout/item_attendee.xml +++ b/app/src/main/res/layout/item_attendee.xml @@ -74,5 +74,18 @@ android:padding="@dimen/small_margin" android:src="@drawable/ic_cross_big"/> + + From 66df18e849fadc2938b166c7b02c86e6670578b2 Mon Sep 17 00:00:00 2001 From: tibbi Date: Tue, 19 Mar 2019 23:30:38 +0100 Subject: [PATCH 18/39] make sure we show our status first --- .../calendar/pro/activities/EventActivity.kt | 15 +++++++++------ 1 file changed, 9 insertions(+), 6 deletions(-) diff --git a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt index 87f3bbe3c..43f4162f9 100644 --- a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt +++ b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt @@ -1153,22 +1153,25 @@ class EventActivity : SimpleActivity() { } private fun updateAttendees() { + val currentCalendar = calDAVHelper.getCalDAVCalendars("", true).firstOrNull { it.id == mEventCalendarId } + + mAttendees.forEach { + if (it.email == currentCalendar?.accountName) { + it.name = ATTENDEE_ME + } + } + mAttendees.sortWith(compareBy + { it.name == ATTENDEE_ME }.thenBy { it.status == CalendarContract.Attendees.ATTENDEE_STATUS_ACCEPTED }.thenBy { it.status == CalendarContract.Attendees.ATTENDEE_STATUS_DECLINED }.thenBy { it.status == CalendarContract.Attendees.ATTENDEE_STATUS_TENTATIVE }.thenBy { it.status }) mAttendees.reverse() - val currentCalendar = calDAVHelper.getCalDAVCalendars("", true).firstOrNull { it.id == mEventCalendarId } - mAttendees.forEach { val attendee = it val deviceContact = mAvailableContacts.firstOrNull { it.email.isNotEmpty() && it.email == attendee.email && it.photoUri.isNotEmpty() } - if (attendee.email == currentCalendar?.accountName) { - attendee.name = ATTENDEE_ME - } - if (deviceContact != null) { attendee.photoUri = deviceContact.photoUri } From c2216ed0fc9e8cc12cd79e62bbe184a4cbc80d06 Mon Sep 17 00:00:00 2001 From: tibbi Date: Tue, 19 Mar 2019 23:56:06 +0100 Subject: [PATCH 19/39] make sure there are no overlapping texts at the event attendees --- .../calendar/pro/activities/EventActivity.kt | 4 ++++ app/src/main/res/layout/item_attendee.xml | 1 + 2 files changed, 5 insertions(+) diff --git a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt index 43f4162f9..ca15a7510 100644 --- a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt +++ b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt @@ -1266,6 +1266,10 @@ class EventActivity : SimpleActivity() { selectedAttendeeDismiss.beGoneIf(isMe) selectedAttendeeDismiss.tag = attendee.contactId + if (isMe) { + (selectedAttendeeName.layoutParams as RelativeLayout.LayoutParams).addRule(RelativeLayout.START_OF, selectedAttendeeHolder.event_contact_me_status.id) + } + selectedAttendeeHolder.event_contact_me_status.beVisibleIf(isMe) selectedAttendeeHolder.event_contact_me_status.text = getString(when (attendee.status) { CalendarContract.Attendees.ATTENDEE_STATUS_ACCEPTED -> R.string.going diff --git a/app/src/main/res/layout/item_attendee.xml b/app/src/main/res/layout/item_attendee.xml index 8c5bd897e..7bd73e26e 100644 --- a/app/src/main/res/layout/item_attendee.xml +++ b/app/src/main/res/layout/item_attendee.xml @@ -80,6 +80,7 @@ android:layout_height="wrap_content" android:layout_alignParentEnd="true" android:layout_centerVertical="true" + android:layout_marginStart="@dimen/normal_margin" android:layout_marginEnd="@dimen/activity_margin" android:ellipsize="end" android:gravity="end" From 9ec52a4ab7494c1ace0563298b5983be3a6f2241 Mon Sep 17 00:00:00 2001 From: tibbi Date: Wed, 20 Mar 2019 10:05:50 +0100 Subject: [PATCH 20/39] tweaking some view referencing around attendees --- app/build.gradle | 2 +- .../calendar/pro/activities/EventActivity.kt | 69 +++++++++++-------- 2 files changed, 40 insertions(+), 31 deletions(-) diff --git a/app/build.gradle b/app/build.gradle index 58c7e298c..3425737cf 100644 --- a/app/build.gradle +++ b/app/build.gradle @@ -57,7 +57,7 @@ android { } dependencies { - implementation 'com.simplemobiletools:commons:5.10.10' + implementation 'com.simplemobiletools:commons:5.10.13' implementation 'joda-time:joda-time:2.10.1' implementation 'androidx.multidex:multidex:2.0.1' implementation 'androidx.constraintlayout:constraintlayout:2.0.0-alpha3' diff --git a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt index ca15a7510..a692230fd 100644 --- a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt +++ b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt @@ -35,7 +35,6 @@ import com.simplemobiletools.commons.extensions.* import com.simplemobiletools.commons.helpers.* import com.simplemobiletools.commons.models.RadioItem import com.simplemobiletools.commons.views.MyAutoCompleteTextView -import com.simplemobiletools.commons.views.MyTextView import kotlinx.android.synthetic.main.activity_event.* import kotlinx.android.synthetic.main.activity_event.view.* import kotlinx.android.synthetic.main.item_attendee.view.* @@ -1193,7 +1192,6 @@ class EventActivity : SimpleActivity() { val attendeeHolder = layoutInflater.inflate(R.layout.item_attendee, event_attendees_holder, false) as RelativeLayout val autoCompleteView = attendeeHolder.event_attendee val selectedAttendeeHolder = attendeeHolder.event_contact_attendee - val selectedAttendeeName = selectedAttendeeHolder.event_contact_name val selectedAttendeeDismiss = attendeeHolder.event_contact_dismiss mAttendeeAutoCompleteViews.add(autoCompleteView) @@ -1212,7 +1210,7 @@ class EventActivity : SimpleActivity() { val textColor = config.textColor autoCompleteView.setColors(textColor, getAdjustedPrimaryColor(), config.backgroundColor) - selectedAttendeeName.setColors(textColor, getAdjustedPrimaryColor(), config.backgroundColor) + selectedAttendeeHolder.event_contact_name.setColors(textColor, getAdjustedPrimaryColor(), config.backgroundColor) selectedAttendeeDismiss.applyColorFilter(textColor) selectedAttendeeDismiss.setOnClickListener { @@ -1226,20 +1224,17 @@ class EventActivity : SimpleActivity() { autoCompleteView.setOnItemClickListener { parent, view, position, id -> val currAttendees = (autoCompleteView.adapter as AutoCompleteTextViewAdapter).resultList val selectedAttendee = currAttendees[position] - addSelectedAttendee(selectedAttendee, autoCompleteView, selectedAttendeeHolder, selectedAttendeeName, selectedAttendeeDismiss) + addSelectedAttendee(selectedAttendee, autoCompleteView, selectedAttendeeHolder) } if (attendee != null) { - addSelectedAttendee(attendee, autoCompleteView, selectedAttendeeHolder, selectedAttendeeName, selectedAttendeeDismiss) + addSelectedAttendee(attendee, autoCompleteView, selectedAttendeeHolder) } } - private fun addSelectedAttendee(attendee: Attendee, autoCompleteView: MyAutoCompleteTextView, selectedAttendeeHolder: RelativeLayout, - selectedAttendeeName: MyTextView, selectedAttendeeDismiss: ImageView) { + private fun addSelectedAttendee(attendee: Attendee, autoCompleteView: MyAutoCompleteTextView, selectedAttendeeHolder: RelativeLayout) { mSelectedContacts.add(attendee) - val selectedAttendeeImage = selectedAttendeeHolder.event_contact_image - val selectedAttendeeStatusImage = selectedAttendeeHolder.event_contact_status_image val showAttendeeStatus = attendee.status == CalendarContract.Attendees.ATTENDEE_STATUS_ACCEPTED || attendee.status == CalendarContract.Attendees.ATTENDEE_STATUS_DECLINED || attendee.status == CalendarContract.Attendees.ATTENDEE_STATUS_TENTATIVE @@ -1250,33 +1245,47 @@ class EventActivity : SimpleActivity() { else -> R.drawable.ic_question_yellow }) - val attendeeStatusBackground = resources.getDrawable(R.drawable.attendee_status_circular_background) - (attendeeStatusBackground as LayerDrawable).findDrawableByLayerId(R.id.attendee_status_circular_background).applyColorFilter(config.backgroundColor) - selectedAttendeeStatusImage.background = attendeeStatusBackground val isMe = attendee.name == ATTENDEE_ME autoCompleteView.beGone() autoCompleteView.focusSearch(View.FOCUS_DOWN)?.requestFocus() - selectedAttendeeName.text = if (isMe) getString(R.string.my_status) else attendee.getPublicName() - selectedAttendeeHolder.beVisible() - selectedAttendeeImage.beVisible() - selectedAttendeeStatusImage.beVisibleIf(showAttendeeStatus) - selectedAttendeeStatusImage.setImageDrawable(attendeeStatusImage) - attendee.updateImage(applicationContext, selectedAttendeeImage, mAttendeePlaceholder) - selectedAttendeeDismiss.beGoneIf(isMe) - selectedAttendeeDismiss.tag = attendee.contactId - if (isMe) { - (selectedAttendeeName.layoutParams as RelativeLayout.LayoutParams).addRule(RelativeLayout.START_OF, selectedAttendeeHolder.event_contact_me_status.id) + selectedAttendeeHolder.apply { + beVisible() + + val attendeeStatusBackground = resources.getDrawable(R.drawable.attendee_status_circular_background) + (attendeeStatusBackground as LayerDrawable).findDrawableByLayerId(R.id.attendee_status_circular_background).applyColorFilter(config.backgroundColor) + event_contact_status_image.apply { + background = attendeeStatusBackground + setImageDrawable(attendeeStatusImage) + beVisibleIf(showAttendeeStatus) + } + + event_contact_image.apply { + attendee.updateImage(applicationContext, this, mAttendeePlaceholder) + beVisible() + } + + event_contact_dismiss.apply { + tag = attendee.contactId + beGoneIf(isMe) + } + + event_contact_name.text = if (isMe) getString(R.string.my_status) else attendee.getPublicName() + if (isMe) { + (event_contact_name.layoutParams as RelativeLayout.LayoutParams).addRule(RelativeLayout.START_OF, event_contact_me_status.id) + } + + event_contact_me_status.apply { + beVisibleIf(isMe) + text = getString(when (attendee.status) { + CalendarContract.Attendees.ATTENDEE_STATUS_ACCEPTED -> R.string.going + CalendarContract.Attendees.ATTENDEE_STATUS_DECLINED -> R.string.not_going + CalendarContract.Attendees.ATTENDEE_STATUS_TENTATIVE -> R.string.maybe_going + else -> R.string.invited + }) + } } - - selectedAttendeeHolder.event_contact_me_status.beVisibleIf(isMe) - selectedAttendeeHolder.event_contact_me_status.text = getString(when (attendee.status) { - CalendarContract.Attendees.ATTENDEE_STATUS_ACCEPTED -> R.string.going - CalendarContract.Attendees.ATTENDEE_STATUS_DECLINED -> R.string.not_going - CalendarContract.Attendees.ATTENDEE_STATUS_TENTATIVE -> R.string.maybe_going - else -> R.string.invited - }) } private fun checkNewAttendeeField() { From 389b50c553362883214134677daaec78c47c6caf Mon Sep 17 00:00:00 2001 From: tibbi Date: Wed, 20 Mar 2019 11:42:36 +0100 Subject: [PATCH 21/39] allow changing the attendance status of myself --- .../calendar/pro/activities/EventActivity.kt | 63 +++++++++++++------ .../calendar/pro/models/Attendee.kt | 5 ++ app/src/main/res/layout/item_attendee.xml | 1 + 3 files changed, 51 insertions(+), 18 deletions(-) diff --git a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt index a692230fd..62330c59f 100644 --- a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt +++ b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt @@ -1235,16 +1235,6 @@ class EventActivity : SimpleActivity() { private fun addSelectedAttendee(attendee: Attendee, autoCompleteView: MyAutoCompleteTextView, selectedAttendeeHolder: RelativeLayout) { mSelectedContacts.add(attendee) - val showAttendeeStatus = attendee.status == CalendarContract.Attendees.ATTENDEE_STATUS_ACCEPTED || - attendee.status == CalendarContract.Attendees.ATTENDEE_STATUS_DECLINED || - attendee.status == CalendarContract.Attendees.ATTENDEE_STATUS_TENTATIVE - - val attendeeStatusImage = resources.getDrawable(when (attendee.status) { - CalendarContract.Attendees.ATTENDEE_STATUS_ACCEPTED -> R.drawable.ic_check_green - CalendarContract.Attendees.ATTENDEE_STATUS_DECLINED -> R.drawable.ic_cross_red - else -> R.drawable.ic_question_yellow - }) - val isMe = attendee.name == ATTENDEE_ME autoCompleteView.beGone() @@ -1257,8 +1247,8 @@ class EventActivity : SimpleActivity() { (attendeeStatusBackground as LayerDrawable).findDrawableByLayerId(R.id.attendee_status_circular_background).applyColorFilter(config.backgroundColor) event_contact_status_image.apply { background = attendeeStatusBackground - setImageDrawable(attendeeStatusImage) - beVisibleIf(showAttendeeStatus) + setImageDrawable(getAttendeeStatusImage(attendee)) + beVisibleIf(attendee.showStatusImage()) } event_contact_image.apply { @@ -1276,14 +1266,51 @@ class EventActivity : SimpleActivity() { (event_contact_name.layoutParams as RelativeLayout.LayoutParams).addRule(RelativeLayout.START_OF, event_contact_me_status.id) } + if (isMe) { + updateAttendeeMe(this, attendee) + } + event_contact_me_status.apply { beVisibleIf(isMe) - text = getString(when (attendee.status) { - CalendarContract.Attendees.ATTENDEE_STATUS_ACCEPTED -> R.string.going - CalendarContract.Attendees.ATTENDEE_STATUS_DECLINED -> R.string.not_going - CalendarContract.Attendees.ATTENDEE_STATUS_TENTATIVE -> R.string.maybe_going - else -> R.string.invited - }) + } + + if (isMe) { + event_contact_attendee.setOnClickListener { + val items = arrayListOf( + RadioItem(CalendarContract.Attendees.ATTENDEE_STATUS_ACCEPTED, getString(R.string.going)), + RadioItem(CalendarContract.Attendees.ATTENDEE_STATUS_DECLINED, getString(R.string.not_going)), + RadioItem(CalendarContract.Attendees.ATTENDEE_STATUS_TENTATIVE, getString(R.string.maybe_going)) + ) + + RadioGroupDialog(this@EventActivity, items, attendee.status) { + attendee.status = it as Int + updateAttendeeMe(this, attendee) + } + } + } + } + } + + private fun getAttendeeStatusImage(attendee: Attendee): Drawable { + return resources.getDrawable(when (attendee.status) { + CalendarContract.Attendees.ATTENDEE_STATUS_ACCEPTED -> R.drawable.ic_check_green + CalendarContract.Attendees.ATTENDEE_STATUS_DECLINED -> R.drawable.ic_cross_red + else -> R.drawable.ic_question_yellow + }) + } + + private fun updateAttendeeMe(holder: RelativeLayout, attendee: Attendee) { + holder.apply { + event_contact_me_status.text = getString(when (attendee.status) { + CalendarContract.Attendees.ATTENDEE_STATUS_ACCEPTED -> R.string.going + CalendarContract.Attendees.ATTENDEE_STATUS_DECLINED -> R.string.not_going + CalendarContract.Attendees.ATTENDEE_STATUS_TENTATIVE -> R.string.maybe_going + else -> R.string.invited + }) + + event_contact_status_image.apply { + beVisibleIf(attendee.showStatusImage()) + setImageDrawable(getAttendeeStatusImage(attendee)) } } } diff --git a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/models/Attendee.kt b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/models/Attendee.kt index 2468b34a9..2fd9c634a 100644 --- a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/models/Attendee.kt +++ b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/models/Attendee.kt @@ -2,6 +2,7 @@ package com.simplemobiletools.calendar.pro.models import android.content.Context import android.graphics.drawable.Drawable +import android.provider.CalendarContract import android.widget.ImageView import com.bumptech.glide.Glide import com.bumptech.glide.load.engine.DiskCacheStrategy @@ -28,4 +29,8 @@ data class Attendee(val contactId: Int, var name: String, val email: String, var .into(imageView) } } + + fun showStatusImage() = status == CalendarContract.Attendees.ATTENDEE_STATUS_ACCEPTED || + status == CalendarContract.Attendees.ATTENDEE_STATUS_DECLINED || + status == CalendarContract.Attendees.ATTENDEE_STATUS_TENTATIVE } diff --git a/app/src/main/res/layout/item_attendee.xml b/app/src/main/res/layout/item_attendee.xml index 7bd73e26e..b178606b2 100644 --- a/app/src/main/res/layout/item_attendee.xml +++ b/app/src/main/res/layout/item_attendee.xml @@ -28,6 +28,7 @@ android:layout_height="@dimen/avatar_size" android:layout_alignTop="@+id/event_attendee" android:layout_alignBottom="@+id/event_attendee" + android:background="?attr/selectableItemBackground" android:visibility="gone"> Date: Wed, 20 Mar 2019 11:56:38 +0100 Subject: [PATCH 22/39] properly store attendee statuses --- .../simplemobiletools/calendar/pro/activities/EventActivity.kt | 3 ++- .../com/simplemobiletools/calendar/pro/helpers/CalDAVHelper.kt | 2 +- 2 files changed, 3 insertions(+), 2 deletions(-) diff --git a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt index 62330c59f..e018417ed 100644 --- a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt +++ b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt @@ -1312,6 +1312,8 @@ class EventActivity : SimpleActivity() { beVisibleIf(attendee.showStatusImage()) setImageDrawable(getAttendeeStatusImage(attendee)) } + + mAttendees.firstOrNull { it.name == ATTENDEE_ME }?.status = attendee.status } } @@ -1324,7 +1326,6 @@ class EventActivity : SimpleActivity() { private fun getAllAttendees(): String { var attendees = ArrayList() mSelectedContacts.forEach { - it.status = CalendarContract.Attendees.ATTENDEE_STATUS_INVITED attendees.add(it) } diff --git a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/helpers/CalDAVHelper.kt b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/helpers/CalDAVHelper.kt index 1bc9af72f..8cd19e572 100644 --- a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/helpers/CalDAVHelper.kt +++ b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/helpers/CalDAVHelper.kt @@ -368,7 +368,7 @@ class CalDAVHelper(val context: Context) { val contentValues = ContentValues().apply { put(CalendarContract.Attendees.ATTENDEE_NAME, it.name) put(CalendarContract.Attendees.ATTENDEE_EMAIL, it.email) - put(CalendarContract.Attendees.ATTENDEE_STATUS, CalendarContract.Attendees.ATTENDEE_STATUS_ACCEPTED) + put(CalendarContract.Attendees.ATTENDEE_STATUS, it.status) put(CalendarContract.Attendees.EVENT_ID, event.getCalDAVEventId()) } From c95429556852d9184e516a4caa417df0a4928345 Mon Sep 17 00:00:00 2001 From: Emanuele Petriglia Date: Wed, 20 Mar 2019 13:09:49 +0000 Subject: [PATCH 23/39] Update italian translation to e79871d --- app/src/main/res/values-it/strings.xml | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/app/src/main/res/values-it/strings.xml b/app/src/main/res/values-it/strings.xml index 146df7adb..0f9ba7c01 100644 --- a/app/src/main/res/values-it/strings.xml +++ b/app/src/main/res/values-it/strings.xml @@ -100,11 +100,11 @@ Aggiungi un partecipante - My status: - Going - Not going - Maybe going - Invited + Il mio stato: + Andando + Non andando + Forse + Invitato Importa eventi From b76512edf974d2671dfaa54250326ae30d8cfc0f Mon Sep 17 00:00:00 2001 From: tibbi Date: Wed, 20 Mar 2019 16:53:54 +0100 Subject: [PATCH 24/39] change the way attendees are loaded --- .../calendar/pro/activities/EventActivity.kt | 46 +++++++++++-------- .../calendar/pro/helpers/CalDAVHelper.kt | 2 +- .../calendar/pro/models/Attendee.kt | 3 +- 3 files changed, 29 insertions(+), 22 deletions(-) diff --git a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt index e018417ed..b2fa07210 100644 --- a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt +++ b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt @@ -109,7 +109,6 @@ class EventActivity : SimpleActivity() { runOnUiThread { gotEvent(savedInstanceState, localEventType, event) } - fillAvailableContacts() }.start() } @@ -149,7 +148,6 @@ class EventActivity : SimpleActivity() { updateTexts() updateEventType() updateCalDAVCalendar() - updateAttendees() } event_show_on_map.setOnClickListener { showOnMap() } @@ -298,7 +296,7 @@ class EventActivity : SimpleActivity() { updateTexts() updateEventType() updateCalDAVCalendar() - updateAttendees() + checkAttendees() } private fun updateTexts() { @@ -333,6 +331,7 @@ class EventActivity : SimpleActivity() { mEventCalendarId = mEvent.getCalDAVCalendarId() mAttendees = Gson().fromJson>(mEvent.attendees, object : TypeToken>() {}.type) ?: ArrayList() checkRepeatTexts(mRepeatInterval) + checkAttendees() } private fun setupNewEvent() { @@ -367,6 +366,17 @@ class EventActivity : SimpleActivity() { } mEventEndDateTime = mEventStartDateTime.plusMinutes(addMinutes) } + + checkAttendees() + } + + private fun checkAttendees() { + Thread { + fillAvailableContacts() + runOnUiThread { + updateAttendees() + } + }.start() } private fun handleNotificationAvailability(callback: () -> Unit) { @@ -1153,15 +1163,12 @@ class EventActivity : SimpleActivity() { private fun updateAttendees() { val currentCalendar = calDAVHelper.getCalDAVCalendars("", true).firstOrNull { it.id == mEventCalendarId } - mAttendees.forEach { - if (it.email == currentCalendar?.accountName) { - it.name = ATTENDEE_ME - } + it.isMe = it.email == currentCalendar?.accountName } mAttendees.sortWith(compareBy - { it.name == ATTENDEE_ME }.thenBy + { it.isMe }.thenBy { it.status == CalendarContract.Attendees.ATTENDEE_STATUS_ACCEPTED }.thenBy { it.status == CalendarContract.Attendees.ATTENDEE_STATUS_DECLINED }.thenBy { it.status == CalendarContract.Attendees.ATTENDEE_STATUS_TENTATIVE }.thenBy @@ -1211,6 +1218,7 @@ class EventActivity : SimpleActivity() { val textColor = config.textColor autoCompleteView.setColors(textColor, getAdjustedPrimaryColor(), config.backgroundColor) selectedAttendeeHolder.event_contact_name.setColors(textColor, getAdjustedPrimaryColor(), config.backgroundColor) + selectedAttendeeHolder.event_contact_me_status.setColors(textColor, getAdjustedPrimaryColor(), config.backgroundColor) selectedAttendeeDismiss.applyColorFilter(textColor) selectedAttendeeDismiss.setOnClickListener { @@ -1235,8 +1243,6 @@ class EventActivity : SimpleActivity() { private fun addSelectedAttendee(attendee: Attendee, autoCompleteView: MyAutoCompleteTextView, selectedAttendeeHolder: RelativeLayout) { mSelectedContacts.add(attendee) - val isMe = attendee.name == ATTENDEE_ME - autoCompleteView.beGone() autoCompleteView.focusSearch(View.FOCUS_DOWN)?.requestFocus() @@ -1258,23 +1264,23 @@ class EventActivity : SimpleActivity() { event_contact_dismiss.apply { tag = attendee.contactId - beGoneIf(isMe) + beGoneIf(attendee.isMe) } - event_contact_name.text = if (isMe) getString(R.string.my_status) else attendee.getPublicName() - if (isMe) { + event_contact_name.text = if (attendee.isMe) getString(R.string.my_status) else attendee.getPublicName() + if (attendee.isMe) { (event_contact_name.layoutParams as RelativeLayout.LayoutParams).addRule(RelativeLayout.START_OF, event_contact_me_status.id) } - if (isMe) { + if (attendee.isMe) { updateAttendeeMe(this, attendee) } event_contact_me_status.apply { - beVisibleIf(isMe) + beVisibleIf(attendee.isMe) } - if (isMe) { + if (attendee.isMe) { event_contact_attendee.setOnClickListener { val items = arrayListOf( RadioItem(CalendarContract.Attendees.ATTENDEE_STATUS_ACCEPTED, getString(R.string.going)), @@ -1313,7 +1319,7 @@ class EventActivity : SimpleActivity() { setImageDrawable(getAttendeeStatusImage(attendee)) } - mAttendees.firstOrNull { it.name == ATTENDEE_ME }?.status = attendee.status + mAttendees.firstOrNull { it.isMe }?.status = attendee.status } } @@ -1331,7 +1337,7 @@ class EventActivity : SimpleActivity() { val customEmails = mAttendeeAutoCompleteViews.filter { it.isVisible() }.map { it.value }.filter { it.isNotEmpty() }.toMutableList() as ArrayList customEmails.mapTo(attendees) { - Attendee(0, "", it, CalendarContract.Attendees.ATTENDEE_STATUS_INVITED, "") + Attendee(0, "", it, CalendarContract.Attendees.ATTENDEE_STATUS_INVITED, "", false) } attendees = attendees.distinctBy { it.email }.toMutableList() as ArrayList return Gson().toJson(attendees) @@ -1368,7 +1374,7 @@ class EventActivity : SimpleActivity() { val names = arrayListOf(prefix, firstName, middleName, surname, suffix).filter { it.trim().isNotEmpty() } val fullName = TextUtils.join("", names) if (fullName.isNotEmpty() || photoUri.isNotEmpty()) { - val contact = Attendee(id, fullName, "", 0, photoUri) + val contact = Attendee(id, fullName, "", 0, photoUri, false) contacts.add(contact) } } while (cursor.moveToNext()) @@ -1395,7 +1401,7 @@ class EventActivity : SimpleActivity() { do { val id = cursor.getIntValue(ContactsContract.Data.CONTACT_ID) val email = cursor.getStringValue(ContactsContract.CommonDataKinds.Email.DATA) ?: continue - val contact = Attendee(id, "", email, 0, "") + val contact = Attendee(id, "", email, 0, "", false) contacts.add(contact) } while (cursor.moveToNext()) } diff --git a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/helpers/CalDAVHelper.kt b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/helpers/CalDAVHelper.kt index 8cd19e572..e69a9fc1f 100644 --- a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/helpers/CalDAVHelper.kt +++ b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/helpers/CalDAVHelper.kt @@ -514,7 +514,7 @@ class CalDAVHelper(val context: Context) { val name = cursor.getStringValue(CalendarContract.Attendees.ATTENDEE_NAME) val email = cursor.getStringValue(CalendarContract.Attendees.ATTENDEE_EMAIL) val status = cursor.getIntValue(CalendarContract.Attendees.ATTENDEE_STATUS) - val attendee = Attendee(0, name, email, status, "") + val attendee = Attendee(0, name, email, status, "", false) attendees.add(attendee) } while (cursor.moveToNext()) } diff --git a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/models/Attendee.kt b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/models/Attendee.kt index 2fd9c634a..58e2f804d 100644 --- a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/models/Attendee.kt +++ b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/models/Attendee.kt @@ -9,7 +9,7 @@ import com.bumptech.glide.load.engine.DiskCacheStrategy import com.bumptech.glide.load.resource.drawable.DrawableTransitionOptions import com.bumptech.glide.request.RequestOptions -data class Attendee(val contactId: Int, var name: String, val email: String, var status: Int, var photoUri: String) { +data class Attendee(val contactId: Int, var name: String, val email: String, var status: Int, var photoUri: String, var isMe: Boolean) { fun getPublicName() = if (name.isNotEmpty()) name else email fun updateImage(context: Context, imageView: ImageView, placeholder: Drawable) { @@ -24,6 +24,7 @@ data class Attendee(val contactId: Int, var name: String, val email: String, var Glide.with(context) .load(photoUri) .transition(DrawableTransitionOptions.withCrossFade()) + .placeholder(placeholder) .apply(options) .apply(RequestOptions.circleCropTransform()) .into(imageView) From 673b97110e2f67a2fb2b04a1b976f817ba44c8ca Mon Sep 17 00:00:00 2001 From: tibbi Date: Wed, 20 Mar 2019 18:20:02 +0100 Subject: [PATCH 25/39] add myself as an event attendee if there is any other attendee --- .../calendar/pro/activities/EventActivity.kt | 15 ++++++++++++--- .../calendar/pro/helpers/Constants.kt | 1 - 2 files changed, 12 insertions(+), 4 deletions(-) diff --git a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt index b2fa07210..a34dca824 100644 --- a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt +++ b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt @@ -253,7 +253,7 @@ class EventActivity : SimpleActivity() { putInt(REPEAT_RULE, mRepeatRule) putLong(REPEAT_LIMIT, mRepeatLimit) - putString(ATTENDEES, getAllAttendees()) + putString(ATTENDEES, getAllAttendees(false)) putLong(EVENT_TYPE_ID, mEventTypeId) putInt(EVENT_CALENDAR_ID, mEventCalendarId) @@ -921,7 +921,7 @@ class EventActivity : SimpleActivity() { flags = mEvent.flags.addBitIf(event_all_day.isChecked, FLAG_ALL_DAY) repeatLimit = if (repeatInterval == 0) 0 else mRepeatLimit repeatRule = mRepeatRule - attendees = if (mEventCalendarId == STORED_LOCALLY_ONLY) "" else getAllAttendees() + attendees = if (mEventCalendarId == STORED_LOCALLY_ONLY) "" else getAllAttendees(true) eventType = newEventType lastUpdated = System.currentTimeMillis() source = newSource @@ -1329,7 +1329,7 @@ class EventActivity : SimpleActivity() { } } - private fun getAllAttendees(): String { + private fun getAllAttendees(isSavingEvent: Boolean): String { var attendees = ArrayList() mSelectedContacts.forEach { attendees.add(it) @@ -1340,6 +1340,15 @@ class EventActivity : SimpleActivity() { Attendee(0, "", it, CalendarContract.Attendees.ATTENDEE_STATUS_INVITED, "", false) } attendees = attendees.distinctBy { it.email }.toMutableList() as ArrayList + + if (mEvent.id == null && isSavingEvent && attendees.isNotEmpty()) { + val currentCalendar = calDAVHelper.getCalDAVCalendars("", true).firstOrNull { it.id == mEventCalendarId } + mAvailableContacts.firstOrNull { it.email == currentCalendar?.accountName }?.apply { + status = CalendarContract.Attendees.ATTENDEE_STATUS_ACCEPTED + attendees.add(this) + } + } + return Gson().toJson(attendees) } diff --git a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/helpers/Constants.kt b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/helpers/Constants.kt index 7a969ed77..4878387c7 100644 --- a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/helpers/Constants.kt +++ b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/helpers/Constants.kt @@ -16,7 +16,6 @@ const val WEEK_START_DATE_TIME = "week_start_date_time" const val CALDAV = "Caldav" const val VIEW_TO_OPEN = "view_to_open" const val SHORTCUT_NEW_EVENT = "shortcut_new_event" -const val ATTENDEE_ME = "attendee_me" const val REGULAR_EVENT_TYPE_ID = 1L const val CHOPPED_LIST_DEFAULT_SIZE = 100 From 1ca6f6379a279afa48f01ab104591cf8100aa0cb Mon Sep 17 00:00:00 2001 From: tibbi Date: Wed, 20 Mar 2019 18:26:51 +0100 Subject: [PATCH 26/39] handle attendee relationships (roles) --- .../calendar/pro/activities/EventActivity.kt | 7 ++++--- .../simplemobiletools/calendar/pro/helpers/CalDAVHelper.kt | 7 +++++-- .../com/simplemobiletools/calendar/pro/models/Attendee.kt | 2 +- 3 files changed, 10 insertions(+), 6 deletions(-) diff --git a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt index a34dca824..555528d0d 100644 --- a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt +++ b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt @@ -1337,7 +1337,7 @@ class EventActivity : SimpleActivity() { val customEmails = mAttendeeAutoCompleteViews.filter { it.isVisible() }.map { it.value }.filter { it.isNotEmpty() }.toMutableList() as ArrayList customEmails.mapTo(attendees) { - Attendee(0, "", it, CalendarContract.Attendees.ATTENDEE_STATUS_INVITED, "", false) + Attendee(0, "", it, CalendarContract.Attendees.ATTENDEE_STATUS_INVITED, "", false, CalendarContract.Attendees.RELATIONSHIP_NONE) } attendees = attendees.distinctBy { it.email }.toMutableList() as ArrayList @@ -1345,6 +1345,7 @@ class EventActivity : SimpleActivity() { val currentCalendar = calDAVHelper.getCalDAVCalendars("", true).firstOrNull { it.id == mEventCalendarId } mAvailableContacts.firstOrNull { it.email == currentCalendar?.accountName }?.apply { status = CalendarContract.Attendees.ATTENDEE_STATUS_ACCEPTED + relationship = CalendarContract.Attendees.RELATIONSHIP_ORGANIZER attendees.add(this) } } @@ -1383,7 +1384,7 @@ class EventActivity : SimpleActivity() { val names = arrayListOf(prefix, firstName, middleName, surname, suffix).filter { it.trim().isNotEmpty() } val fullName = TextUtils.join("", names) if (fullName.isNotEmpty() || photoUri.isNotEmpty()) { - val contact = Attendee(id, fullName, "", 0, photoUri, false) + val contact = Attendee(id, fullName, "", CalendarContract.Attendees.ATTENDEE_STATUS_NONE, photoUri, false, CalendarContract.Attendees.RELATIONSHIP_NONE) contacts.add(contact) } } while (cursor.moveToNext()) @@ -1410,7 +1411,7 @@ class EventActivity : SimpleActivity() { do { val id = cursor.getIntValue(ContactsContract.Data.CONTACT_ID) val email = cursor.getStringValue(ContactsContract.CommonDataKinds.Email.DATA) ?: continue - val contact = Attendee(id, "", email, 0, "", false) + val contact = Attendee(id, "", email, CalendarContract.Attendees.ATTENDEE_STATUS_NONE, "", false, CalendarContract.Attendees.RELATIONSHIP_NONE) contacts.add(contact) } while (cursor.moveToNext()) } diff --git a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/helpers/CalDAVHelper.kt b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/helpers/CalDAVHelper.kt index e69a9fc1f..304e536da 100644 --- a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/helpers/CalDAVHelper.kt +++ b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/helpers/CalDAVHelper.kt @@ -369,6 +369,7 @@ class CalDAVHelper(val context: Context) { put(CalendarContract.Attendees.ATTENDEE_NAME, it.name) put(CalendarContract.Attendees.ATTENDEE_EMAIL, it.email) put(CalendarContract.Attendees.ATTENDEE_STATUS, it.status) + put(CalendarContract.Attendees.ATTENDEE_RELATIONSHIP, it.relationship) put(CalendarContract.Attendees.EVENT_ID, event.getCalDAVEventId()) } @@ -504,7 +505,8 @@ class CalDAVHelper(val context: Context) { val projection = arrayOf( CalendarContract.Attendees.ATTENDEE_NAME, CalendarContract.Attendees.ATTENDEE_EMAIL, - CalendarContract.Attendees.ATTENDEE_STATUS) + CalendarContract.Attendees.ATTENDEE_STATUS, + CalendarContract.Attendees.ATTENDEE_RELATIONSHIP) val selection = "${CalendarContract.Attendees.EVENT_ID} = $eventId" var cursor: Cursor? = null try { @@ -514,7 +516,8 @@ class CalDAVHelper(val context: Context) { val name = cursor.getStringValue(CalendarContract.Attendees.ATTENDEE_NAME) val email = cursor.getStringValue(CalendarContract.Attendees.ATTENDEE_EMAIL) val status = cursor.getIntValue(CalendarContract.Attendees.ATTENDEE_STATUS) - val attendee = Attendee(0, name, email, status, "", false) + val relationship = cursor.getIntValue(CalendarContract.Attendees.ATTENDEE_RELATIONSHIP) + val attendee = Attendee(0, name, email, status, "", false, relationship) attendees.add(attendee) } while (cursor.moveToNext()) } diff --git a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/models/Attendee.kt b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/models/Attendee.kt index 58e2f804d..004b3201f 100644 --- a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/models/Attendee.kt +++ b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/models/Attendee.kt @@ -9,7 +9,7 @@ import com.bumptech.glide.load.engine.DiskCacheStrategy import com.bumptech.glide.load.resource.drawable.DrawableTransitionOptions import com.bumptech.glide.request.RequestOptions -data class Attendee(val contactId: Int, var name: String, val email: String, var status: Int, var photoUri: String, var isMe: Boolean) { +data class Attendee(val contactId: Int, var name: String, val email: String, var status: Int, var photoUri: String, var isMe: Boolean, var relationship: Int) { fun getPublicName() = if (name.isNotEmpty()) name else email fun updateImage(context: Context, imageView: ImageView, placeholder: Drawable) { From 87b14ea7c4077888c977a56125b3b9a77603d5bd Mon Sep 17 00:00:00 2001 From: tibbi Date: Wed, 20 Mar 2019 18:57:59 +0100 Subject: [PATCH 27/39] fix #573, listen to CalDAV events in the background, update asap --- app/src/main/AndroidManifest.xml | 5 ++ .../calendar/pro/activities/MainActivity.kt | 18 +++++ .../calendar/pro/jobs/CalDAVUpdateListener.kt | 65 +++++++++++++++++++ 3 files changed, 88 insertions(+) create mode 100644 app/src/main/kotlin/com/simplemobiletools/calendar/pro/jobs/CalDAVUpdateListener.kt diff --git a/app/src/main/AndroidManifest.xml b/app/src/main/AndroidManifest.xml index 00a9a0f36..f8c4de799 100644 --- a/app/src/main/AndroidManifest.xml +++ b/app/src/main/AndroidManifest.xml @@ -177,6 +177,11 @@ + + diff --git a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/MainActivity.kt b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/MainActivity.kt index 489e81dcf..d592a2a7d 100644 --- a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/MainActivity.kt +++ b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/MainActivity.kt @@ -31,6 +31,7 @@ import com.simplemobiletools.calendar.pro.extensions.* import com.simplemobiletools.calendar.pro.fragments.* import com.simplemobiletools.calendar.pro.helpers.* import com.simplemobiletools.calendar.pro.helpers.Formatter +import com.simplemobiletools.calendar.pro.jobs.CalDAVUpdateListener import com.simplemobiletools.calendar.pro.models.Event import com.simplemobiletools.calendar.pro.models.EventType import com.simplemobiletools.calendar.pro.models.ListEvent @@ -102,6 +103,10 @@ class MainActivity : SimpleActivity(), RefreshRecyclerViewListener { } checkAppOnSDCard() + + if (savedInstanceState == null) { + checkCalDAVUpdateListener() + } } override fun onResume() { @@ -265,6 +270,19 @@ class MainActivity : SimpleActivity(), RefreshRecyclerViewListener { mSearchMenuItem?.collapseActionView() } + private fun checkCalDAVUpdateListener() { + if (isNougatPlus()) { + val updateListener = CalDAVUpdateListener() + if (config.caldavSync) { + if (!updateListener.isScheduled(applicationContext)) { + updateListener.scheduleJob(applicationContext) + } + } else { + updateListener.cancelJob(applicationContext) + } + } + } + @SuppressLint("NewApi") private fun checkShortcuts() { val appIconColor = config.appIconColor diff --git a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/jobs/CalDAVUpdateListener.kt b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/jobs/CalDAVUpdateListener.kt new file mode 100644 index 000000000..510ca3a13 --- /dev/null +++ b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/jobs/CalDAVUpdateListener.kt @@ -0,0 +1,65 @@ +package com.simplemobiletools.calendar.pro.jobs + +import android.annotation.TargetApi +import android.app.job.JobInfo +import android.app.job.JobParameters +import android.app.job.JobScheduler +import android.app.job.JobService +import android.content.ComponentName +import android.content.Context +import android.os.Build +import android.os.Handler +import android.provider.CalendarContract +import com.simplemobiletools.calendar.pro.extensions.recheckCalDAVCalendars + +// based on https://developer.android.com/reference/android/app/job/JobInfo.Builder.html#addTriggerContentUri(android.app.job.JobInfo.TriggerContentUri) +@TargetApi(Build.VERSION_CODES.N) +class CalDAVUpdateListener : JobService() { + companion object { + const val CALDAV_EVENT_CONTENT_JOB = 1 + } + + private val mHandler = Handler() + private val mWorker = Runnable { + scheduleJob(this@CalDAVUpdateListener) + jobFinished(mRunningParams, false) + } + + private var mRunningParams: JobParameters? = null + + fun scheduleJob(context: Context) { + val componentName = ComponentName(context, CalDAVUpdateListener::class.java) + val uri = CalendarContract.Calendars.CONTENT_URI + JobInfo.Builder(CALDAV_EVENT_CONTENT_JOB, componentName).apply { + addTriggerContentUri(JobInfo.TriggerContentUri(uri, JobInfo.TriggerContentUri.FLAG_NOTIFY_FOR_DESCENDANTS)) + context.getSystemService(JobScheduler::class.java).schedule(build()) + } + } + + fun isScheduled(context: Context): Boolean { + val jobScheduler = context.getSystemService(JobScheduler::class.java) + val jobs = jobScheduler.allPendingJobs ?: return false + return jobs.any { it.id == CALDAV_EVENT_CONTENT_JOB } + } + + fun cancelJob(context: Context) { + val js = context.getSystemService(JobScheduler::class.java) + js.cancel(CALDAV_EVENT_CONTENT_JOB) + } + + override fun onStartJob(params: JobParameters): Boolean { + mRunningParams = params + + if (params.triggeredContentAuthorities != null && params.triggeredContentUris != null) { + recheckCalDAVCalendars {} + } + + mHandler.post(mWorker) + return true + } + + override fun onStopJob(params: JobParameters): Boolean { + mHandler.removeCallbacks(mWorker) + return false + } +} From 5ff520c93d86bacbda0ef614e47e3ebc9e170165 Mon Sep 17 00:00:00 2001 From: tibbi Date: Wed, 20 Mar 2019 19:04:22 +0100 Subject: [PATCH 28/39] increase the dimmed events alpha on widgets --- .../calendar/pro/helpers/MyWidgetMonthlyProvider.kt | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/helpers/MyWidgetMonthlyProvider.kt b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/helpers/MyWidgetMonthlyProvider.kt index dce554934..474eafded 100644 --- a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/helpers/MyWidgetMonthlyProvider.kt +++ b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/helpers/MyWidgetMonthlyProvider.kt @@ -112,7 +112,7 @@ class MyWidgetMonthlyProvider : AppWidgetProvider() { } } - val weakTextColor = textColor.adjustAlpha(LOW_ALPHA) + val weakTextColor = textColor.adjustAlpha(MEDIUM_ALPHA) for (i in 0 until len) { val day = days[i] val currTextColor = if (day.isThisMonth) textColor else weakTextColor @@ -126,8 +126,8 @@ class MyWidgetMonthlyProvider : AppWidgetProvider() { var eventTextColor = backgroundColor.getContrastColor() if (!day.isThisMonth || (dimPastEvents && it.isPastEvent)) { - eventTextColor = eventTextColor.adjustAlpha(0.25f) - backgroundColor = backgroundColor.adjustAlpha(0.25f) + eventTextColor = eventTextColor.adjustAlpha(MEDIUM_ALPHA) + backgroundColor = backgroundColor.adjustAlpha(MEDIUM_ALPHA) } val newRemoteView = RemoteViews(packageName, R.layout.day_monthly_event_view).apply { From 15053ef67c340040453bc6d3cb74b74731be6728 Mon Sep 17 00:00:00 2001 From: tibbi Date: Wed, 20 Mar 2019 19:24:59 +0100 Subject: [PATCH 29/39] do not filter out empty reminders at importing events from .ics --- .../com/simplemobiletools/calendar/pro/helpers/IcsImporter.kt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/helpers/IcsImporter.kt b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/helpers/IcsImporter.kt index c834bb5dd..43a7f96e2 100644 --- a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/helpers/IcsImporter.kt +++ b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/helpers/IcsImporter.kt @@ -160,8 +160,8 @@ class IcsImporter(val activity: SimpleActivity) { Reminder(curReminderMinutes.getOrElse(1) { REMINDER_OFF }, curReminderActions.getOrElse(1) { REMINDER_NOTIFICATION }), Reminder(curReminderMinutes.getOrElse(2) { REMINDER_OFF }, curReminderActions.getOrElse(2) { REMINDER_NOTIFICATION }) ) - reminders = reminders.filter { it.minutes != REMINDER_OFF }.sortedBy { it.minutes }.toMutableList() as ArrayList + reminders = reminders.sortedBy { it.minutes }.toMutableList() as ArrayList val eventType = eventTypes.firstOrNull { it.id == curEventTypeId } val source = if (calDAVCalendarId == 0 || eventType?.isSyncedEventType() == false) SOURCE_IMPORTED_ICS else "$CALDAV-$calDAVCalendarId" val event = Event(null, curStart, curEnd, curTitle, curLocation, curDescription, reminders[0].minutes, From 2a9c368329c74f0a4fb3aa6b987569d0f5a0ba29 Mon Sep 17 00:00:00 2001 From: tibbi Date: Wed, 20 Mar 2019 20:10:06 +0100 Subject: [PATCH 30/39] fix #812, fixing some sorting related glitches --- .../pro/adapters/EventListWidgetAdapter.kt | 13 +++++++--- .../calendar/pro/extensions/Context.kt | 26 ++++++++++++++++--- .../calendar/pro/fragments/WeekFragment.kt | 2 +- 3 files changed, 33 insertions(+), 8 deletions(-) diff --git a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/adapters/EventListWidgetAdapter.kt b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/adapters/EventListWidgetAdapter.kt index 2b6a89c75..66d4ac3b7 100644 --- a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/adapters/EventListWidgetAdapter.kt +++ b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/adapters/EventListWidgetAdapter.kt @@ -13,6 +13,7 @@ import com.simplemobiletools.calendar.pro.extensions.eventsHelper import com.simplemobiletools.calendar.pro.extensions.seconds import com.simplemobiletools.calendar.pro.helpers.* import com.simplemobiletools.calendar.pro.helpers.Formatter +import com.simplemobiletools.calendar.pro.models.Event import com.simplemobiletools.calendar.pro.models.ListEvent import com.simplemobiletools.calendar.pro.models.ListItem import com.simplemobiletools.calendar.pro.models.ListSection @@ -159,13 +160,19 @@ class EventListWidgetAdapter(val context: Context) : RemoteViewsService.RemoteVi context.eventsHelper.getEventsSync(fromTS, toTS, applyTypeFilter = true) { val listItems = ArrayList(it.size) val replaceDescription = context.config.replaceDescription - val sorted = it.sortedWith(compareBy({ + val sorted = it.sortedWith(compareBy { if (it.getIsAllDay()) { - Formatter.getDayStartTS(Formatter.getDayCodeFromTS(it.startTS)) + Formatter.getDayStartTS(Formatter.getDayCodeFromTS(it.startTS)) - 1 } else { it.startTS } - }, { it.endTS }, { it.title }, { if (replaceDescription) it.location else it.description })) + }.thenBy { + if (it.getIsAllDay()) { + Formatter.getDayEndTS(Formatter.getDayCodeFromTS(it.endTS)) + } else { + it.endTS + } + }.thenBy { it.title }.thenBy { if (replaceDescription) it.location else it.description }) var prevCode = "" val now = getNowSeconds() diff --git a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/extensions/Context.kt b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/extensions/Context.kt index 3813e37bc..a3a75ea17 100644 --- a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/extensions/Context.kt +++ b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/extensions/Context.kt @@ -393,7 +393,19 @@ private fun addTodaysBackground(textView: TextView, res: Resources, dayLabelHeig fun Context.addDayEvents(day: DayMonthly, linearLayout: LinearLayout, res: Resources, dividerMargin: Int) { val eventLayoutParams = LinearLayout.LayoutParams(ViewGroup.LayoutParams.MATCH_PARENT, ViewGroup.LayoutParams.WRAP_CONTENT) - day.dayEvents.sortedWith(compareBy({ it.startTS }, { it.endTS }, { it.title })).forEach { + day.dayEvents.sortedWith(compareBy { + if (it.getIsAllDay()) { + Formatter.getDayStartTS(Formatter.getDayCodeFromTS(it.startTS)) - 1 + } else { + it.startTS + } + }.thenBy { + if (it.getIsAllDay()) { + Formatter.getDayEndTS(Formatter.getDayCodeFromTS(it.endTS)) + } else { + it.endTS + } + }.thenBy { it.title }).forEach { val backgroundDrawable = res.getDrawable(R.drawable.day_monthly_event_background) backgroundDrawable.applyColorFilter(it.color) eventLayoutParams.setMargins(dividerMargin, 0, dividerMargin, dividerMargin) @@ -420,13 +432,19 @@ fun Context.getEventListItems(events: List): ArrayList { val replaceDescription = config.replaceDescription // move all-day events in front of others - val sorted = events.sortedWith(compareBy({ + val sorted = events.sortedWith(compareBy { if (it.getIsAllDay()) { - Formatter.getDayStartTS(Formatter.getDayCodeFromTS(it.startTS)) + Formatter.getDayStartTS(Formatter.getDayCodeFromTS(it.startTS)) - 1 } else { it.startTS } - }, { it.endTS }, { it.title }, { if (replaceDescription) it.location else it.description })) + }.thenBy { + if (it.getIsAllDay()) { + Formatter.getDayEndTS(Formatter.getDayCodeFromTS(it.endTS)) + } else { + it.endTS + } + }.thenBy { it.title }.thenBy { if (replaceDescription) it.location else it.description }) var prevCode = "" val now = getNowSeconds() diff --git a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/fragments/WeekFragment.kt b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/fragments/WeekFragment.kt index f67f605f2..51f420f24 100644 --- a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/fragments/WeekFragment.kt +++ b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/fragments/WeekFragment.kt @@ -259,7 +259,7 @@ class WeekFragment : Fragment(), WeeklyCalendar { var hadAllDayEvent = false val replaceDescription = mConfig.replaceDescription - val sorted = events.sortedWith(compareBy({ it.startTS }, { it.endTS }, { it.title }, { if (replaceDescription) it.location else it.description })) + val sorted = events.sortedWith(compareBy { it.startTS }.thenBy { it.endTS }.thenBy { it.title }.thenBy { if (replaceDescription) it.location else it.description }) for (event in sorted) { val startDateTime = Formatter.getDateTimeFromTS(event.startTS) val endDateTime = Formatter.getDateTimeFromTS(event.endTS) From 92ec9e29f6139fb51102234411f2cee931689ae4 Mon Sep 17 00:00:00 2001 From: tibbi Date: Wed, 20 Mar 2019 20:27:53 +0100 Subject: [PATCH 31/39] avoid adding myself to the events twice --- .../simplemobiletools/calendar/pro/activities/EventActivity.kt | 1 + 1 file changed, 1 insertion(+) diff --git a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt index 555528d0d..9922a1771 100644 --- a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt +++ b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt @@ -1344,6 +1344,7 @@ class EventActivity : SimpleActivity() { if (mEvent.id == null && isSavingEvent && attendees.isNotEmpty()) { val currentCalendar = calDAVHelper.getCalDAVCalendars("", true).firstOrNull { it.id == mEventCalendarId } mAvailableContacts.firstOrNull { it.email == currentCalendar?.accountName }?.apply { + attendees = attendees.filter { it.email != currentCalendar?.accountName }.toMutableList() as ArrayList status = CalendarContract.Attendees.ATTENDEE_STATUS_ACCEPTED relationship = CalendarContract.Attendees.RELATIONSHIP_ORGANIZER attendees.add(this) From 3c39c193f280b85ef2e1e324f93f9f46cd7cbbb5 Mon Sep 17 00:00:00 2001 From: tibbi Date: Wed, 20 Mar 2019 21:02:33 +0100 Subject: [PATCH 32/39] fix attendee deleting from events --- .../calendar/pro/activities/EventActivity.kt | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt index 9922a1771..f1da95d31 100644 --- a/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt +++ b/app/src/main/kotlin/com/simplemobiletools/calendar/pro/activities/EventActivity.kt @@ -1223,7 +1223,7 @@ class EventActivity : SimpleActivity() { selectedAttendeeDismiss.setOnClickListener { attendeeHolder.beGone() - mSelectedContacts = mSelectedContacts.filter { it.contactId == selectedAttendeeDismiss.tag }.toMutableList() as ArrayList + mSelectedContacts = mSelectedContacts.filter { it.toString() != selectedAttendeeDismiss.tag }.toMutableList() as ArrayList } val adapter = AutoCompleteTextViewAdapter(this, mAvailableContacts) @@ -1263,7 +1263,7 @@ class EventActivity : SimpleActivity() { } event_contact_dismiss.apply { - tag = attendee.contactId + tag = attendee.toString() beGoneIf(attendee.isMe) } From 29bb013bd546358aebe2f89932bbbda71c10e0d2 Mon Sep 17 00:00:00 2001 From: tibbi Date: Wed, 20 Mar 2019 21:27:19 +0100 Subject: [PATCH 33/39] adding some new features at the release notes --- app/src/main/res/values/donottranslate.xml | 3 +++ 1 file changed, 3 insertions(+) diff --git a/app/src/main/res/values/donottranslate.xml b/app/src/main/res/values/donottranslate.xml index e2fbb264c..4a46b6a49 100644 --- a/app/src/main/res/values/donottranslate.xml +++ b/app/src/main/res/values/donottranslate.xml @@ -2,6 +2,9 @@ + + Added email reminders and attendees in CalDAV synced events + Allow setting default start time/duration/event type for new events\n Allow exporting/importing settings From 77cdf720e2f02dc671723ce3a71f40bf974131b0 Mon Sep 17 00:00:00 2001 From: tibbi Date: Wed, 20 Mar 2019 21:35:37 +0100 Subject: [PATCH 34/39] update version to 6.4.0 --- app/build.gradle | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/app/build.gradle b/app/build.gradle index 3425737cf..7f71d6647 100644 --- a/app/build.gradle +++ b/app/build.gradle @@ -16,8 +16,8 @@ android { applicationId "com.simplemobiletools.calendar.pro" minSdkVersion 21 targetSdkVersion 28 - versionCode 145 - versionName "6.3.2" + versionCode 146 + versionName "6.4.0" multiDexEnabled true setProperty("archivesBaseName", "calendar") } From 4675fad9b242c5ea6c07cfb2d972b6f927dab857 Mon Sep 17 00:00:00 2001 From: tibbi Date: Wed, 20 Mar 2019 21:35:46 +0100 Subject: [PATCH 35/39] updating changelog --- CHANGELOG.md | 8 ++++++++ 1 file changed, 8 insertions(+) diff --git a/CHANGELOG.md b/CHANGELOG.md index f584eb633..67e2f88ed 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,6 +1,14 @@ Changelog ========== +Version 6.4.0 *(2019-03-20)* +---------------------------- + + * Added email reminders and attendees in CalDAV synced events + * Improved CalDAV event syncing in the background + * Fixed some sorting related glitches + * Some other stability and UX improvements + Version 6.3.2 *(2019-03-07)* ---------------------------- From 5f5aeef1423f5194dd28cf2f90381ea92f41b968 Mon Sep 17 00:00:00 2001 From: fricyo <30796677+fricyo@users.noreply.github.com> Date: Thu, 21 Mar 2019 18:35:43 +0800 Subject: [PATCH 36/39] Update Translation --- app/src/main/res/values-zh-rTW/strings.xml | 14 +++++++------- 1 file changed, 7 insertions(+), 7 deletions(-) diff --git a/app/src/main/res/values-zh-rTW/strings.xml b/app/src/main/res/values-zh-rTW/strings.xml index 7418edf57..232e8a145 100644 --- a/app/src/main/res/values-zh-rTW/strings.xml +++ b/app/src/main/res/values-zh-rTW/strings.xml @@ -10,7 +10,7 @@ 簡易活動列表 你近期似乎沒有任何活動。 前往今天 - Go to date + 前往日期 月曆 @@ -99,12 +99,12 @@ 活動提醒 - Add another attendee - My status: - Going - Not going - Maybe going - Invited + 新增另一場出席 + 我的狀態: + 前去 + 不前去 + 或許前去 + 被邀請 匯入活動 From b9e1c14c1c94a0ee40c6ad0ada247b4d24d8e404 Mon Sep 17 00:00:00 2001 From: tibbi Date: Thu, 21 Mar 2019 19:25:38 +0100 Subject: [PATCH 37/39] updating the app google play descriptions --- app/src/main/res/values-ar/strings.xml | 42 +++++++++++++++++---- app/src/main/res/values-az/strings.xml | 42 +++++++++++++++++---- app/src/main/res/values-br/strings.xml | 42 +++++++++++++++++---- app/src/main/res/values-cs/strings.xml | 42 +++++++++++++++++---- app/src/main/res/values-da/strings.xml | 42 +++++++++++++++++---- app/src/main/res/values-de/strings.xml | 44 ++++++++++++++++++---- app/src/main/res/values-el/strings.xml | 42 +++++++++++++++++---- app/src/main/res/values-es/strings.xml | 42 +++++++++++++++++---- app/src/main/res/values-fr/strings.xml | 42 +++++++++++++++++---- app/src/main/res/values-gl/strings.xml | 42 +++++++++++++++++---- app/src/main/res/values-hi-rIN/strings.xml | 42 +++++++++++++++++---- app/src/main/res/values-hr/strings.xml | 42 +++++++++++++++++---- app/src/main/res/values-hu/strings.xml | 42 +++++++++++++++++---- app/src/main/res/values-it/strings.xml | 44 ++++++++++++++++++---- app/src/main/res/values-iw/strings.xml | 44 +++++++++++++++++++++- app/src/main/res/values-ja/strings.xml | 42 +++++++++++++++++---- app/src/main/res/values-ko/strings.xml | 42 +++++++++++++++++---- app/src/main/res/values-lt/strings.xml | 42 +++++++++++++++++---- app/src/main/res/values-nb/strings.xml | 42 +++++++++++++++++---- app/src/main/res/values-nl/strings.xml | 42 +++++++++++++++++---- app/src/main/res/values-no/strings.xml | 42 +++++++++++++++++---- app/src/main/res/values-pl/strings.xml | 42 +++++++++++++++++---- app/src/main/res/values-pt-rBR/strings.xml | 42 +++++++++++++++++---- app/src/main/res/values-pt/strings.xml | 44 ++++++++++++++++++---- app/src/main/res/values-ru/strings.xml | 42 +++++++++++++++++---- app/src/main/res/values-sk/strings.xml | 42 +++++++++++++++++---- app/src/main/res/values-sv/strings.xml | 42 +++++++++++++++++---- app/src/main/res/values-tr/strings.xml | 42 +++++++++++++++++---- app/src/main/res/values-zh-rTW/strings.xml | 42 +++++++++++++++++---- app/src/main/res/values/strings.xml | 42 +++++++++++++++++---- 30 files changed, 1060 insertions(+), 208 deletions(-) diff --git a/app/src/main/res/values-ar/strings.xml b/app/src/main/res/values-ar/strings.xml index 546509269..c029f472e 100644 --- a/app/src/main/res/values-ar/strings.xml +++ b/app/src/main/res/values-ar/strings.xml @@ -233,19 +233,47 @@ - An offline calendar for your events without ads, respecting your privacy. + Offline calendar with no ads. Organizer & reminders for appointments, events etc - A simple calendar with optional CalDAV synchronization. You can easily create recurring events and setup reminders, it can also display week numbers. + Simple Calendar Pro is a fully customizable, offline calendar designed to do exactly what a calendar should do. No complicated features, unnecessary permissions and no ads! - Contains a monthly view and an event list widget where you can customize the color of the text, as well as the alpha and the color of the background. + Whether you’re organizing single or recurring events, birthdays, anniversaries, business meetings, appointments or anything else, Simple Calendar Pro makes it easy to stay organized. With an incredible variety of customization options you can customize event reminders, notification sounds, calendar widgets and how the app looks. - Contains no ads or unnecessary permissions. It is fully opensource, provides customizable colors. + Daily, weekly and monthly views make checking your upcoming events & appointments a breeze. You can even view everything as a simple list of events rather than in calendar view, so you know exactly what’s coming up in your life and when. - The Storage permission is needed only for exporting or importing events from .ics files. + ---------------------------------------------------------- + Simple Calendar Pro – Features & Benefits + ---------------------------------------------------------- - The Contacts permission is used only at importing contact birthdays and anniversaries. + ✔️ No ads or annoying popups + ✔️ No internet access needed, giving you more privacy & security + ✔️ Only the bare minimum permissions required + ✔️ Emphasis on simplicity – does what a calendar needs to do! + ✔️ Open source + ✔️ Fully customizable themes & calendar / event widgets + ✔️ Translated into 29 languages + ✔️ Export settings to .txt files to import to another device + ✔️ CalDAV calendar sync supported to sync events across devices + ✔️ Daily, weekly, monthly, yearly & event views on the calendar + ✔️ Supports exporting & importing events via .ics files + ✔️ Set multiple event reminders, customize event reminder sound and vibration + ✔️ Snooze option for reminders + ✔️ Easily add holidays, birthdays, anniversaries & appointments + ✔️ Customize events – start time, duration, reminders etc + ✔️ Add event attendees to each event + ✔️ Use as a personal calendar or a business calendar + ✔️ Choose between reminders & email notifications to alert you about an event - This app is just one piece of a bigger series of apps. You can find the rest of them at https://www.simplemobiletools.com + DOWNLOAD SIMPLE CALENDAR PRO – THE SIMPLE OFFLINE CALENDAR WITH NO ADS! + + Check out the full suite of Simple Tools here: + https://www.simplemobiletools.com + + Facebook: + https://www.facebook.com/simplemobiletools + + Reddit: + https://www.reddit.com/r/SimpleMobileTools - An offline calendar for your events without ads, respecting your privacy. + Offline calendar with no ads. Organizer & reminders for appointments, events etc - CalDAV sinxronizasiyalı sadə bir kalendar. Siz asanca təkrarlanan hadisələrinizi və xatırladıcılarınızı yarada bilərsiniz, hətta həftə nömrələrini də göstərə bilir. + Simple Calendar Pro is a fully customizable, offline calendar designed to do exactly what a calendar should do. No complicated features, unnecessary permissions and no ads! - Aylıq görünüş və hadisə siyahısı widgeti ehtiva edir hansı ki, siz oradan yazı rəngini, həmçinin, alfanı və arxa plan rəngini dəyişdirə bilərsiniz. + Whether you’re organizing single or recurring events, birthdays, anniversaries, business meetings, appointments or anything else, Simple Calendar Pro makes it easy to stay organized. With an incredible variety of customization options you can customize event reminders, notification sounds, calendar widgets and how the app looks. - Lazımsız reklam və ya icazə mövcud deyil. Tamamilə açıqlisanslıdır, rəng dəyişmə parametrləri var. + Daily, weekly and monthly views make checking your upcoming events & appointments a breeze. You can even view everything as a simple list of events rather than in calendar view, so you know exactly what’s coming up in your life and when. - Yaddaş icazəsi yalnız .ics faylından hadisələri çıxarmaq və ya daxil etmək üçün istifadə olunur. + ---------------------------------------------------------- + Simple Calendar Pro – Features & Benefits + ---------------------------------------------------------- - Kontakt icazəsi yalnız kontakt ad günlərini və il dönümlərini daxil etmək üçün istifadə olunur. + ✔️ No ads or annoying popups + ✔️ No internet access needed, giving you more privacy & security + ✔️ Only the bare minimum permissions required + ✔️ Emphasis on simplicity – does what a calendar needs to do! + ✔️ Open source + ✔️ Fully customizable themes & calendar / event widgets + ✔️ Translated into 29 languages + ✔️ Export settings to .txt files to import to another device + ✔️ CalDAV calendar sync supported to sync events across devices + ✔️ Daily, weekly, monthly, yearly & event views on the calendar + ✔️ Supports exporting & importing events via .ics files + ✔️ Set multiple event reminders, customize event reminder sound and vibration + ✔️ Snooze option for reminders + ✔️ Easily add holidays, birthdays, anniversaries & appointments + ✔️ Customize events – start time, duration, reminders etc + ✔️ Add event attendees to each event + ✔️ Use as a personal calendar or a business calendar + ✔️ Choose between reminders & email notifications to alert you about an event - Bu, böyük bir tətbiq seriyasının yalnız bir hissəsidir. Digər tətbiqləri buradan əldə edə bilərsiniz https://www.simplemobiletools.com + DOWNLOAD SIMPLE CALENDAR PRO – THE SIMPLE OFFLINE CALENDAR WITH NO ADS! + + Check out the full suite of Simple Tools here: + https://www.simplemobiletools.com + + Facebook: + https://www.facebook.com/simplemobiletools + + Reddit: + https://www.reddit.com/r/SimpleMobileTools - An offline calendar for your events without ads, respecting your privacy. + Offline calendar with no ads. Organizer & reminders for appointments, events etc - Un deiziataer eeun gant ur goubredañ diret da zeiziataer CalDAV. Aes eo krouiñ darvoudoù a addegouezh ha lakaat adc\'halvoù. Gallout a ra ivez diskouez niverenn ar sizhunvezhioù. + Simple Calendar Pro is a fully customizable, offline calendar designed to do exactly what a calendar should do. No complicated features, unnecessary permissions and no ads! - Dont a ra gant ur widjet 4x4 a c\'haller adventañ ha personelaat liv an destenn, an alfa ha liv an drekleur. + Whether you’re organizing single or recurring events, birthdays, anniversaries, business meetings, appointments or anything else, Simple Calendar Pro makes it easy to stay organized. With an incredible variety of customization options you can customize event reminders, notification sounds, calendar widgets and how the app looks. - N\'eus tamm bruderezh ebet ha n\'eo goulennet aotre arbennik ebet. Digor eo e darzh ha gallout a rit personelaat al livioù. + Daily, weekly and monthly views make checking your upcoming events & appointments a breeze. You can even view everything as a simple list of events rather than in calendar view, so you know exactly what’s coming up in your life and when. - Ret eo reiñ an aotre kadaviñ evit ezporzhiañ hag enporzhiañ darvoudoù gant restroù .ics. + ---------------------------------------------------------- + Simple Calendar Pro – Features & Benefits + ---------------------------------------------------------- - Ret eo reiñ an aotre Darempredoù evit enporzhiañ deizioù-ha-bloaz an darempredoù. + ✔️ No ads or annoying popups + ✔️ No internet access needed, giving you more privacy & security + ✔️ Only the bare minimum permissions required + ✔️ Emphasis on simplicity – does what a calendar needs to do! + ✔️ Open source + ✔️ Fully customizable themes & calendar / event widgets + ✔️ Translated into 29 languages + ✔️ Export settings to .txt files to import to another device + ✔️ CalDAV calendar sync supported to sync events across devices + ✔️ Daily, weekly, monthly, yearly & event views on the calendar + ✔️ Supports exporting & importing events via .ics files + ✔️ Set multiple event reminders, customize event reminder sound and vibration + ✔️ Snooze option for reminders + ✔️ Easily add holidays, birthdays, anniversaries & appointments + ✔️ Customize events – start time, duration, reminders etc + ✔️ Add event attendees to each event + ✔️ Use as a personal calendar or a business calendar + ✔️ Choose between reminders & email notifications to alert you about an event - An arload-mañ a zo ul lodenn eus un heuliad arloadoù brasoc\'h. Gallout a rit o kavout anezho war https://www.simplemobiletools.com + DOWNLOAD SIMPLE CALENDAR PRO – THE SIMPLE OFFLINE CALENDAR WITH NO ADS! + + Check out the full suite of Simple Tools here: + https://www.simplemobiletools.com + + Facebook: + https://www.facebook.com/simplemobiletools + + Reddit: + https://www.reddit.com/r/SimpleMobileTools - An offline calendar for your events without ads, respecting your privacy. + Offline calendar with no ads. Organizer & reminders for appointments, events etc - Jednoduchý kalendář s volitelnou synchronizací CalDAV. Můžete snadno vytvářet opakující se události a nastavovat připomenutí, můžete také zobrazovat čísla týdnů. + Simple Calendar Pro is a fully customizable, offline calendar designed to do exactly what a calendar should do. No complicated features, unnecessary permissions and no ads! - Obsahuje přizpůsobitelný widget 4x4, kde můžete měnit barvu textu, stejně jako průhlednost a barvu pozadí. + Whether you’re organizing single or recurring events, birthdays, anniversaries, business meetings, appointments or anything else, Simple Calendar Pro makes it easy to stay organized. With an incredible variety of customization options you can customize event reminders, notification sounds, calendar widgets and how the app looks. - Neobsahuje žádné reklamy ani zbytečná oprávnění. Je plně OpenSource, umožňuje měnit barvy. + Daily, weekly and monthly views make checking your upcoming events & appointments a breeze. You can even view everything as a simple list of events rather than in calendar view, so you know exactly what’s coming up in your life and when. - Povolení úložiště je potřeba pouze pro export nebo import událostí ze souborů .ics. + ---------------------------------------------------------- + Simple Calendar Pro – Features & Benefits + ---------------------------------------------------------- - Povolení kontaktů se používá pouze při importu narozenin a výročí. + ✔️ No ads or annoying popups + ✔️ No internet access needed, giving you more privacy & security + ✔️ Only the bare minimum permissions required + ✔️ Emphasis on simplicity – does what a calendar needs to do! + ✔️ Open source + ✔️ Fully customizable themes & calendar / event widgets + ✔️ Translated into 29 languages + ✔️ Export settings to .txt files to import to another device + ✔️ CalDAV calendar sync supported to sync events across devices + ✔️ Daily, weekly, monthly, yearly & event views on the calendar + ✔️ Supports exporting & importing events via .ics files + ✔️ Set multiple event reminders, customize event reminder sound and vibration + ✔️ Snooze option for reminders + ✔️ Easily add holidays, birthdays, anniversaries & appointments + ✔️ Customize events – start time, duration, reminders etc + ✔️ Add event attendees to each event + ✔️ Use as a personal calendar or a business calendar + ✔️ Choose between reminders & email notifications to alert you about an event - Tato aplikace je součástí větší sady aplikací. Tyto a další aplikace najdete na https://www.simplemobiletools.com + DOWNLOAD SIMPLE CALENDAR PRO – THE SIMPLE OFFLINE CALENDAR WITH NO ADS! + + Check out the full suite of Simple Tools here: + https://www.simplemobiletools.com + + Facebook: + https://www.facebook.com/simplemobiletools + + Reddit: + https://www.reddit.com/r/SimpleMobileTools - An offline calendar for your events without ads, respecting your privacy. + Offline calendar with no ads. Organizer & reminders for appointments, events etc - En simpel kalender med mulighed for at synkronisere med CalDAV. Nem opsætning af gentagne begivenheder og af påmindelser. + Simple Calendar Pro is a fully customizable, offline calendar designed to do exactly what a calendar should do. No complicated features, unnecessary permissions and no ads! - Indeholder en skalerbar 4x4 widget med mulighed for at tilpasse tekstfarve samt alfa og farve på baggrunden. + Whether you’re organizing single or recurring events, birthdays, anniversaries, business meetings, appointments or anything else, Simple Calendar Pro makes it easy to stay organized. With an incredible variety of customization options you can customize event reminders, notification sounds, calendar widgets and how the app looks. - Uden reklamer og unødvendige tilladelser. Den er helt igennem open source, og du kan selv bestemme farverne. + Daily, weekly and monthly views make checking your upcoming events & appointments a breeze. You can even view everything as a simple list of events rather than in calendar view, so you know exactly what’s coming up in your life and when. - Adgang til at gemme er kun nødvendig i forbindelse med eksport til og import fra ics-filer. + ---------------------------------------------------------- + Simple Calendar Pro – Features & Benefits + ---------------------------------------------------------- - Adgang til kontaktpersoner er nødvendig hvis du vil importere fødselsdage. + ✔️ No ads or annoying popups + ✔️ No internet access needed, giving you more privacy & security + ✔️ Only the bare minimum permissions required + ✔️ Emphasis on simplicity – does what a calendar needs to do! + ✔️ Open source + ✔️ Fully customizable themes & calendar / event widgets + ✔️ Translated into 29 languages + ✔️ Export settings to .txt files to import to another device + ✔️ CalDAV calendar sync supported to sync events across devices + ✔️ Daily, weekly, monthly, yearly & event views on the calendar + ✔️ Supports exporting & importing events via .ics files + ✔️ Set multiple event reminders, customize event reminder sound and vibration + ✔️ Snooze option for reminders + ✔️ Easily add holidays, birthdays, anniversaries & appointments + ✔️ Customize events – start time, duration, reminders etc + ✔️ Add event attendees to each event + ✔️ Use as a personal calendar or a business calendar + ✔️ Choose between reminders & email notifications to alert you about an event - Denne app er en enkelt del af en større serie apps. Du kan finde dem alle på siden https://www.simplemobiletools.com + DOWNLOAD SIMPLE CALENDAR PRO – THE SIMPLE OFFLINE CALENDAR WITH NO ADS! + + Check out the full suite of Simple Tools here: + https://www.simplemobiletools.com + + Facebook: + https://www.facebook.com/simplemobiletools + + Reddit: + https://www.reddit.com/r/SimpleMobileTools - An offline calendar for your events without ads, respecting your privacy. + Offline calendar with no ads. Organizer & reminders for appointments, events etc - Ein schlichter Kalender mit optionaler CalDAV-Synchronisation. Du kannst ganz einfach wiederholende Termine sowie Erinnerungen erstellen, inklusive optionaler Anzeige der Kalenderwoche. + Simple Calendar Pro is a fully customizable, offline calendar designed to do exactly what a calendar should do. No complicated features, unnecessary permissions and no ads! - Enthält ein skalierbares 4x4 Bedienelement, bei welchem die Schriftfarbe sowie die Hintergrundfarbe und Transparenz anpassbar sind. - - Beinhaltet keine Werbung oder unnötige Berechtigungen. Sie ist komplett Open Source, alle verwendeten Farben sind anpassbar. + Whether you’re organizing single or recurring events, birthdays, anniversaries, business meetings, appointments or anything else, Simple Calendar Pro makes it easy to stay organized. With an incredible variety of customization options you can customize event reminders, notification sounds, calendar widgets and how the app looks. - Die Speicher-Berechtigung ist nur für das Importieren von .ics Termin-Dateien notwendig. + Daily, weekly and monthly views make checking your upcoming events & appointments a breeze. You can even view everything as a simple list of events rather than in calendar view, so you know exactly what’s coming up in your life and when. - Die Kontakte-Berechtigung wird nur für das Importieren von Geburtstagen benötigt. + ---------------------------------------------------------- + Simple Calendar Pro – Features & Benefits + ---------------------------------------------------------- - Diese App ist nur eine aus einer größeren Serie von schlichten Apps. Der Rest davon findet sich auf https://www.simplemobiletools.com + ✔️ No ads or annoying popups + ✔️ No internet access needed, giving you more privacy & security + ✔️ Only the bare minimum permissions required + ✔️ Emphasis on simplicity – does what a calendar needs to do! + ✔️ Open source + ✔️ Fully customizable themes & calendar / event widgets + ✔️ Translated into 29 languages + ✔️ Export settings to .txt files to import to another device + ✔️ CalDAV calendar sync supported to sync events across devices + ✔️ Daily, weekly, monthly, yearly & event views on the calendar + ✔️ Supports exporting & importing events via .ics files + ✔️ Set multiple event reminders, customize event reminder sound and vibration + ✔️ Snooze option for reminders + ✔️ Easily add holidays, birthdays, anniversaries & appointments + ✔️ Customize events – start time, duration, reminders etc + ✔️ Add event attendees to each event + ✔️ Use as a personal calendar or a business calendar + ✔️ Choose between reminders & email notifications to alert you about an event + + DOWNLOAD SIMPLE CALENDAR PRO – THE SIMPLE OFFLINE CALENDAR WITH NO ADS! + + Check out the full suite of Simple Tools here: + https://www.simplemobiletools.com + + Facebook: + https://www.facebook.com/simplemobiletools + + Reddit: + https://www.reddit.com/r/SimpleMobileTools - Ένα offline calendar χωρίς διαφημίσεις, σεβόμενοι τα προσωπικά σας δεδομένα. + Offline calendar with no ads. Organizer & reminders for appointments, events etc - Ένα απλό ημερολόγιο με προαιρετικό συγχρονισμό CalDAV. Μπορείτε εύκολα να δημιουργήσετε επαναλαμβανόμενες εκδηλώσεις με ρυθμίσεις υπενθυμίσεων, μπορεί επίσης να εμφανίσει αριθμούς εβδομάδων. + Simple Calendar Pro is a fully customizable, offline calendar designed to do exactly what a calendar should do. No complicated features, unnecessary permissions and no ads! - Περιέχει μια μηνιαία προβολή και ένα widget λίστας εκδηλώσεων, όπου μπορείτε να προσαρμόσετε το χρώμα του κειμένου, καθώς το alpha και το χρώμα του φόντου. + Whether you’re organizing single or recurring events, birthdays, anniversaries, business meetings, appointments or anything else, Simple Calendar Pro makes it easy to stay organized. With an incredible variety of customization options you can customize event reminders, notification sounds, calendar widgets and how the app looks. - Δεν περιέχει διαφημίσεις ή περιττά δικαιώματα. Έιναι όλη ανοιχτού κώδικα και παρέχει προσαρμόσιμα χρώματα για την εφαρμογή. + Daily, weekly and monthly views make checking your upcoming events & appointments a breeze. You can even view everything as a simple list of events rather than in calendar view, so you know exactly what’s coming up in your life and when. - Η άδεια αποθήκευσης απαιτείται μόνο για την εξαγωγή ή την εισαγωγή εκδηλώσεων από αρχεία .ics. + ---------------------------------------------------------- + Simple Calendar Pro – Features & Benefits + ---------------------------------------------------------- - Η άδεια Επαφών χρησιμοποιείται μόνο κατά την εισαγωγή γενεθλίων επαφών και επετείων. + ✔️ No ads or annoying popups + ✔️ No internet access needed, giving you more privacy & security + ✔️ Only the bare minimum permissions required + ✔️ Emphasis on simplicity – does what a calendar needs to do! + ✔️ Open source + ✔️ Fully customizable themes & calendar / event widgets + ✔️ Translated into 29 languages + ✔️ Export settings to .txt files to import to another device + ✔️ CalDAV calendar sync supported to sync events across devices + ✔️ Daily, weekly, monthly, yearly & event views on the calendar + ✔️ Supports exporting & importing events via .ics files + ✔️ Set multiple event reminders, customize event reminder sound and vibration + ✔️ Snooze option for reminders + ✔️ Easily add holidays, birthdays, anniversaries & appointments + ✔️ Customize events – start time, duration, reminders etc + ✔️ Add event attendees to each event + ✔️ Use as a personal calendar or a business calendar + ✔️ Choose between reminders & email notifications to alert you about an event - Αυτή η εφαρμογή είναι μέρος μιας σειράς εφαρμογών. Μπορείτε να βρείτε τις υπόλοιπες στο https://www.simplemobiletools.com + DOWNLOAD SIMPLE CALENDAR PRO – THE SIMPLE OFFLINE CALENDAR WITH NO ADS! + + Check out the full suite of Simple Tools here: + https://www.simplemobiletools.com + + Facebook: + https://www.facebook.com/simplemobiletools + + Reddit: + https://www.reddit.com/r/SimpleMobileTools - An offline calendar for your events without ads, respecting your privacy. + Offline calendar with no ads. Organizer & reminders for appointments, events etc - Un simple calendario con sincronización opcional con CalDAV. Puedes crear fácilmente eventos que se repitan y configurar recordatorios, o que te muestre los días de la semana. + Simple Calendar Pro is a fully customizable, offline calendar designed to do exactly what a calendar should do. No complicated features, unnecessary permissions and no ads! - Contiene un widget 4x4 redimensionable donde puedes personalizar el color del texto, así como la transparencia y el color del fondo. + Whether you’re organizing single or recurring events, birthdays, anniversaries, business meetings, appointments or anything else, Simple Calendar Pro makes it easy to stay organized. With an incredible variety of customization options you can customize event reminders, notification sounds, calendar widgets and how the app looks. - No contiene anuncios ni permisos innecesarios. Es completamente de código abierto, permite personalizar los colores. + Daily, weekly and monthly views make checking your upcoming events & appointments a breeze. You can even view everything as a simple list of events rather than in calendar view, so you know exactly what’s coming up in your life and when. - El permiso de almacenamiento sólo se necesita para exportar o importar eventos desde archivos .ics. + ---------------------------------------------------------- + Simple Calendar Pro – Features & Benefits + ---------------------------------------------------------- - El permiso de contactos se usa sólo para importar los cumpleaños de los contactos. + ✔️ No ads or annoying popups + ✔️ No internet access needed, giving you more privacy & security + ✔️ Only the bare minimum permissions required + ✔️ Emphasis on simplicity – does what a calendar needs to do! + ✔️ Open source + ✔️ Fully customizable themes & calendar / event widgets + ✔️ Translated into 29 languages + ✔️ Export settings to .txt files to import to another device + ✔️ CalDAV calendar sync supported to sync events across devices + ✔️ Daily, weekly, monthly, yearly & event views on the calendar + ✔️ Supports exporting & importing events via .ics files + ✔️ Set multiple event reminders, customize event reminder sound and vibration + ✔️ Snooze option for reminders + ✔️ Easily add holidays, birthdays, anniversaries & appointments + ✔️ Customize events – start time, duration, reminders etc + ✔️ Add event attendees to each event + ✔️ Use as a personal calendar or a business calendar + ✔️ Choose between reminders & email notifications to alert you about an event - Esta aplicación es sólo una parte de una mayor serie de aplicaciones. Puede encontrar el resto en https://www.simplemobiletools.com + DOWNLOAD SIMPLE CALENDAR PRO – THE SIMPLE OFFLINE CALENDAR WITH NO ADS! + + Check out the full suite of Simple Tools here: + https://www.simplemobiletools.com + + Facebook: + https://www.facebook.com/simplemobiletools + + Reddit: + https://www.reddit.com/r/SimpleMobileTools - An offline calendar for your events without ads, respecting your privacy. + Offline calendar with no ads. Organizer & reminders for appointments, events etc - Un calendrier hors ligne sans aucune autre intégration de calendrier. Vous pouvez aisément créer des événements récurrents et configurer des rappels, il est aussi possible d\'afficher les numéros de semaine. + Simple Calendar Pro is a fully customizable, offline calendar designed to do exactly what a calendar should do. No complicated features, unnecessary permissions and no ads! - Contient un widget 4x4 redimensionnable où vous pouvez personnaliser la couleur du texte, ainsi que l\'alpha et la couleur de l\'arrière plan. + Whether you’re organizing single or recurring events, birthdays, anniversaries, business meetings, appointments or anything else, Simple Calendar Pro makes it easy to stay organized. With an incredible variety of customization options you can customize event reminders, notification sounds, calendar widgets and how the app looks. - Ne contient pas de publicités ou de permissions inutiles. Complètement opensource, fournit une personnalisation des couleurs. + Daily, weekly and monthly views make checking your upcoming events & appointments a breeze. You can even view everything as a simple list of events rather than in calendar view, so you know exactly what’s coming up in your life and when. - La permission d\'accès au stockage est necéssaire uniquement pour importer des événements depuis des fichiers .ics. + ---------------------------------------------------------- + Simple Calendar Pro – Features & Benefits + ---------------------------------------------------------- - La permission Contacts ne sert qu\'à importer l\'anniversaire de vos contacts. + ✔️ No ads or annoying popups + ✔️ No internet access needed, giving you more privacy & security + ✔️ Only the bare minimum permissions required + ✔️ Emphasis on simplicity – does what a calendar needs to do! + ✔️ Open source + ✔️ Fully customizable themes & calendar / event widgets + ✔️ Translated into 29 languages + ✔️ Export settings to .txt files to import to another device + ✔️ CalDAV calendar sync supported to sync events across devices + ✔️ Daily, weekly, monthly, yearly & event views on the calendar + ✔️ Supports exporting & importing events via .ics files + ✔️ Set multiple event reminders, customize event reminder sound and vibration + ✔️ Snooze option for reminders + ✔️ Easily add holidays, birthdays, anniversaries & appointments + ✔️ Customize events – start time, duration, reminders etc + ✔️ Add event attendees to each event + ✔️ Use as a personal calendar or a business calendar + ✔️ Choose between reminders & email notifications to alert you about an event - Cette application est juste une pièce d\'une plus grosse série d\'applications. Vous pouvez trouver le reste de celles-ci à https://www.simplemobiletools.com + DOWNLOAD SIMPLE CALENDAR PRO – THE SIMPLE OFFLINE CALENDAR WITH NO ADS! + + Check out the full suite of Simple Tools here: + https://www.simplemobiletools.com + + Facebook: + https://www.facebook.com/simplemobiletools + + Reddit: + https://www.reddit.com/r/SimpleMobileTools - An offline calendar for your events without ads, respecting your privacy. + Offline calendar with no ads. Organizer & reminders for appointments, events etc - Un calendario que funciona sin precisar sincronización CalDAV. Pode crear fácilmente eventos recurrentes e configurar recordatorios. También mostra o número de semana. + Simple Calendar Pro is a fully customizable, offline calendar designed to do exactly what a calendar should do. No complicated features, unnecessary permissions and no ads! - Ten un widget 4x4 de tamaño variable no que pode personalizar a cor do texto, así como a transparencia e cor de fondo. + Whether you’re organizing single or recurring events, birthdays, anniversaries, business meetings, appointments or anything else, Simple Calendar Pro makes it easy to stay organized. With an incredible variety of customization options you can customize event reminders, notification sounds, calendar widgets and how the app looks. - Non contén anuncios ni permisos innecesarios. É totalmente de código abierto e tamén proporciona un decorado oscuro. + Daily, weekly and monthly views make checking your upcoming events & appointments a breeze. You can even view everything as a simple list of events rather than in calendar view, so you know exactly what’s coming up in your life and when. - O permiso ao Almacenamento só é preciso para importar ficheiros .ics. + ---------------------------------------------------------- + Simple Calendar Pro – Features & Benefits + ---------------------------------------------------------- - O permiso aos Contactos só é preciso se quere importar os cumpleanos dos contactos. + ✔️ No ads or annoying popups + ✔️ No internet access needed, giving you more privacy & security + ✔️ Only the bare minimum permissions required + ✔️ Emphasis on simplicity – does what a calendar needs to do! + ✔️ Open source + ✔️ Fully customizable themes & calendar / event widgets + ✔️ Translated into 29 languages + ✔️ Export settings to .txt files to import to another device + ✔️ CalDAV calendar sync supported to sync events across devices + ✔️ Daily, weekly, monthly, yearly & event views on the calendar + ✔️ Supports exporting & importing events via .ics files + ✔️ Set multiple event reminders, customize event reminder sound and vibration + ✔️ Snooze option for reminders + ✔️ Easily add holidays, birthdays, anniversaries & appointments + ✔️ Customize events – start time, duration, reminders etc + ✔️ Add event attendees to each event + ✔️ Use as a personal calendar or a business calendar + ✔️ Choose between reminders & email notifications to alert you about an event - Esta aplicación é parte de unha serie máis grande de aplicativos. Puede atopar o resto en https://www.simplemobiletools.com + DOWNLOAD SIMPLE CALENDAR PRO – THE SIMPLE OFFLINE CALENDAR WITH NO ADS! + + Check out the full suite of Simple Tools here: + https://www.simplemobiletools.com + + Facebook: + https://www.facebook.com/simplemobiletools + + Reddit: + https://www.reddit.com/r/SimpleMobileTools - An offline calendar for your events without ads, respecting your privacy. + Offline calendar with no ads. Organizer & reminders for appointments, events etc - एक ऑफलाइन कैलेंडर बिना अन्य कैलेंडर इंटीग्रेशन के। आप आसानी से इवेंट्स व रिमाइंडर बना सकते हैं, यह सफ्ताह क्रमांक भी दर्शाता हैं। + Simple Calendar Pro is a fully customizable, offline calendar designed to do exactly what a calendar should do. No complicated features, unnecessary permissions and no ads! - इसमें आकार बदल सकने वाला 4x4 विजेट हैं जहा आप टेक्स्ट का रंग अनुकूलित कर सकते हैं, और अल्फा व बैकग्राउंड का रंग भी बदल सकते हैं। + Whether you’re organizing single or recurring events, birthdays, anniversaries, business meetings, appointments or anything else, Simple Calendar Pro makes it easy to stay organized. With an incredible variety of customization options you can customize event reminders, notification sounds, calendar widgets and how the app looks. - कोई भी विज्ञापन व अनावश्यक अनुमतियों की आवश्यकता नहीं। यह पूर्ण रूप से ओपन सोर्स हैं, और काली थीम हैं। + Daily, weekly and monthly views make checking your upcoming events & appointments a breeze. You can even view everything as a simple list of events rather than in calendar view, so you know exactly what’s coming up in your life and when. - The Storage permission is needed only for exporting or importing events from .ics files. + ---------------------------------------------------------- + Simple Calendar Pro – Features & Benefits + ---------------------------------------------------------- - The Contacts permission is used only at importing contact birthdays and anniversaries. + ✔️ No ads or annoying popups + ✔️ No internet access needed, giving you more privacy & security + ✔️ Only the bare minimum permissions required + ✔️ Emphasis on simplicity – does what a calendar needs to do! + ✔️ Open source + ✔️ Fully customizable themes & calendar / event widgets + ✔️ Translated into 29 languages + ✔️ Export settings to .txt files to import to another device + ✔️ CalDAV calendar sync supported to sync events across devices + ✔️ Daily, weekly, monthly, yearly & event views on the calendar + ✔️ Supports exporting & importing events via .ics files + ✔️ Set multiple event reminders, customize event reminder sound and vibration + ✔️ Snooze option for reminders + ✔️ Easily add holidays, birthdays, anniversaries & appointments + ✔️ Customize events – start time, duration, reminders etc + ✔️ Add event attendees to each event + ✔️ Use as a personal calendar or a business calendar + ✔️ Choose between reminders & email notifications to alert you about an event - This app is just one piece of a bigger series of apps. You can find the rest of them at https://www.simplemobiletools.com + DOWNLOAD SIMPLE CALENDAR PRO – THE SIMPLE OFFLINE CALENDAR WITH NO ADS! + + Check out the full suite of Simple Tools here: + https://www.simplemobiletools.com + + Facebook: + https://www.facebook.com/simplemobiletools + + Reddit: + https://www.reddit.com/r/SimpleMobileTools - Izvanmrežni kalendar za događaje, bez oglasa, poštujući Vašu privatnost. + Offline calendar with no ads. Organizer & reminders for appointments, events etc - Jednostavan kalendar s dodatnom CalDAV sinkronizacijom. Možete jednostavno stvoriti ponavljajuće događaje i postaviti podsjetnike, također je moguće prikazati tjedne brojeve. + Simple Calendar Pro is a fully customizable, offline calendar designed to do exactly what a calendar should do. No complicated features, unnecessary permissions and no ads! - Sadrži mjesečni prikaz i widget s popisom događaja gdje možete prilagoditi boju teksta, kao i transparentnost te boju pozadine. + Whether you’re organizing single or recurring events, birthdays, anniversaries, business meetings, appointments or anything else, Simple Calendar Pro makes it easy to stay organized. With an incredible variety of customization options you can customize event reminders, notification sounds, calendar widgets and how the app looks. - Ne sadrži oglase ili nepotrebne dozvole. Aplikacije je otvorenog koda, pruža prilagodljive boje. + Daily, weekly and monthly views make checking your upcoming events & appointments a breeze. You can even view everything as a simple list of events rather than in calendar view, so you know exactly what’s coming up in your life and when. - Dopuštenje za pohranu podataka potrebna je samo za izvoz ili uvoz događaja iz .ics datoteka. + ---------------------------------------------------------- + Simple Calendar Pro – Features & Benefits + ---------------------------------------------------------- - Dopuštenje za kontakte upotrebljava se samo pri uvozu rođendana i obljetnica kontakata. + ✔️ No ads or annoying popups + ✔️ No internet access needed, giving you more privacy & security + ✔️ Only the bare minimum permissions required + ✔️ Emphasis on simplicity – does what a calendar needs to do! + ✔️ Open source + ✔️ Fully customizable themes & calendar / event widgets + ✔️ Translated into 29 languages + ✔️ Export settings to .txt files to import to another device + ✔️ CalDAV calendar sync supported to sync events across devices + ✔️ Daily, weekly, monthly, yearly & event views on the calendar + ✔️ Supports exporting & importing events via .ics files + ✔️ Set multiple event reminders, customize event reminder sound and vibration + ✔️ Snooze option for reminders + ✔️ Easily add holidays, birthdays, anniversaries & appointments + ✔️ Customize events – start time, duration, reminders etc + ✔️ Add event attendees to each event + ✔️ Use as a personal calendar or a business calendar + ✔️ Choose between reminders & email notifications to alert you about an event - Ova je aplikacija samo dio većeg broja aplikacija. Možete pronaći ostatak na https://www.simplemobiletools.com + DOWNLOAD SIMPLE CALENDAR PRO – THE SIMPLE OFFLINE CALENDAR WITH NO ADS! + + Check out the full suite of Simple Tools here: + https://www.simplemobiletools.com + + Facebook: + https://www.facebook.com/simplemobiletools + + Reddit: + https://www.reddit.com/r/SimpleMobileTools - An offline calendar for your events without ads, respecting your privacy. + Offline calendar with no ads. Organizer & reminders for appointments, events etc - Egy egyszerű naptár, CalDAV integráció lehetőségével. Könnyedén lehet ismétlődő eseményeket és emlékeztetőket felvenni, és a hetek sorszámait is mutatja. + Simple Calendar Pro is a fully customizable, offline calendar designed to do exactly what a calendar should do. No complicated features, unnecessary permissions and no ads! - Egy 4x4-es átméretezhető widget-et is biztosít, aminek beállíthatod a színét, az alfáját és a háttérszínét is. + Whether you’re organizing single or recurring events, birthdays, anniversaries, business meetings, appointments or anything else, Simple Calendar Pro makes it easy to stay organized. With an incredible variety of customization options you can customize event reminders, notification sounds, calendar widgets and how the app looks. - Nincsenek reklámok, és nem igényel szükségtelen engedélyeket. A forráskódja teljesen nyílt, és sötét téma is beállítható. + Daily, weekly and monthly views make checking your upcoming events & appointments a breeze. You can even view everything as a simple list of events rather than in calendar view, so you know exactly what’s coming up in your life and when. - The Storage permission is needed only for exporting or importing events from .ics files. + ---------------------------------------------------------- + Simple Calendar Pro – Features & Benefits + ---------------------------------------------------------- - The Contacts permission is used only at importing contact birthdays and anniversaries. + ✔️ No ads or annoying popups + ✔️ No internet access needed, giving you more privacy & security + ✔️ Only the bare minimum permissions required + ✔️ Emphasis on simplicity – does what a calendar needs to do! + ✔️ Open source + ✔️ Fully customizable themes & calendar / event widgets + ✔️ Translated into 29 languages + ✔️ Export settings to .txt files to import to another device + ✔️ CalDAV calendar sync supported to sync events across devices + ✔️ Daily, weekly, monthly, yearly & event views on the calendar + ✔️ Supports exporting & importing events via .ics files + ✔️ Set multiple event reminders, customize event reminder sound and vibration + ✔️ Snooze option for reminders + ✔️ Easily add holidays, birthdays, anniversaries & appointments + ✔️ Customize events – start time, duration, reminders etc + ✔️ Add event attendees to each event + ✔️ Use as a personal calendar or a business calendar + ✔️ Choose between reminders & email notifications to alert you about an event - Ez az alkalmazás egy nagyobb alkalmazás-sorozat része. A továbbiak itt találhatók: https://www.simplemobiletools.com + DOWNLOAD SIMPLE CALENDAR PRO – THE SIMPLE OFFLINE CALENDAR WITH NO ADS! + + Check out the full suite of Simple Tools here: + https://www.simplemobiletools.com + + Facebook: + https://www.facebook.com/simplemobiletools + + Reddit: + https://www.reddit.com/r/SimpleMobileTools - Un calendario per gestire gli eventi senza pubblicità. + Offline calendar with no ads. Organizer & reminders for appointments, events etc - Un semplice calendario con l\'opzione di sincronizzazione CalDAV. Si possono facilmente creare eventi ricorrenti e impostare promemoria, mostra anche il numero di settimana. + Simple Calendar Pro is a fully customizable, offline calendar designed to do exactly what a calendar should do. No complicated features, unnecessary permissions and no ads! - Contiene una vista mensile e un widget con la lista degli eventi, con il colore del testo personalizzabile, come per la trasparenza ed il colore dello sfondo. + Whether you’re organizing single or recurring events, birthdays, anniversaries, business meetings, appointments or anything else, Simple Calendar Pro makes it easy to stay organized. With an incredible variety of customization options you can customize event reminders, notification sounds, calendar widgets and how the app looks. - L\'applicazione non contiene pubblicità o permessi non necessari; è completamente opensource e la si può personalizzare con i propri colori preferiti. + Daily, weekly and monthly views make checking your upcoming events & appointments a breeze. You can even view everything as a simple list of events rather than in calendar view, so you know exactly what’s coming up in your life and when. - Il permesso di archiviazione è necesario solamente per esportare od importare venti da file .ic - - Il permesso dei contatti è usato solamente per importare i compleanni e gli anniversari. + ---------------------------------------------------------- + Simple Calendar Pro – Features & Benefits + ---------------------------------------------------------- - Questa è solamente una delle tante applicazioni della serie Simple Mobile Tools. Si possono trovare le altre su https://www.simplemobiletools.com + ✔️ No ads or annoying popups + ✔️ No internet access needed, giving you more privacy & security + ✔️ Only the bare minimum permissions required + ✔️ Emphasis on simplicity – does what a calendar needs to do! + ✔️ Open source + ✔️ Fully customizable themes & calendar / event widgets + ✔️ Translated into 29 languages + ✔️ Export settings to .txt files to import to another device + ✔️ CalDAV calendar sync supported to sync events across devices + ✔️ Daily, weekly, monthly, yearly & event views on the calendar + ✔️ Supports exporting & importing events via .ics files + ✔️ Set multiple event reminders, customize event reminder sound and vibration + ✔️ Snooze option for reminders + ✔️ Easily add holidays, birthdays, anniversaries & appointments + ✔️ Customize events – start time, duration, reminders etc + ✔️ Add event attendees to each event + ✔️ Use as a personal calendar or a business calendar + ✔️ Choose between reminders & email notifications to alert you about an event + + DOWNLOAD SIMPLE CALENDAR PRO – THE SIMPLE OFFLINE CALENDAR WITH NO ADS! + + Check out the full suite of Simple Tools here: + https://www.simplemobiletools.com + + Facebook: + https://www.facebook.com/simplemobiletools + + Reddit: + https://www.reddit.com/r/SimpleMobileTools - An offline calendar for your events without ads, respecting your privacy. - לוח שנה אוף-ליין ללא כל אינטגרציה עם לוח שנה אחר. אפשר בקלות ליצור אירועים מחזוריים ותזכורות אליהם. יש אפשרות להציג את מספרי השבועות. מכיל וויג\'ט 4×4 שניתן להתאים אישית את גודלו, צבע הטקסט והרקע שלו, ושקיפותו. אין פרסומות או דרישות להרשאות בלתי-נחוצות. קוד המקור לגמרי פתוח, וניתן לעצב את צבעי הממשק.\nאפליקציה זו היא רק פיסה אחת מתוך סדרה גדולה יותר של אפליקציות. ניתן למצוא את השאר בכתובת https://www.simplemobiletools.com + Offline calendar with no ads. Organizer & reminders for appointments, events etc + + Simple Calendar Pro is a fully customizable, offline calendar designed to do exactly what a calendar should do. No complicated features, unnecessary permissions and no ads! + + Whether you’re organizing single or recurring events, birthdays, anniversaries, business meetings, appointments or anything else, Simple Calendar Pro makes it easy to stay organized. With an incredible variety of customization options you can customize event reminders, notification sounds, calendar widgets and how the app looks. + + Daily, weekly and monthly views make checking your upcoming events & appointments a breeze. You can even view everything as a simple list of events rather than in calendar view, so you know exactly what’s coming up in your life and when. + + ---------------------------------------------------------- + Simple Calendar Pro – Features & Benefits + ---------------------------------------------------------- + + ✔️ No ads or annoying popups + ✔️ No internet access needed, giving you more privacy & security + ✔️ Only the bare minimum permissions required + ✔️ Emphasis on simplicity – does what a calendar needs to do! + ✔️ Open source + ✔️ Fully customizable themes & calendar / event widgets + ✔️ Translated into 29 languages + ✔️ Export settings to .txt files to import to another device + ✔️ CalDAV calendar sync supported to sync events across devices + ✔️ Daily, weekly, monthly, yearly & event views on the calendar + ✔️ Supports exporting & importing events via .ics files + ✔️ Set multiple event reminders, customize event reminder sound and vibration + ✔️ Snooze option for reminders + ✔️ Easily add holidays, birthdays, anniversaries & appointments + ✔️ Customize events – start time, duration, reminders etc + ✔️ Add event attendees to each event + ✔️ Use as a personal calendar or a business calendar + ✔️ Choose between reminders & email notifications to alert you about an event + + DOWNLOAD SIMPLE CALENDAR PRO – THE SIMPLE OFFLINE CALENDAR WITH NO ADS! + + Check out the full suite of Simple Tools here: + https://www.simplemobiletools.com + + Facebook: + https://www.facebook.com/simplemobiletools + + Reddit: + https://www.reddit.com/r/SimpleMobileTools + - An offline calendar for your events without ads, respecting your privacy. + Offline calendar with no ads. Organizer & reminders for appointments, events etc - CalDAVとの同期オプションも備えた、シンプルなカレンダー。 簡単に定期的な予定を作成し、リマインダーを設定することができます。また、週番号も表示することができます。 + Simple Calendar Pro is a fully customizable, offline calendar designed to do exactly what a calendar should do. No complicated features, unnecessary permissions and no ads! - サイズ変更が可能な 4x4 ウィジェットが含まれており、文字色や背景色、透明度をカスタマイズすることができます。 + Whether you’re organizing single or recurring events, birthdays, anniversaries, business meetings, appointments or anything else, Simple Calendar Pro makes it easy to stay organized. With an incredible variety of customization options you can customize event reminders, notification sounds, calendar widgets and how the app looks. - 広告や不要なアクセス権限は含まれていません。 完全にオープンソースで、ダークテーマも提供しています。 + Daily, weekly and monthly views make checking your upcoming events & appointments a breeze. You can even view everything as a simple list of events rather than in calendar view, so you know exactly what’s coming up in your life and when. - ストレージへのアクセス権限は、.icsファイルから予定をインポート/エクスポートするために必要です。 + ---------------------------------------------------------- + Simple Calendar Pro – Features & Benefits + ---------------------------------------------------------- - 連絡先へのアクセス権限は、誕生日や記念日をインポートするために必要です。 + ✔️ No ads or annoying popups + ✔️ No internet access needed, giving you more privacy & security + ✔️ Only the bare minimum permissions required + ✔️ Emphasis on simplicity – does what a calendar needs to do! + ✔️ Open source + ✔️ Fully customizable themes & calendar / event widgets + ✔️ Translated into 29 languages + ✔️ Export settings to .txt files to import to another device + ✔️ CalDAV calendar sync supported to sync events across devices + ✔️ Daily, weekly, monthly, yearly & event views on the calendar + ✔️ Supports exporting & importing events via .ics files + ✔️ Set multiple event reminders, customize event reminder sound and vibration + ✔️ Snooze option for reminders + ✔️ Easily add holidays, birthdays, anniversaries & appointments + ✔️ Customize events – start time, duration, reminders etc + ✔️ Add event attendees to each event + ✔️ Use as a personal calendar or a business calendar + ✔️ Choose between reminders & email notifications to alert you about an event - このアプリは、大きな一連のアプリの一つです。 他のアプリは https://www.simplemobiletools.com で見つけることができます + DOWNLOAD SIMPLE CALENDAR PRO – THE SIMPLE OFFLINE CALENDAR WITH NO ADS! + + Check out the full suite of Simple Tools here: + https://www.simplemobiletools.com + + Facebook: + https://www.facebook.com/simplemobiletools + + Reddit: + https://www.reddit.com/r/SimpleMobileTools - An offline calendar for your events without ads, respecting your privacy. + Offline calendar with no ads. Organizer & reminders for appointments, events etc - Google 동기화가 있는 심플한 캘린더입니다. 쉽게 반복 이벤트와 알림을 설정할 수 있으며, 주 번호도 표시할 수 있습니다. + Simple Calendar Pro is a fully customizable, offline calendar designed to do exactly what a calendar should do. No complicated features, unnecessary permissions and no ads! - 텍스트의 색상은 물론 배경의 투명도와 색상을 정할 수 있는, 크기 조절이 가능한 4x4 위젯이 포함되어 있습니다. + Whether you’re organizing single or recurring events, birthdays, anniversaries, business meetings, appointments or anything else, Simple Calendar Pro makes it easy to stay organized. With an incredible variety of customization options you can customize event reminders, notification sounds, calendar widgets and how the app looks. - 광고와 불필요한 권한이 없습니다. 이것은 완전히 오픈소스이며, 색상을 설정할 수 있습니다. + Daily, weekly and monthly views make checking your upcoming events & appointments a breeze. You can even view everything as a simple list of events rather than in calendar view, so you know exactly what’s coming up in your life and when. - 저장 권한은 .ics 파일에서 이벤트를 가져오는 경우에만 필요합니다. + ---------------------------------------------------------- + Simple Calendar Pro – Features & Benefits + ---------------------------------------------------------- - The Contacts permission is used only at importing contact birthdays and anniversaries. + ✔️ No ads or annoying popups + ✔️ No internet access needed, giving you more privacy & security + ✔️ Only the bare minimum permissions required + ✔️ Emphasis on simplicity – does what a calendar needs to do! + ✔️ Open source + ✔️ Fully customizable themes & calendar / event widgets + ✔️ Translated into 29 languages + ✔️ Export settings to .txt files to import to another device + ✔️ CalDAV calendar sync supported to sync events across devices + ✔️ Daily, weekly, monthly, yearly & event views on the calendar + ✔️ Supports exporting & importing events via .ics files + ✔️ Set multiple event reminders, customize event reminder sound and vibration + ✔️ Snooze option for reminders + ✔️ Easily add holidays, birthdays, anniversaries & appointments + ✔️ Customize events – start time, duration, reminders etc + ✔️ Add event attendees to each event + ✔️ Use as a personal calendar or a business calendar + ✔️ Choose between reminders & email notifications to alert you about an event - 이 앱은 더 큰 시리즈의 앱들 중 하나입니다. 나머지는 https://www.simplemobiletools.com 에서 찾을 수 있습니다. + DOWNLOAD SIMPLE CALENDAR PRO – THE SIMPLE OFFLINE CALENDAR WITH NO ADS! + + Check out the full suite of Simple Tools here: + https://www.simplemobiletools.com + + Facebook: + https://www.facebook.com/simplemobiletools + + Reddit: + https://www.reddit.com/r/SimpleMobileTools - An offline calendar for your events without ads, respecting your privacy. + Offline calendar with no ads. Organizer & reminders for appointments, events etc - Paprastas kalendorius su CalDAV sinchronizacija. Galite lengvai kurti pasikartojančius įvykius ir nustatyti priminimus, kalendorius gali rodyti savaitės numerius. + Simple Calendar Pro is a fully customizable, offline calendar designed to do exactly what a calendar should do. No complicated features, unnecessary permissions and no ads! - Palaiko mėnesio peržiūrą ir įvykių sąrašo valdiklį, kuriame Jūs galite tinkinti teksto, pagrindinę ir fono spalvas. + Whether you’re organizing single or recurring events, birthdays, anniversaries, business meetings, appointments or anything else, Simple Calendar Pro makes it easy to stay organized. With an incredible variety of customization options you can customize event reminders, notification sounds, calendar widgets and how the app looks. - Neturi reklamų ar nereikalingų leidimų. Programėlė visiškai atviro kodo, yra galimybė keisti spalvas. + Daily, weekly and monthly views make checking your upcoming events & appointments a breeze. You can even view everything as a simple list of events rather than in calendar view, so you know exactly what’s coming up in your life and when. - Saugyklos leidimas reikalingas tik eksportuoti ir importuoti įvykius iš .ics bylų. + ---------------------------------------------------------- + Simple Calendar Pro – Features & Benefits + ---------------------------------------------------------- - Kontaktų leidimas naudojamas tik importuoti kontaktų gimtadienius ir sukaktis. + ✔️ No ads or annoying popups + ✔️ No internet access needed, giving you more privacy & security + ✔️ Only the bare minimum permissions required + ✔️ Emphasis on simplicity – does what a calendar needs to do! + ✔️ Open source + ✔️ Fully customizable themes & calendar / event widgets + ✔️ Translated into 29 languages + ✔️ Export settings to .txt files to import to another device + ✔️ CalDAV calendar sync supported to sync events across devices + ✔️ Daily, weekly, monthly, yearly & event views on the calendar + ✔️ Supports exporting & importing events via .ics files + ✔️ Set multiple event reminders, customize event reminder sound and vibration + ✔️ Snooze option for reminders + ✔️ Easily add holidays, birthdays, anniversaries & appointments + ✔️ Customize events – start time, duration, reminders etc + ✔️ Add event attendees to each event + ✔️ Use as a personal calendar or a business calendar + ✔️ Choose between reminders & email notifications to alert you about an event - Ši programėle yra viena iš keletos mūsų programėlių. Likusias Jūs galite rasti čia https://www.simplemobiletools.com + DOWNLOAD SIMPLE CALENDAR PRO – THE SIMPLE OFFLINE CALENDAR WITH NO ADS! + + Check out the full suite of Simple Tools here: + https://www.simplemobiletools.com + + Facebook: + https://www.facebook.com/simplemobiletools + + Reddit: + https://www.reddit.com/r/SimpleMobileTools - An offline calendar for your events without ads, respecting your privacy. + Offline calendar with no ads. Organizer & reminders for appointments, events etc - A simple calendar with optional CalDAV synchronization. You can easily create recurring events and setup reminders, it can also display week numbers. + Simple Calendar Pro is a fully customizable, offline calendar designed to do exactly what a calendar should do. No complicated features, unnecessary permissions and no ads! - Contains a monthly view and an event list widget where you can customize the color of the text, as well as the alpha and the color of the background. + Whether you’re organizing single or recurring events, birthdays, anniversaries, business meetings, appointments or anything else, Simple Calendar Pro makes it easy to stay organized. With an incredible variety of customization options you can customize event reminders, notification sounds, calendar widgets and how the app looks. - Contains no ads or unnecessary permissions. It is fully opensource, provides customizable colors. + Daily, weekly and monthly views make checking your upcoming events & appointments a breeze. You can even view everything as a simple list of events rather than in calendar view, so you know exactly what’s coming up in your life and when. - The Storage permission is needed only for exporting or importing events from .ics files. + ---------------------------------------------------------- + Simple Calendar Pro – Features & Benefits + ---------------------------------------------------------- - The Contacts permission is used only at importing contact birthdays and anniversaries. + ✔️ No ads or annoying popups + ✔️ No internet access needed, giving you more privacy & security + ✔️ Only the bare minimum permissions required + ✔️ Emphasis on simplicity – does what a calendar needs to do! + ✔️ Open source + ✔️ Fully customizable themes & calendar / event widgets + ✔️ Translated into 29 languages + ✔️ Export settings to .txt files to import to another device + ✔️ CalDAV calendar sync supported to sync events across devices + ✔️ Daily, weekly, monthly, yearly & event views on the calendar + ✔️ Supports exporting & importing events via .ics files + ✔️ Set multiple event reminders, customize event reminder sound and vibration + ✔️ Snooze option for reminders + ✔️ Easily add holidays, birthdays, anniversaries & appointments + ✔️ Customize events – start time, duration, reminders etc + ✔️ Add event attendees to each event + ✔️ Use as a personal calendar or a business calendar + ✔️ Choose between reminders & email notifications to alert you about an event - This app is just one piece of a bigger series of apps. You can find the rest of them at https://www.simplemobiletools.com + DOWNLOAD SIMPLE CALENDAR PRO – THE SIMPLE OFFLINE CALENDAR WITH NO ADS! + + Check out the full suite of Simple Tools here: + https://www.simplemobiletools.com + + Facebook: + https://www.facebook.com/simplemobiletools + + Reddit: + https://www.reddit.com/r/SimpleMobileTools - Een privacyvriendelijke advertentievrije agenda met aan te passen widget. + Offline calendar with no ads. Organizer & reminders for appointments, events etc - Een simpele agenda met optionele CalDAV-synchronisatie. Creëer met gemak herhaalde afspraken met herinneringen. Kan weeknummers tonen. + Simple Calendar Pro is a fully customizable, offline calendar designed to do exactly what a calendar should do. No complicated features, unnecessary permissions and no ads! - Heeft een 4x4 widget, waarbij grootte, achtergrond- en tekstkleuren zijn aan te passen. + Whether you’re organizing single or recurring events, birthdays, anniversaries, business meetings, appointments or anything else, Simple Calendar Pro makes it easy to stay organized. With an incredible variety of customization options you can customize event reminders, notification sounds, calendar widgets and how the app looks. - Bevat geen advertenties of onnodige machtigingen. Volledig open-source. Kleuren van de app kunnen worden aangepast. + Daily, weekly and monthly views make checking your upcoming events & appointments a breeze. You can even view everything as a simple list of events rather than in calendar view, so you know exactly what’s coming up in your life and when. - De machtiging voor externe opslag is alleen nodig voor het importeren/exporteren van afspraken in .ics-bestanden. + ---------------------------------------------------------- + Simple Calendar Pro – Features & Benefits + ---------------------------------------------------------- - De machtiging voor contacten wordt alleen gebruikt voor het importeren van verjaardagen en feestdagen. + ✔️ No ads or annoying popups + ✔️ No internet access needed, giving you more privacy & security + ✔️ Only the bare minimum permissions required + ✔️ Emphasis on simplicity – does what a calendar needs to do! + ✔️ Open source + ✔️ Fully customizable themes & calendar / event widgets + ✔️ Translated into 29 languages + ✔️ Export settings to .txt files to import to another device + ✔️ CalDAV calendar sync supported to sync events across devices + ✔️ Daily, weekly, monthly, yearly & event views on the calendar + ✔️ Supports exporting & importing events via .ics files + ✔️ Set multiple event reminders, customize event reminder sound and vibration + ✔️ Snooze option for reminders + ✔️ Easily add holidays, birthdays, anniversaries & appointments + ✔️ Customize events – start time, duration, reminders etc + ✔️ Add event attendees to each event + ✔️ Use as a personal calendar or a business calendar + ✔️ Choose between reminders & email notifications to alert you about an event - Deze app is onderdeel van een grotere verzameling. Vind de andere apps op https://www.simplemobiletools.com + DOWNLOAD SIMPLE CALENDAR PRO – THE SIMPLE OFFLINE CALENDAR WITH NO ADS! + + Check out the full suite of Simple Tools here: + https://www.simplemobiletools.com + + Facebook: + https://www.facebook.com/simplemobiletools + + Reddit: + https://www.reddit.com/r/SimpleMobileTools - An offline calendar for your events without ads, respecting your privacy. + Offline calendar with no ads. Organizer & reminders for appointments, events etc - A simple calendar with optional CalDAV synchronization. You can easily create recurring events and setup reminders, it can also display week numbers. + Simple Calendar Pro is a fully customizable, offline calendar designed to do exactly what a calendar should do. No complicated features, unnecessary permissions and no ads! - Contains a monthly view and an event list widget where you can customize the color of the text, as well as the alpha and the color of the background. + Whether you’re organizing single or recurring events, birthdays, anniversaries, business meetings, appointments or anything else, Simple Calendar Pro makes it easy to stay organized. With an incredible variety of customization options you can customize event reminders, notification sounds, calendar widgets and how the app looks. - Contains no ads or unnecessary permissions. It is fully opensource, provides customizable colors. + Daily, weekly and monthly views make checking your upcoming events & appointments a breeze. You can even view everything as a simple list of events rather than in calendar view, so you know exactly what’s coming up in your life and when. - The Storage permission is needed only for exporting or importing events from .ics files. + ---------------------------------------------------------- + Simple Calendar Pro – Features & Benefits + ---------------------------------------------------------- - The Contacts permission is used only at importing contact birthdays and anniversaries. + ✔️ No ads or annoying popups + ✔️ No internet access needed, giving you more privacy & security + ✔️ Only the bare minimum permissions required + ✔️ Emphasis on simplicity – does what a calendar needs to do! + ✔️ Open source + ✔️ Fully customizable themes & calendar / event widgets + ✔️ Translated into 29 languages + ✔️ Export settings to .txt files to import to another device + ✔️ CalDAV calendar sync supported to sync events across devices + ✔️ Daily, weekly, monthly, yearly & event views on the calendar + ✔️ Supports exporting & importing events via .ics files + ✔️ Set multiple event reminders, customize event reminder sound and vibration + ✔️ Snooze option for reminders + ✔️ Easily add holidays, birthdays, anniversaries & appointments + ✔️ Customize events – start time, duration, reminders etc + ✔️ Add event attendees to each event + ✔️ Use as a personal calendar or a business calendar + ✔️ Choose between reminders & email notifications to alert you about an event - This app is just one piece of a bigger series of apps. You can find the rest of them at https://www.simplemobiletools.com + DOWNLOAD SIMPLE CALENDAR PRO – THE SIMPLE OFFLINE CALENDAR WITH NO ADS! + + Check out the full suite of Simple Tools here: + https://www.simplemobiletools.com + + Facebook: + https://www.facebook.com/simplemobiletools + + Reddit: + https://www.reddit.com/r/SimpleMobileTools - An offline calendar for your events without ads, respecting your privacy. + Offline calendar with no ads. Organizer & reminders for appointments, events etc -       Prosty kalendarz z obsługą synchronizacji z Dyskiem Google. Dzięki niemu możesz z łatwością tworzyć wydarzenia i przypomnienia, które nigdy nie zaginą. + Simple Calendar Pro is a fully customizable, offline calendar designed to do exactly what a calendar should do. No complicated features, unnecessary permissions and no ads! - Zawiera widżet 4x4 z możliwością ustawiania koloru tekstu i tła, a dla tego drugiego również stopień przezroczystości. + Whether you’re organizing single or recurring events, birthdays, anniversaries, business meetings, appointments or anything else, Simple Calendar Pro makes it easy to stay organized. With an incredible variety of customization options you can customize event reminders, notification sounds, calendar widgets and how the app looks. -       Nie zawiera żadnych żadnych reklam, nie potrzebuje masy uprawnień, jest w pełni otwartoźródłowy, kolory można dowolnie modyfikować. + Daily, weekly and monthly views make checking your upcoming events & appointments a breeze. You can even view everything as a simple list of events rather than in calendar view, so you know exactly what’s coming up in your life and when. - Uprawniena pamięci są potrzebne tylko do eksportowania lub importowania wydarzeń z plików .ics. + ---------------------------------------------------------- + Simple Calendar Pro – Features & Benefits + ---------------------------------------------------------- - Uprawnienia kontaktów są używane tylko do importowania urodzin. + ✔️ No ads or annoying popups + ✔️ No internet access needed, giving you more privacy & security + ✔️ Only the bare minimum permissions required + ✔️ Emphasis on simplicity – does what a calendar needs to do! + ✔️ Open source + ✔️ Fully customizable themes & calendar / event widgets + ✔️ Translated into 29 languages + ✔️ Export settings to .txt files to import to another device + ✔️ CalDAV calendar sync supported to sync events across devices + ✔️ Daily, weekly, monthly, yearly & event views on the calendar + ✔️ Supports exporting & importing events via .ics files + ✔️ Set multiple event reminders, customize event reminder sound and vibration + ✔️ Snooze option for reminders + ✔️ Easily add holidays, birthdays, anniversaries & appointments + ✔️ Customize events – start time, duration, reminders etc + ✔️ Add event attendees to each event + ✔️ Use as a personal calendar or a business calendar + ✔️ Choose between reminders & email notifications to alert you about an event - Niniejsza aplikacja jest tylko częścią naszej kolekcji prostych narzędzi. Ta, jak i pozostałe, dostępne są na stronie https://www.simplemobiletools.com + DOWNLOAD SIMPLE CALENDAR PRO – THE SIMPLE OFFLINE CALENDAR WITH NO ADS! + + Check out the full suite of Simple Tools here: + https://www.simplemobiletools.com + + Facebook: + https://www.facebook.com/simplemobiletools + + Reddit: + https://www.reddit.com/r/SimpleMobileTools - An offline calendar for your events without ads, respecting your privacy. + Offline calendar with no ads. Organizer & reminders for appointments, events etc - Um calendário que não possui qualquer tipo de integração. Pode-se adicionar eventos e lembretes recorrentes, e possui uma opção para mostrar o número da semana. + Simple Calendar Pro is a fully customizable, offline calendar designed to do exactly what a calendar should do. No complicated features, unnecessary permissions and no ads! - Contém um widget 4x4, em que se pode personalizar a cor do texto, bem como a cor e o valor alfa do fundo. + Whether you’re organizing single or recurring events, birthdays, anniversaries, business meetings, appointments or anything else, Simple Calendar Pro makes it easy to stay organized. With an incredible variety of customization options you can customize event reminders, notification sounds, calendar widgets and how the app looks. - Não contém anúncios nem permissões desnecessárias. Disponibiliza um tema escuro, e é totalmente \'open source\'. + Daily, weekly and monthly views make checking your upcoming events & appointments a breeze. You can even view everything as a simple list of events rather than in calendar view, so you know exactly what’s coming up in your life and when. - A permissão de armazenamento é necessária apenas para importar eventos dos arquivos .ics. + ---------------------------------------------------------- + Simple Calendar Pro – Features & Benefits + ---------------------------------------------------------- - A permissão de Contatos é usada apenas na importação de aniversários e aniversários de contato. + ✔️ No ads or annoying popups + ✔️ No internet access needed, giving you more privacy & security + ✔️ Only the bare minimum permissions required + ✔️ Emphasis on simplicity – does what a calendar needs to do! + ✔️ Open source + ✔️ Fully customizable themes & calendar / event widgets + ✔️ Translated into 29 languages + ✔️ Export settings to .txt files to import to another device + ✔️ CalDAV calendar sync supported to sync events across devices + ✔️ Daily, weekly, monthly, yearly & event views on the calendar + ✔️ Supports exporting & importing events via .ics files + ✔️ Set multiple event reminders, customize event reminder sound and vibration + ✔️ Snooze option for reminders + ✔️ Easily add holidays, birthdays, anniversaries & appointments + ✔️ Customize events – start time, duration, reminders etc + ✔️ Add event attendees to each event + ✔️ Use as a personal calendar or a business calendar + ✔️ Choose between reminders & email notifications to alert you about an event - Este aplicativo é apenas parte de um conjunto mais vasto de aplicações. Saiba mais em https://www.simplemobiletools.com + DOWNLOAD SIMPLE CALENDAR PRO – THE SIMPLE OFFLINE CALENDAR WITH NO ADS! + + Check out the full suite of Simple Tools here: + https://www.simplemobiletools.com + + Facebook: + https://www.facebook.com/simplemobiletools + + Reddit: + https://www.reddit.com/r/SimpleMobileTools - Aplicação para gerir os seus eventos, sem anúncios e com total privacidade. + Offline calendar with no ads. Organizer & reminders for appointments, events etc - Um calendário local que não possui qualquer tipo de integração. Pode adicionar eventos e lembretes recorrentes e possui uma opção para mostrar o número da semana. + Simple Calendar Pro is a fully customizable, offline calendar designed to do exactly what a calendar should do. No complicated features, unnecessary permissions and no ads! - Contém um widget 4x4, em que pode personalizar a cor do texto, bem como a cor e o valor alfa do fundo. + Whether you’re organizing single or recurring events, birthdays, anniversaries, business meetings, appointments or anything else, Simple Calendar Pro makes it easy to stay organized. With an incredible variety of customization options you can customize event reminders, notification sounds, calendar widgets and how the app looks. - Não contém anúncios nem permissões desnecessárias. Disponibiliza um tema escuro e é totalmente \'open source\'. + Daily, weekly and monthly views make checking your upcoming events & appointments a breeze. You can even view everything as a simple list of events rather than in calendar view, so you know exactly what’s coming up in your life and when. - A permissão Armazenamento apenas é utilizada para importar eventos de ficheiros .ics. + ---------------------------------------------------------- + Simple Calendar Pro – Features & Benefits + ---------------------------------------------------------- - A permissão Contactos apenas é utilizada para importar os aniversários. - - Esta aplicação é apenas parte de um conjunto mais vasto de aplicações. Saiba mais em https://www.simplemobiletools.com + ✔️ No ads or annoying popups + ✔️ No internet access needed, giving you more privacy & security + ✔️ Only the bare minimum permissions required + ✔️ Emphasis on simplicity – does what a calendar needs to do! + ✔️ Open source + ✔️ Fully customizable themes & calendar / event widgets + ✔️ Translated into 29 languages + ✔️ Export settings to .txt files to import to another device + ✔️ CalDAV calendar sync supported to sync events across devices + ✔️ Daily, weekly, monthly, yearly & event views on the calendar + ✔️ Supports exporting & importing events via .ics files + ✔️ Set multiple event reminders, customize event reminder sound and vibration + ✔️ Snooze option for reminders + ✔️ Easily add holidays, birthdays, anniversaries & appointments + ✔️ Customize events – start time, duration, reminders etc + ✔️ Add event attendees to each event + ✔️ Use as a personal calendar or a business calendar + ✔️ Choose between reminders & email notifications to alert you about an event + + DOWNLOAD SIMPLE CALENDAR PRO – THE SIMPLE OFFLINE CALENDAR WITH NO ADS! + + Check out the full suite of Simple Tools here: + https://www.simplemobiletools.com + + Facebook: + https://www.facebook.com/simplemobiletools + + Reddit: + https://www.reddit.com/r/SimpleMobileTools - Автономный календарь для управления событиями. Конфиденциальный. Без рекламы. + Offline calendar with no ads. Organizer & reminders for appointments, events etc - Оффлайн календарь, без каких-либо интегрированных сторонних функций. Можно создавать повторяющиеся события и устанавливать напоминания. Есть возможность отображения номеров недель. + Simple Calendar Pro is a fully customizable, offline calendar designed to do exactly what a calendar should do. No complicated features, unnecessary permissions and no ads! - У приложения есть виджет 4x4 с изменяемым размером, у которого можно изменить цвет текста, цвет и прозрачность фона. + Whether you’re organizing single or recurring events, birthdays, anniversaries, business meetings, appointments or anything else, Simple Calendar Pro makes it easy to stay organized. With an incredible variety of customization options you can customize event reminders, notification sounds, calendar widgets and how the app looks. - Это приложение не показывает рекламу и не запрашивает лишние разрешения. У него полностью открытый исходный код и настраиваемые цвета оформления. + Daily, weekly and monthly views make checking your upcoming events & appointments a breeze. You can even view everything as a simple list of events rather than in calendar view, so you know exactly what’s coming up in your life and when. - Разрешение для доступа к памяти требуется только для экспорта или импорта событий из файлов .ics. + ---------------------------------------------------------- + Simple Calendar Pro – Features & Benefits + ---------------------------------------------------------- - Разрешение на чтение контактов требуется только при импорте дней рождения. + ✔️ No ads or annoying popups + ✔️ No internet access needed, giving you more privacy & security + ✔️ Only the bare minimum permissions required + ✔️ Emphasis on simplicity – does what a calendar needs to do! + ✔️ Open source + ✔️ Fully customizable themes & calendar / event widgets + ✔️ Translated into 29 languages + ✔️ Export settings to .txt files to import to another device + ✔️ CalDAV calendar sync supported to sync events across devices + ✔️ Daily, weekly, monthly, yearly & event views on the calendar + ✔️ Supports exporting & importing events via .ics files + ✔️ Set multiple event reminders, customize event reminder sound and vibration + ✔️ Snooze option for reminders + ✔️ Easily add holidays, birthdays, anniversaries & appointments + ✔️ Customize events – start time, duration, reminders etc + ✔️ Add event attendees to each event + ✔️ Use as a personal calendar or a business calendar + ✔️ Choose between reminders & email notifications to alert you about an event - Это приложение является лишь частью крупной серии приложений. Вы можете найти остальные на https://www.simplemobiletools.com + DOWNLOAD SIMPLE CALENDAR PRO – THE SIMPLE OFFLINE CALENDAR WITH NO ADS! + + Check out the full suite of Simple Tools here: + https://www.simplemobiletools.com + + Facebook: + https://www.facebook.com/simplemobiletools + + Reddit: + https://www.reddit.com/r/SimpleMobileTools - Offline kalendár pre vaše udalosti bez reklám, rešpektujúca vaše súkromie. + Offline calendar with no ads. Organizer & reminders for appointments, events etc - Jednoduchý kalendár s možnosťou CalDAV synchronizácie. Viete si jednoducho vytvoriť opakujúce sa udalosti s pripomienkami, alebo zobraziť čísla týždňov. + Simple Calendar Pro is a fully customizable, offline calendar designed to do exactly what a calendar should do. No complicated features, unnecessary permissions and no ads! - Obsahuje škálovateľné widgety s mesačným náhľadom alebo zoznamom udalostí, kde viete upraviť farbu textu, ako aj priehľadnosť a farbu pozadia. + Whether you’re organizing single or recurring events, birthdays, anniversaries, business meetings, appointments or anything else, Simple Calendar Pro makes it easy to stay organized. With an incredible variety of customization options you can customize event reminders, notification sounds, calendar widgets and how the app looks. - Neobsahuje žiadne reklamy a nepotrebné oprávnenia. Je opensource, poskytuje možnosť zmeny farieb. + Daily, weekly and monthly views make checking your upcoming events & appointments a breeze. You can even view everything as a simple list of events rather than in calendar view, so you know exactly what’s coming up in your life and when. - Oprávnenie na prístup k súborom je potrebné iba v prípade exportovania a importovania udalostí z .ics súborov. + ---------------------------------------------------------- + Simple Calendar Pro – Features & Benefits + ---------------------------------------------------------- - Oprávnenie ku kontaktom je používané iba pri pridávaní narodenín alebo výročí kontaktov. + ✔️ No ads or annoying popups + ✔️ No internet access needed, giving you more privacy & security + ✔️ Only the bare minimum permissions required + ✔️ Emphasis on simplicity – does what a calendar needs to do! + ✔️ Open source + ✔️ Fully customizable themes & calendar / event widgets + ✔️ Translated into 29 languages + ✔️ Export settings to .txt files to import to another device + ✔️ CalDAV calendar sync supported to sync events across devices + ✔️ Daily, weekly, monthly, yearly & event views on the calendar + ✔️ Supports exporting & importing events via .ics files + ✔️ Set multiple event reminders, customize event reminder sound and vibration + ✔️ Snooze option for reminders + ✔️ Easily add holidays, birthdays, anniversaries & appointments + ✔️ Customize events – start time, duration, reminders etc + ✔️ Add event attendees to each event + ✔️ Use as a personal calendar or a business calendar + ✔️ Choose between reminders & email notifications to alert you about an event - Táto aplikácia je iba jednou zo skupiny aplikácií. Ostatné viete nájsť na https://www.simplemobiletools.com + DOWNLOAD SIMPLE CALENDAR PRO – THE SIMPLE OFFLINE CALENDAR WITH NO ADS! + + Check out the full suite of Simple Tools here: + https://www.simplemobiletools.com + + Facebook: + https://www.facebook.com/simplemobiletools + + Reddit: + https://www.reddit.com/r/SimpleMobileTools - En offlinekalender för dina händelser utan reklam, respekterar din integritet. + Offline calendar with no ads. Organizer & reminders for appointments, events etc - En enkel kalender med valfri CalDAV-synkronisering. Du kan enkelt skapa återkommande händelser och ställa in påminnelser. Den kan också visa veckonummer. + Simple Calendar Pro is a fully customizable, offline calendar designed to do exactly what a calendar should do. No complicated features, unnecessary permissions and no ads! - Har en widget med en månadsvy och en widget med en händelselista. Du kan anpassa widgetarnas textfärger, bakgrundsfärger och bakgrundsgenomskinligheter. + Whether you’re organizing single or recurring events, birthdays, anniversaries, business meetings, appointments or anything else, Simple Calendar Pro makes it easy to stay organized. With an incredible variety of customization options you can customize event reminders, notification sounds, calendar widgets and how the app looks. - Innehåller ingen reklam eller onödiga behörigheter. Den har helt öppen källkod och anpassningsbara färger. + Daily, weekly and monthly views make checking your upcoming events & appointments a breeze. You can even view everything as a simple list of events rather than in calendar view, so you know exactly what’s coming up in your life and when. - Lagringsbehörigheten behövs bara för att exportera eller importera händelser från .ics-filer. + ---------------------------------------------------------- + Simple Calendar Pro – Features & Benefits + ---------------------------------------------------------- - Kontaktbehörigheten används bara för att importera kontakters födelsedagar och årsdagar. + ✔️ No ads or annoying popups + ✔️ No internet access needed, giving you more privacy & security + ✔️ Only the bare minimum permissions required + ✔️ Emphasis on simplicity – does what a calendar needs to do! + ✔️ Open source + ✔️ Fully customizable themes & calendar / event widgets + ✔️ Translated into 29 languages + ✔️ Export settings to .txt files to import to another device + ✔️ CalDAV calendar sync supported to sync events across devices + ✔️ Daily, weekly, monthly, yearly & event views on the calendar + ✔️ Supports exporting & importing events via .ics files + ✔️ Set multiple event reminders, customize event reminder sound and vibration + ✔️ Snooze option for reminders + ✔️ Easily add holidays, birthdays, anniversaries & appointments + ✔️ Customize events – start time, duration, reminders etc + ✔️ Add event attendees to each event + ✔️ Use as a personal calendar or a business calendar + ✔️ Choose between reminders & email notifications to alert you about an event - Denna app är bara en del av en större serie appar. Du hittar resten av dem på https://www.simplemobiletools.com + DOWNLOAD SIMPLE CALENDAR PRO – THE SIMPLE OFFLINE CALENDAR WITH NO ADS! + + Check out the full suite of Simple Tools here: + https://www.simplemobiletools.com + + Facebook: + https://www.facebook.com/simplemobiletools + + Reddit: + https://www.reddit.com/r/SimpleMobileTools - Etkinlikleriniz için reklamsız, gizliliğinizi önemseyen bir çevrimdışı takvim. + Offline calendar with no ads. Organizer & reminders for appointments, events etc - İsteğe bağlı CalDAV senkronizasyonu ile basit bir takvim. Kolayca tekrarlanan etkinlikler oluşturabilir ve hatırlatıcılar ayarlayabilir, ayrıca hafta sayılarını görüntüleyebilirsiniz. + Simple Calendar Pro is a fully customizable, offline calendar designed to do exactly what a calendar should do. No complicated features, unnecessary permissions and no ads! - Metnin renginin yanı sıra alfa ve arka plan rengini özelleştirebileceğiniz aylık görünüm ve etkinlik listesi widget\'ı içerir. + Whether you’re organizing single or recurring events, birthdays, anniversaries, business meetings, appointments or anything else, Simple Calendar Pro makes it easy to stay organized. With an incredible variety of customization options you can customize event reminders, notification sounds, calendar widgets and how the app looks. - Reklam veya gereksiz izinler içermez. Tamamen açık kaynaktır, özelleştirilebilir renkler sağlar. + Daily, weekly and monthly views make checking your upcoming events & appointments a breeze. You can even view everything as a simple list of events rather than in calendar view, so you know exactly what’s coming up in your life and when. - Depolama izni yalnızca .ics dosyalarındaki etkinlikleri dışa veya içe aktarmak için gereklidir. + ---------------------------------------------------------- + Simple Calendar Pro – Features & Benefits + ---------------------------------------------------------- - Kişiler izni yalnızca doğum günlerini ve yıldönümlerini içe aktarırken kullanılır. + ✔️ No ads or annoying popups + ✔️ No internet access needed, giving you more privacy & security + ✔️ Only the bare minimum permissions required + ✔️ Emphasis on simplicity – does what a calendar needs to do! + ✔️ Open source + ✔️ Fully customizable themes & calendar / event widgets + ✔️ Translated into 29 languages + ✔️ Export settings to .txt files to import to another device + ✔️ CalDAV calendar sync supported to sync events across devices + ✔️ Daily, weekly, monthly, yearly & event views on the calendar + ✔️ Supports exporting & importing events via .ics files + ✔️ Set multiple event reminders, customize event reminder sound and vibration + ✔️ Snooze option for reminders + ✔️ Easily add holidays, birthdays, anniversaries & appointments + ✔️ Customize events – start time, duration, reminders etc + ✔️ Add event attendees to each event + ✔️ Use as a personal calendar or a business calendar + ✔️ Choose between reminders & email notifications to alert you about an event - Bu uygulama, daha büyük bir uygulama serisinden sadece bir parça. Geri kalanı http://www.simplemobiletools.com adresinde bulabilirsiniz. + DOWNLOAD SIMPLE CALENDAR PRO – THE SIMPLE OFFLINE CALENDAR WITH NO ADS! + + Check out the full suite of Simple Tools here: + https://www.simplemobiletools.com + + Facebook: + https://www.facebook.com/simplemobiletools + + Reddit: + https://www.reddit.com/r/SimpleMobileTools - 一個沒有廣告的離線行事曆,用來管理你的活動,並且尊重您的隱私。 + Offline calendar with no ads. Organizer & reminders for appointments, events etc - 一個有CalDAV同步選項的簡易行事曆。你可以輕鬆建立週期活動和設置提醒,也能顯示週數。 + Simple Calendar Pro is a fully customizable, offline calendar designed to do exactly what a calendar should do. No complicated features, unnecessary permissions and no ads! - 含有月曆和活動列表的小工具,你可以自訂文字顏色,以及背景顏色和透明度。 + Whether you’re organizing single or recurring events, birthdays, anniversaries, business meetings, appointments or anything else, Simple Calendar Pro makes it easy to stay organized. With an incredible variety of customization options you can customize event reminders, notification sounds, calendar widgets and how the app looks. - 不包含廣告及非必要的權限,而且完全開放原始碼,並提供自訂顏色。 + Daily, weekly and monthly views make checking your upcoming events & appointments a breeze. You can even view everything as a simple list of events rather than in calendar view, so you know exactly what’s coming up in your life and when. - 儲存空間權限只需要用來從.ics檔案匯出或匯入活動。 + ---------------------------------------------------------- + Simple Calendar Pro – Features & Benefits + ---------------------------------------------------------- - 聯絡人權限只是用來匯入聯絡人生日和紀念日。 + ✔️ No ads or annoying popups + ✔️ No internet access needed, giving you more privacy & security + ✔️ Only the bare minimum permissions required + ✔️ Emphasis on simplicity – does what a calendar needs to do! + ✔️ Open source + ✔️ Fully customizable themes & calendar / event widgets + ✔️ Translated into 29 languages + ✔️ Export settings to .txt files to import to another device + ✔️ CalDAV calendar sync supported to sync events across devices + ✔️ Daily, weekly, monthly, yearly & event views on the calendar + ✔️ Supports exporting & importing events via .ics files + ✔️ Set multiple event reminders, customize event reminder sound and vibration + ✔️ Snooze option for reminders + ✔️ Easily add holidays, birthdays, anniversaries & appointments + ✔️ Customize events – start time, duration, reminders etc + ✔️ Add event attendees to each event + ✔️ Use as a personal calendar or a business calendar + ✔️ Choose between reminders & email notifications to alert you about an event - 這程式只是一系列眾多應用程式的其中一項,你可以在這發現更多 https://www.simplemobiletools.com + DOWNLOAD SIMPLE CALENDAR PRO – THE SIMPLE OFFLINE CALENDAR WITH NO ADS! + + Check out the full suite of Simple Tools here: + https://www.simplemobiletools.com + + Facebook: + https://www.facebook.com/simplemobiletools + + Reddit: + https://www.reddit.com/r/SimpleMobileTools - An offline calendar for your events without ads, respecting your privacy. + Offline calendar with no ads. Organizer & reminders for appointments, events etc - A simple calendar with optional CalDAV synchronization. You can easily create recurring events and setup reminders, it can also display week numbers. + Simple Calendar Pro is a fully customizable, offline calendar designed to do exactly what a calendar should do. No complicated features, unnecessary permissions and no ads! - Contains a monthly view and an event list widget where you can customize the color of the text, as well as the alpha and the color of the background. + Whether you’re organizing single or recurring events, birthdays, anniversaries, business meetings, appointments or anything else, Simple Calendar Pro makes it easy to stay organized. With an incredible variety of customization options you can customize event reminders, notification sounds, calendar widgets and how the app looks. - Contains no ads or unnecessary permissions. It is fully opensource, provides customizable colors. + Daily, weekly and monthly views make checking your upcoming events & appointments a breeze. You can even view everything as a simple list of events rather than in calendar view, so you know exactly what’s coming up in your life and when. - The Storage permission is needed only for exporting or importing events from .ics files. + ---------------------------------------------------------- + Simple Calendar Pro – Features & Benefits + ---------------------------------------------------------- - The Contacts permission is used only at importing contact birthdays and anniversaries. + ✔️ No ads or annoying popups + ✔️ No internet access needed, giving you more privacy & security + ✔️ Only the bare minimum permissions required + ✔️ Emphasis on simplicity – does what a calendar needs to do! + ✔️ Open source + ✔️ Fully customizable themes & calendar / event widgets + ✔️ Translated into 29 languages + ✔️ Export settings to .txt files to import to another device + ✔️ CalDAV calendar sync supported to sync events across devices + ✔️ Daily, weekly, monthly, yearly & event views on the calendar + ✔️ Supports exporting & importing events via .ics files + ✔️ Set multiple event reminders, customize event reminder sound and vibration + ✔️ Snooze option for reminders + ✔️ Easily add holidays, birthdays, anniversaries & appointments + ✔️ Customize events – start time, duration, reminders etc + ✔️ Add event attendees to each event + ✔️ Use as a personal calendar or a business calendar + ✔️ Choose between reminders & email notifications to alert you about an event - This app is just one piece of a bigger series of apps. You can find the rest of them at https://www.simplemobiletools.com + DOWNLOAD SIMPLE CALENDAR PRO – THE SIMPLE OFFLINE CALENDAR WITH NO ADS! + + Check out the full suite of Simple Tools here: + https://www.simplemobiletools.com + + Facebook: + https://www.facebook.com/simplemobiletools + + Reddit: + https://www.reddit.com/r/SimpleMobileTools