1 /* 2 * Copyright (C) 2021 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 package com.android.calendar 17 18 import android.provider.CalendarContract.EXTRA_EVENT_BEGIN_TIME 19 import android.provider.CalendarContract.EXTRA_EVENT_END_TIME 20 import android.provider.CalendarContract.Attendees.ATTENDEE_STATUS 21 import android.app.ActionBar 22 import android.app.Activity 23 import android.app.FragmentManager 24 import android.app.FragmentTransaction 25 import android.content.Intent 26 import android.content.res.Resources 27 import android.database.ContentObserver 28 import android.net.Uri 29 import android.os.Bundle 30 import android.os.Handler 31 import android.provider.CalendarContract 32 import android.provider.CalendarContract.Attendees 33 import android.util.Log 34 import android.widget.Toast 35 36 class EventInfoActivity : Activity() { 37 private var mInfoFragment: EventInfoFragment? = null 38 private var mStartMillis: Long = 0 39 private var mEndMillis: Long = 0 40 private var mEventId: Long = 0 41 42 // Create an observer so that we can update the views whenever a 43 // Calendar event changes. 44 private val mObserver: ContentObserver = object : ContentObserver(Handler()) { 45 @Override deliverSelfNotificationsnull46 override fun deliverSelfNotifications(): Boolean { 47 return false 48 } 49 50 @Override onChangenull51 override fun onChange(selfChange: Boolean) { 52 if (selfChange) return 53 val temp = mInfoFragment 54 if (temp != null) { 55 mInfoFragment?.reloadEvents() 56 } 57 } 58 } 59 60 @Override onCreatenull61 protected override fun onCreate(icicle: Bundle?) { 62 super.onCreate(icicle) 63 64 // Get the info needed for the fragment 65 val intent: Intent = getIntent() 66 var attendeeResponse = 0 67 mEventId = -1 68 var isDialog = false 69 if (icicle != null) { 70 mEventId = icicle.getLong(EventInfoFragment.BUNDLE_KEY_EVENT_ID) 71 mStartMillis = icicle.getLong(EventInfoFragment.BUNDLE_KEY_START_MILLIS) 72 mEndMillis = icicle.getLong(EventInfoFragment.BUNDLE_KEY_END_MILLIS) 73 attendeeResponse = icicle.getInt(EventInfoFragment.BUNDLE_KEY_ATTENDEE_RESPONSE) 74 isDialog = icicle.getBoolean(EventInfoFragment.BUNDLE_KEY_IS_DIALOG) 75 } else if (intent != null && Intent.ACTION_VIEW.equals(intent.getAction())) { 76 mStartMillis = intent.getLongExtra(EXTRA_EVENT_BEGIN_TIME, 0) 77 mEndMillis = intent.getLongExtra(EXTRA_EVENT_END_TIME, 0) 78 attendeeResponse = intent.getIntExtra( 79 ATTENDEE_STATUS, 80 Attendees.ATTENDEE_STATUS_NONE 81 ) 82 val data: Uri? = intent.getData() 83 if (data != null) { 84 try { 85 val pathSegments = data.getPathSegments() 86 val size: Int = pathSegments.size 87 if (size > 2 && "EventTime".equals(pathSegments[2])) { 88 // Support non-standard VIEW intent format: 89 // dat = content://com.android.calendar/events/[id]/EventTime/[start]/[end] 90 mEventId = pathSegments[1].toLong() 91 if (size > 4) { 92 mStartMillis = pathSegments[3].toLong() 93 mEndMillis = pathSegments[4].toLong() 94 } 95 } else { 96 mEventId = data.getLastPathSegment() as Long 97 } 98 } catch (e: NumberFormatException) { 99 if (mEventId == -1L) { 100 // do nothing here , deal with it later 101 } else if (mStartMillis == 0L || mEndMillis == 0L) { 102 // Parsing failed on the start or end time , make sure the times were not 103 // pulled from the intent's extras and reset them. 104 mStartMillis = 0 105 mEndMillis = 0 106 } 107 } 108 } 109 } 110 if (mEventId == -1L) { 111 Log.w(TAG, "No event id") 112 Toast.makeText(this, R.string.event_not_found, Toast.LENGTH_SHORT).show() 113 finish() 114 } 115 116 // If we do not support showing full screen event info in this configuration, 117 // close the activity and show the event in AllInOne. 118 val res: Resources = getResources() 119 if (!res.getBoolean(R.bool.agenda_show_event_info_full_screen) && 120 !res.getBoolean(R.bool.show_event_info_full_screen) 121 ) { 122 CalendarController.getInstance(this) 123 ?.launchViewEvent(mEventId, mStartMillis, mEndMillis, attendeeResponse) 124 finish() 125 return 126 } 127 setContentView(R.layout.simple_frame_layout) 128 129 // Get the fragment if exists 130 mInfoFragment = getFragmentManager().findFragmentById(R.id.main_frame) as EventInfoFragment 131 132 // Remove the application title 133 val bar: ActionBar? = getActionBar() 134 if (bar != null) { 135 bar.setDisplayOptions(ActionBar.DISPLAY_HOME_AS_UP or ActionBar.DISPLAY_SHOW_HOME) 136 } 137 138 // Create a new fragment if none exists 139 if (mInfoFragment == null) { 140 val fragmentManager: FragmentManager = getFragmentManager() 141 val ft: FragmentTransaction = fragmentManager.beginTransaction() 142 mInfoFragment = EventInfoFragment( 143 this, 144 mEventId, 145 mStartMillis, 146 mEndMillis, 147 attendeeResponse, 148 isDialog, 149 if (isDialog) EventInfoFragment.DIALOG_WINDOW_STYLE 150 else EventInfoFragment.FULL_WINDOW_STYLE 151 ) 152 ft.replace(R.id.main_frame, mInfoFragment) 153 ft.commit() 154 } 155 } 156 157 @Override onNewIntentnull158 protected override fun onNewIntent(intent: Intent?) { 159 // From the Android Dev Guide: "It's important to note that when 160 // onNewIntent(Intent) is called, the Activity has not been restarted, 161 // so the getIntent() method will still return the Intent that was first 162 // received with onCreate(). This is why setIntent(Intent) is called 163 // inside onNewIntent(Intent) (just in case you call getIntent() at a 164 // later time)." 165 setIntent(intent) 166 } 167 168 @Override onSaveInstanceStatenull169 override fun onSaveInstanceState(outState: Bundle) { 170 super.onSaveInstanceState(outState) 171 } 172 173 @Override onResumenull174 protected override fun onResume() { 175 super.onResume() 176 getContentResolver().registerContentObserver( 177 CalendarContract.Events.CONTENT_URI, 178 true, mObserver 179 ) 180 } 181 182 @Override onPausenull183 protected override fun onPause() { 184 super.onPause() 185 getContentResolver().unregisterContentObserver(mObserver) 186 } 187 188 @Override onDestroynull189 protected override fun onDestroy() { 190 super.onDestroy() 191 } 192 193 companion object { 194 private const val TAG = "EventInfoActivity" 195 } 196 }