summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--cmds/incidentd/Android.bp14
-rw-r--r--cmds/incidentd/src/Privacy.cpp6
-rw-r--r--cmds/incidentd/src/Privacy.h3
-rw-r--r--cmds/incidentd/src/PrivacyFilter.cpp86
-rw-r--r--cmds/incidentd/src/PrivacyFilter.h8
-rw-r--r--cmds/incidentd/src/Reporter.cpp3
-rw-r--r--cmds/incidentd/src/cipher/IncidentKeyStore.cpp87
-rw-r--r--cmds/incidentd/src/cipher/IncidentKeyStore.h53
-rw-r--r--cmds/incidentd/src/cipher/ProtoEncryption.cpp139
-rw-r--r--cmds/incidentd/src/cipher/ProtoEncryption.h80
-rw-r--r--cmds/incidentd/tests/IncidentKeyStore_test.cpp66
-rw-r--r--cmds/incidentd/tests/ProtoEncryption_test.cpp85
-rw-r--r--cmds/screencap/screencap.cpp60
-rw-r--r--cmds/statsd/src/atoms.proto10
-rw-r--r--cmds/statsd/src/external/GpuStatsPuller.cpp3
-rw-r--r--cmds/statsd/tests/external/GpuStatsPuller_test.cpp56
-rw-r--r--config/boot-image-profile.txt9
-rw-r--r--core/java/android/app/ActivityThread.java3
-rw-r--r--core/java/android/app/DownloadManager.java16
-rw-r--r--core/java/android/content/pm/PackageManager.java9
-rw-r--r--core/java/android/content/pm/PackageManagerInternal.java31
-rw-r--r--core/java/android/content/pm/PackageParser.java46
-rw-r--r--core/java/android/net/ConnectivityManager.java10
-rw-r--r--core/java/android/net/IpSecManager.java6
-rw-r--r--core/java/android/net/IpSecTransform.java3
-rw-r--r--core/java/android/os/GraphicsEnvironment.java6
-rw-r--r--core/java/android/os/Process.java9
-rw-r--r--core/java/android/os/ZygoteProcess.java18
-rw-r--r--core/java/android/os/storage/IStorageManager.aidl2
-rw-r--r--core/java/android/os/storage/StorageManager.java30
-rw-r--r--core/java/android/os/storage/StorageManagerInternal.java31
-rw-r--r--core/java/android/provider/Settings.java13
-rw-r--r--core/java/android/view/RenderNodeAnimator.java6
-rw-r--r--core/java/android/view/Window.java1
-rw-r--r--core/java/android/view/autofill/AutofillManager.java46
-rw-r--r--core/java/com/android/internal/os/BatteryStatsImpl.java6
-rw-r--r--core/java/com/android/internal/os/Zygote.java20
-rw-r--r--core/java/com/android/internal/os/ZygoteArguments.java13
-rw-r--r--core/java/com/android/internal/os/ZygoteConnection.java3
-rw-r--r--core/java/com/android/internal/policy/DecorView.java26
-rw-r--r--core/jni/android_os_GraphicsEnvironment.cpp5
-rw-r--r--core/jni/com_android_internal_os_Zygote.cpp405
-rw-r--r--core/proto/android/app/settings_enums.proto19
-rw-r--r--[-rwxr-xr-x]core/res/res/anim/lock_in.xml255
-rw-r--r--[-rwxr-xr-x]core/res/res/anim/lock_lock.xml379
-rwxr-xr-xcore/res/res/anim/lock_out.xml277
-rw-r--r--core/res/res/anim/lock_scanning.xml301
-rw-r--r--[-rwxr-xr-x]core/res/res/anim/lock_to_error.xml109
-rw-r--r--[-rwxr-xr-x]core/res/res/anim/lock_unlock.xml328
-rw-r--r--core/res/res/drawable/ic_lock.xml14
-rw-r--r--core/res/res/drawable/ic_lock_open.xml12
-rw-r--r--core/res/res/layout-car/car_preference.xml12
-rw-r--r--core/res/res/layout-car/car_preference_category.xml14
-rw-r--r--core/res/res/values-af/strings.xml11
-rw-r--r--core/res/res/values-am/strings.xml11
-rw-r--r--core/res/res/values-ar/strings.xml11
-rw-r--r--core/res/res/values-as/strings.xml11
-rw-r--r--core/res/res/values-az/strings.xml11
-rw-r--r--core/res/res/values-b+sr+Latn/strings.xml11
-rw-r--r--core/res/res/values-be/strings.xml11
-rw-r--r--core/res/res/values-bg/strings.xml11
-rw-r--r--core/res/res/values-bn/strings.xml17
-rw-r--r--core/res/res/values-bs/strings.xml11
-rw-r--r--core/res/res/values-ca/strings.xml21
-rw-r--r--core/res/res/values-cs/strings.xml13
-rw-r--r--core/res/res/values-da/strings.xml13
-rw-r--r--core/res/res/values-de/strings.xml11
-rw-r--r--core/res/res/values-el/strings.xml11
-rw-r--r--core/res/res/values-en-rAU/strings.xml15
-rw-r--r--core/res/res/values-en-rCA/strings.xml15
-rw-r--r--core/res/res/values-en-rGB/strings.xml15
-rw-r--r--core/res/res/values-en-rIN/strings.xml15
-rw-r--r--core/res/res/values-en-rXC/strings.xml11
-rw-r--r--core/res/res/values-es-rUS/strings.xml13
-rw-r--r--core/res/res/values-es/strings.xml11
-rw-r--r--core/res/res/values-et/strings.xml11
-rw-r--r--core/res/res/values-eu/strings.xml11
-rw-r--r--core/res/res/values-fa/strings.xml11
-rw-r--r--core/res/res/values-fi/strings.xml13
-rw-r--r--core/res/res/values-fr-rCA/strings.xml11
-rw-r--r--core/res/res/values-fr/strings.xml13
-rw-r--r--core/res/res/values-gl/strings.xml43
-rw-r--r--core/res/res/values-gu/strings.xml9
-rw-r--r--core/res/res/values-hi/strings.xml55
-rw-r--r--core/res/res/values-hr/strings.xml13
-rw-r--r--core/res/res/values-hu/strings.xml27
-rw-r--r--core/res/res/values-hy/strings.xml15
-rw-r--r--core/res/res/values-in/strings.xml11
-rw-r--r--core/res/res/values-is/strings.xml11
-rw-r--r--core/res/res/values-it/strings.xml17
-rw-r--r--core/res/res/values-iw/strings.xml11
-rw-r--r--core/res/res/values-ja/strings.xml13
-rw-r--r--core/res/res/values-ka/strings.xml11
-rw-r--r--core/res/res/values-kk/strings.xml13
-rw-r--r--core/res/res/values-km/strings.xml13
-rw-r--r--core/res/res/values-kn/strings.xml13
-rw-r--r--core/res/res/values-ko/strings.xml13
-rw-r--r--core/res/res/values-ky/strings.xml23
-rw-r--r--core/res/res/values-lo/strings.xml9
-rw-r--r--core/res/res/values-lt/strings.xml11
-rw-r--r--core/res/res/values-lv/strings.xml11
-rw-r--r--core/res/res/values-mk/strings.xml13
-rw-r--r--core/res/res/values-ml/strings.xml11
-rw-r--r--core/res/res/values-mn/strings.xml11
-rw-r--r--core/res/res/values-mr/strings.xml17
-rw-r--r--core/res/res/values-ms/strings.xml11
-rw-r--r--core/res/res/values-my/strings.xml13
-rw-r--r--core/res/res/values-nb/strings.xml15
-rw-r--r--core/res/res/values-ne/strings.xml11
-rw-r--r--core/res/res/values-nl/strings.xml27
-rw-r--r--core/res/res/values-or/strings.xml21
-rw-r--r--core/res/res/values-pa/strings.xml11
-rw-r--r--core/res/res/values-pl/strings.xml11
-rw-r--r--core/res/res/values-pt-rBR/strings.xml13
-rw-r--r--core/res/res/values-pt-rPT/strings.xml11
-rw-r--r--core/res/res/values-pt/strings.xml13
-rw-r--r--core/res/res/values-ro/strings.xml11
-rw-r--r--core/res/res/values-ru/strings.xml13
-rw-r--r--core/res/res/values-si/strings.xml11
-rw-r--r--core/res/res/values-sk/strings.xml21
-rw-r--r--core/res/res/values-sl/strings.xml13
-rw-r--r--core/res/res/values-sq/strings.xml13
-rw-r--r--core/res/res/values-sr/strings.xml11
-rw-r--r--core/res/res/values-sv/strings.xml11
-rw-r--r--core/res/res/values-sw/strings.xml13
-rw-r--r--core/res/res/values-ta/strings.xml26
-rw-r--r--core/res/res/values-te/strings.xml11
-rw-r--r--core/res/res/values-th/strings.xml13
-rw-r--r--core/res/res/values-tl/strings.xml11
-rw-r--r--core/res/res/values-tr/strings.xml11
-rw-r--r--core/res/res/values-uk/strings.xml13
-rw-r--r--core/res/res/values-ur/strings.xml13
-rw-r--r--core/res/res/values-uz/strings.xml15
-rw-r--r--core/res/res/values-vi/strings.xml11
-rw-r--r--core/res/res/values-zh-rCN/strings.xml9
-rw-r--r--core/res/res/values-zh-rHK/strings.xml15
-rw-r--r--core/res/res/values-zh-rTW/strings.xml13
-rw-r--r--core/res/res/values-zu/strings.xml13
-rw-r--r--core/res/res/values/config.xml5
-rw-r--r--core/res/res/values/dimens_car.xml4
-rw-r--r--core/res/res/values/styles_device_defaults.xml22
-rw-r--r--core/tests/coretests/src/android/provider/SettingsBackupTest.java3
-rw-r--r--data/etc/privapp-permissions-platform.xml7
-rw-r--r--libs/protoutil/src/ProtoFileReader.cpp2
-rw-r--r--location/java/com/android/internal/location/GpsNetInitiatedHandler.java14
-rw-r--r--media/java/android/media/AudioManager.java2
-rw-r--r--media/java/android/media/AudioRecord.java1
-rw-r--r--media/java/android/media/AudioRecordingConfiguration.java2
-rw-r--r--media/java/android/media/IAudioService.aidl2
-rw-r--r--media/java/android/media/MediaParceledListSlice.aidl20
-rw-r--r--media/java/android/media/MediaParceledListSlice.java200
-rw-r--r--media/java/android/media/browse/MediaBrowser.java8
-rw-r--r--media/java/android/media/session/ISession.aidl4
-rw-r--r--media/java/android/media/session/ISessionController.aidl4
-rw-r--r--media/java/android/media/session/ISessionControllerCallback.aidl4
-rw-r--r--media/java/android/media/session/MediaController.java8
-rw-r--r--media/java/android/media/session/MediaSession.java4
-rw-r--r--media/java/android/service/media/IMediaBrowserServiceCallbacks.aidl6
-rw-r--r--media/java/android/service/media/MediaBrowserService.java6
-rw-r--r--packages/CaptivePortalLogin/AndroidManifest.xml1
-rw-r--r--packages/CaptivePortalLogin/res/drawable/app_icon.xml26
-rw-r--r--packages/CaptivePortalLogin/res/drawable/maybe_wifi.xml27
-rw-r--r--packages/DefaultContainerService/Android.bp8
-rw-r--r--packages/DefaultContainerService/AndroidManifest.xml23
-rw-r--r--packages/DefaultContainerService/jni/Android.bp36
-rw-r--r--packages/DefaultContainerService/jni/com_android_defcontainer_MeasurementUtils.cpp76
-rw-r--r--packages/DefaultContainerService/res/values-af/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-am/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-ar/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-as/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-az/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-b+sr+Latn/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-be/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-bg/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-bn/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-bs/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-ca/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-cs/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-da/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-de/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-el/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-en-rAU/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-en-rCA/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-en-rGB/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-en-rIN/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-en-rXC/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-es-rUS/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-es/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-et/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-eu/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-fa/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-fi/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-fr-rCA/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-fr/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-gl/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-gu/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-hi/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-hr/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-hu/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-hy/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-in/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-is/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-it/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-iw/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-ja/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-ka/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-kk/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-km/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-kn/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-ko/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-ky/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-lo/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-lt/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-lv/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-mk/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-ml/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-mn/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-mr/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-ms/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-my/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-nb/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-ne/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-nl/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-or/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-pa/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-pl/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-pt-rBR/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-pt-rPT/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-pt/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-ro/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-ru/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-si/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-sk/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-sl/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-sq/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-sr/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-sv/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-sw/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-ta/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-te/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-th/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-tl/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-tr/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-uk/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-ur/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-uz/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-vi/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-zh-rCN/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-zh-rHK/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-zh-rTW/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values-zu/strings.xml24
-rw-r--r--packages/DefaultContainerService/res/values/strings.xml23
-rw-r--r--packages/DefaultContainerService/src/com/android/defcontainer/DefaultContainerService.java211
-rw-r--r--packages/DefaultContainerService/src/com/android/defcontainer/MeasurementUtils.java29
-rw-r--r--packages/ExtServices/src/android/ext/services/autofill/EditDistanceScorer.java2
-rw-r--r--packages/ExtServices/tests/src/android/ext/services/autofill/EditDistanceScorerTest.java8
-rw-r--r--packages/NetworkStack/src/android/net/NetworkStackIpMemoryStore.java8
-rw-r--r--packages/NetworkStack/src/com/android/server/connectivity/NetworkMonitor.java27
-rw-r--r--packages/NetworkStack/tests/src/com/android/server/connectivity/NetworkMonitorTest.java209
-rw-r--r--packages/SettingsLib/src/com/android/settingslib/net/DataUsageController.java40
-rw-r--r--packages/SettingsLib/src/com/android/settingslib/wifi/WifiTracker.java5
-rw-r--r--packages/SettingsLib/tests/robotests/src/com/android/settingslib/net/DataUsageControllerTest.java62
-rw-r--r--packages/SettingsProvider/res/values/defaults.xml6
-rw-r--r--packages/SettingsProvider/src/com/android/providers/settings/SettingsProvider.java33
-rw-r--r--packages/SystemUI/plugin/src/com/android/systemui/plugins/GlobalActionsPanelPlugin.java10
-rw-r--r--packages/SystemUI/plugin/src/com/android/systemui/plugins/statusbar/phone/NavBarButtonProvider.java56
-rw-r--r--packages/SystemUI/plugin/src/com/android/systemui/plugins/statusbar/phone/NavGesture.java54
-rw-r--r--packages/SystemUI/res-keyguard/layout/digital_clock.xml1
-rw-r--r--packages/SystemUI/res-keyguard/layout/keyguard_bouncer.xml3
-rw-r--r--packages/SystemUI/res-keyguard/layout/keyguard_clock_switch.xml3
-rw-r--r--packages/SystemUI/res-keyguard/layout/keyguard_status_area.xml7
-rw-r--r--packages/SystemUI/res-keyguard/layout/keyguard_status_view.xml1
-rw-r--r--packages/SystemUI/res-keyguard/values-ca/strings.xml6
-rw-r--r--packages/SystemUI/res-keyguard/values-h560dp/dimens.xml4
-rw-r--r--packages/SystemUI/res-keyguard/values-h650dp/dimens.xml4
-rw-r--r--packages/SystemUI/res-keyguard/values-hi/strings.xml8
-rw-r--r--packages/SystemUI/res-keyguard/values-sw600dp/dimens.xml2
-rw-r--r--packages/SystemUI/res-keyguard/values/dimens.xml21
-rw-r--r--packages/SystemUI/res-keyguard/values/styles.xml1
-rw-r--r--packages/SystemUI/res/drawable/bubble_dismiss_circle.xml27
-rw-r--r--packages/SystemUI/res/drawable/bubble_dismiss_icon.xml26
-rw-r--r--packages/SystemUI/res/drawable/global_action_panel_scrim.xml26
-rw-r--r--packages/SystemUI/res/layout/bubble_dismiss_target.xml66
-rw-r--r--packages/SystemUI/res/layout/nav_bar_tuner_inflater.xml27
-rw-r--r--packages/SystemUI/res/layout/notif_half_shelf.xml126
-rw-r--r--packages/SystemUI/res/layout/notif_half_shelf_row.xml78
-rw-r--r--packages/SystemUI/res/values-af/strings.xml10
-rw-r--r--packages/SystemUI/res/values-am/strings.xml10
-rw-r--r--packages/SystemUI/res/values-ar/strings.xml10
-rw-r--r--packages/SystemUI/res/values-as/strings.xml10
-rw-r--r--packages/SystemUI/res/values-az/strings.xml8
-rw-r--r--packages/SystemUI/res/values-b+sr+Latn/strings.xml16
-rw-r--r--packages/SystemUI/res/values-be/strings.xml10
-rw-r--r--packages/SystemUI/res/values-bg/strings.xml10
-rw-r--r--packages/SystemUI/res/values-bn/strings.xml12
-rw-r--r--packages/SystemUI/res/values-bs/strings.xml16
-rw-r--r--packages/SystemUI/res/values-ca/strings.xml28
-rw-r--r--packages/SystemUI/res/values-cs/strings.xml12
-rw-r--r--packages/SystemUI/res/values-da/strings.xml12
-rw-r--r--packages/SystemUI/res/values-de/strings.xml10
-rw-r--r--packages/SystemUI/res/values-el/strings.xml8
-rw-r--r--packages/SystemUI/res/values-en-rAU/strings.xml10
-rw-r--r--packages/SystemUI/res/values-en-rCA/strings.xml10
-rw-r--r--packages/SystemUI/res/values-en-rGB/strings.xml10
-rw-r--r--packages/SystemUI/res/values-en-rIN/strings.xml10
-rw-r--r--packages/SystemUI/res/values-en-rXC/strings.xml2
-rw-r--r--packages/SystemUI/res/values-es-rUS/strings.xml10
-rw-r--r--packages/SystemUI/res/values-es/strings.xml16
-rw-r--r--packages/SystemUI/res/values-et/strings.xml10
-rw-r--r--packages/SystemUI/res/values-eu/strings.xml20
-rw-r--r--packages/SystemUI/res/values-fa/strings.xml18
-rw-r--r--packages/SystemUI/res/values-fi/strings.xml10
-rw-r--r--packages/SystemUI/res/values-fr-rCA/strings.xml10
-rw-r--r--packages/SystemUI/res/values-fr/strings.xml20
-rw-r--r--packages/SystemUI/res/values-gl/strings.xml28
-rw-r--r--packages/SystemUI/res/values-gu/strings.xml10
-rw-r--r--packages/SystemUI/res/values-hi/strings.xml50
-rw-r--r--packages/SystemUI/res/values-hr/strings.xml10
-rw-r--r--packages/SystemUI/res/values-hu/strings.xml10
-rw-r--r--packages/SystemUI/res/values-hy/strings.xml10
-rw-r--r--packages/SystemUI/res/values-in/strings.xml14
-rw-r--r--packages/SystemUI/res/values-is/strings.xml10
-rw-r--r--packages/SystemUI/res/values-it/strings.xml18
-rw-r--r--packages/SystemUI/res/values-iw/strings.xml10
-rw-r--r--packages/SystemUI/res/values-ja/strings.xml12
-rw-r--r--packages/SystemUI/res/values-ka/strings.xml12
-rw-r--r--packages/SystemUI/res/values-kk/strings.xml14
-rw-r--r--packages/SystemUI/res/values-km/strings.xml12
-rw-r--r--packages/SystemUI/res/values-kn/strings.xml10
-rw-r--r--packages/SystemUI/res/values-ko/strings.xml20
-rw-r--r--packages/SystemUI/res/values-ky/strings.xml28
-rw-r--r--packages/SystemUI/res/values-lo/strings.xml8
-rw-r--r--packages/SystemUI/res/values-lt/strings.xml7
-rw-r--r--packages/SystemUI/res/values-lv/strings.xml10
-rw-r--r--packages/SystemUI/res/values-mk/strings.xml8
-rw-r--r--packages/SystemUI/res/values-ml/strings.xml14
-rw-r--r--packages/SystemUI/res/values-mn/strings.xml12
-rw-r--r--packages/SystemUI/res/values-mr/strings.xml18
-rw-r--r--packages/SystemUI/res/values-ms/strings.xml10
-rw-r--r--packages/SystemUI/res/values-my/strings.xml10
-rw-r--r--packages/SystemUI/res/values-nb/strings.xml10
-rw-r--r--packages/SystemUI/res/values-ne/strings.xml10
-rw-r--r--packages/SystemUI/res/values-night/colors.xml3
-rw-r--r--packages/SystemUI/res/values-nl/strings.xml16
-rw-r--r--packages/SystemUI/res/values-or/strings.xml18
-rw-r--r--packages/SystemUI/res/values-pa/strings.xml10
-rw-r--r--packages/SystemUI/res/values-pl/strings.xml12
-rw-r--r--packages/SystemUI/res/values-pt-rBR/strings.xml10
-rw-r--r--packages/SystemUI/res/values-pt-rPT/strings.xml10
-rw-r--r--packages/SystemUI/res/values-pt/strings.xml10
-rw-r--r--packages/SystemUI/res/values-ro/strings.xml10
-rw-r--r--packages/SystemUI/res/values-ru/strings.xml14
-rw-r--r--packages/SystemUI/res/values-si/strings.xml10
-rw-r--r--packages/SystemUI/res/values-sk/strings.xml14
-rw-r--r--packages/SystemUI/res/values-sl/strings.xml18
-rw-r--r--packages/SystemUI/res/values-sq/strings.xml10
-rw-r--r--packages/SystemUI/res/values-sr/strings.xml16
-rw-r--r--packages/SystemUI/res/values-sv/strings.xml10
-rw-r--r--packages/SystemUI/res/values-sw/strings.xml10
-rw-r--r--packages/SystemUI/res/values-ta/strings.xml34
-rw-r--r--packages/SystemUI/res/values-te/strings.xml12
-rw-r--r--packages/SystemUI/res/values-th/strings.xml14
-rw-r--r--packages/SystemUI/res/values-tl/strings.xml10
-rw-r--r--packages/SystemUI/res/values-tr/strings.xml20
-rw-r--r--packages/SystemUI/res/values-uk/strings.xml12
-rw-r--r--packages/SystemUI/res/values-ur/strings.xml27
-rw-r--r--packages/SystemUI/res/values-uz/strings.xml18
-rw-r--r--packages/SystemUI/res/values-vi/strings.xml12
-rw-r--r--packages/SystemUI/res/values-zh-rCN/strings.xml9
-rw-r--r--packages/SystemUI/res/values-zh-rHK/strings.xml10
-rw-r--r--packages/SystemUI/res/values-zh-rTW/strings.xml10
-rw-r--r--packages/SystemUI/res/values-zu/strings.xml10
-rw-r--r--packages/SystemUI/res/values/colors.xml2
-rw-r--r--packages/SystemUI/res/values/dimens.xml11
-rw-r--r--packages/SystemUI/res/values/strings.xml8
-rw-r--r--packages/SystemUI/res/values/styles.xml6
-rw-r--r--packages/SystemUI/src/com/android/keyguard/KeyguardClockSwitch.java2
-rw-r--r--packages/SystemUI/src/com/android/keyguard/KeyguardPatternView.java7
-rw-r--r--packages/SystemUI/src/com/android/keyguard/KeyguardSecurityContainer.java140
-rw-r--r--packages/SystemUI/src/com/android/keyguard/KeyguardSecurityView.java11
-rw-r--r--packages/SystemUI/src/com/android/keyguard/KeyguardSliceView.java21
-rw-r--r--packages/SystemUI/src/com/android/keyguard/KeyguardStatusView.java32
-rw-r--r--packages/SystemUI/src/com/android/keyguard/KeyguardUpdateMonitor.java20
-rw-r--r--packages/SystemUI/src/com/android/systemui/Dependency.java6
-rw-r--r--packages/SystemUI/src/com/android/systemui/DependencyProvider.java9
-rw-r--r--packages/SystemUI/src/com/android/systemui/bubbles/BubbleController.java2
-rw-r--r--packages/SystemUI/src/com/android/systemui/bubbles/BubbleDismissView.java227
-rw-r--r--packages/SystemUI/src/com/android/systemui/bubbles/BubbleStackView.java247
-rw-r--r--packages/SystemUI/src/com/android/systemui/bubbles/BubbleTouchHandler.java132
-rw-r--r--packages/SystemUI/src/com/android/systemui/bubbles/animation/ExpandedAnimationController.java101
-rw-r--r--packages/SystemUI/src/com/android/systemui/bubbles/animation/PhysicsAnimationLayout.java73
-rw-r--r--packages/SystemUI/src/com/android/systemui/bubbles/animation/StackAnimationController.java183
-rw-r--r--packages/SystemUI/src/com/android/systemui/classifier/ClassifierData.java2
-rw-r--r--packages/SystemUI/src/com/android/systemui/classifier/FalsingManagerImpl.java22
-rw-r--r--packages/SystemUI/src/com/android/systemui/globalactions/GlobalActionsDialog.java25
-rw-r--r--packages/SystemUI/src/com/android/systemui/qs/TileLayout.java2
-rw-r--r--packages/SystemUI/src/com/android/systemui/statusbar/KeyguardIndicationController.java2
-rw-r--r--packages/SystemUI/src/com/android/systemui/statusbar/notification/NotificationUtils.java16
-rw-r--r--packages/SystemUI/src/com/android/systemui/statusbar/notification/row/ChannelEditorDialogController.kt267
-rw-r--r--packages/SystemUI/src/com/android/systemui/statusbar/notification/row/ChannelEditorListView.kt172
-rw-r--r--packages/SystemUI/src/com/android/systemui/statusbar/notification/row/ExpandableNotificationRow.java11
-rw-r--r--packages/SystemUI/src/com/android/systemui/statusbar/notification/row/NotificationGutsManager.java9
-rw-r--r--packages/SystemUI/src/com/android/systemui/statusbar/notification/row/NotificationInfo.java34
-rw-r--r--packages/SystemUI/src/com/android/systemui/statusbar/phone/ButtonDispatcher.java1
-rw-r--r--packages/SystemUI/src/com/android/systemui/statusbar/phone/ButtonInterface.java (renamed from cmds/incidentd/src/cipher/cipher_blocks.proto)22
-rw-r--r--packages/SystemUI/src/com/android/systemui/statusbar/phone/NavigationBarFragment.java4
-rw-r--r--packages/SystemUI/src/com/android/systemui/statusbar/phone/NavigationBarInflaterView.java58
-rw-r--r--packages/SystemUI/src/com/android/systemui/statusbar/phone/NavigationBarTransitions.java1
-rw-r--r--packages/SystemUI/src/com/android/systemui/statusbar/phone/NavigationBarView.java74
-rw-r--r--packages/SystemUI/src/com/android/systemui/statusbar/phone/NavigationHandle.java1
-rw-r--r--packages/SystemUI/src/com/android/systemui/statusbar/phone/ShadeController.java6
-rw-r--r--packages/SystemUI/src/com/android/systemui/statusbar/phone/StatusBar.java6
-rw-r--r--packages/SystemUI/src/com/android/systemui/statusbar/policy/BluetoothControllerImpl.java20
-rw-r--r--packages/SystemUI/src/com/android/systemui/statusbar/policy/KeyButtonView.java2
-rw-r--r--packages/SystemUI/src/com/android/systemui/tuner/PreviewNavInflater.java74
-rw-r--r--packages/SystemUI/tests/src/com/android/systemui/bubbles/animation/ExpandedAnimationControllerTest.java80
-rw-r--r--packages/SystemUI/tests/src/com/android/systemui/bubbles/animation/PhysicsAnimationLayoutTestCase.java6
-rw-r--r--packages/SystemUI/tests/src/com/android/systemui/bubbles/animation/StackAnimationControllerTest.java64
-rw-r--r--packages/SystemUI/tests/src/com/android/systemui/statusbar/KeyguardIndicationControllerTest.java2
-rw-r--r--packages/SystemUI/tests/src/com/android/systemui/statusbar/notification/row/ChannelEditorDialogControllerTest.kt190
-rw-r--r--packages/SystemUI/tests/src/com/android/systemui/statusbar/notification/row/NotificationGutsManagerTest.java11
-rw-r--r--packages/SystemUI/tests/src/com/android/systemui/statusbar/notification/row/NotificationInfoTest.java156
-rw-r--r--packages/SystemUI/tests/src/com/android/systemui/statusbar/policy/BluetoothControllerImplTest.java20
-rw-r--r--proto/src/metrics_constants/metrics_constants.proto9
-rw-r--r--services/autofill/java/com/android/server/autofill/AutofillManagerServiceImpl.java7
-rw-r--r--services/autofill/java/com/android/server/autofill/Session.java10
-rw-r--r--services/autofill/java/com/android/server/autofill/ui/FillUi.java1
-rw-r--r--services/core/java/com/android/server/IpSecService.java20
-rw-r--r--services/core/java/com/android/server/StorageManagerService.java194
-rw-r--r--services/core/java/com/android/server/am/ActiveServices.java17
-rw-r--r--services/core/java/com/android/server/am/ActivityManagerService.java7
-rw-r--r--services/core/java/com/android/server/am/ProcessList.java10
-rw-r--r--services/core/java/com/android/server/am/ServiceRecord.java72
-rw-r--r--services/core/java/com/android/server/am/UserController.java62
-rw-r--r--services/core/java/com/android/server/am/UserState.java11
-rw-r--r--services/core/java/com/android/server/appop/AppOpsService.java4
-rw-r--r--services/core/java/com/android/server/attention/AttentionManagerService.java31
-rw-r--r--services/core/java/com/android/server/audio/AudioService.java91
-rw-r--r--services/core/java/com/android/server/audio/RecordingActivityMonitor.java19
-rw-r--r--services/core/java/com/android/server/display/BrightnessMappingStrategy.java1
-rw-r--r--services/core/java/com/android/server/location/GnssLocationProvider.java135
-rw-r--r--services/core/java/com/android/server/location/GnssVisibilityControl.java65
-rw-r--r--services/core/java/com/android/server/media/MediaSessionRecord.java14
-rw-r--r--services/core/java/com/android/server/media/MediaSessionService.java2230
-rw-r--r--services/core/java/com/android/server/media/MediaSessionServiceImpl.java2274
-rw-r--r--services/core/java/com/android/server/notification/NotificationManagerService.java10
-rw-r--r--services/core/java/com/android/server/pm/ApexManager.java203
-rw-r--r--services/core/java/com/android/server/pm/PackageDexOptimizer.java18
-rw-r--r--services/core/java/com/android/server/pm/PackageInstallerService.java3
-rw-r--r--services/core/java/com/android/server/pm/PackageInstallerSession.java2
-rw-r--r--services/core/java/com/android/server/pm/PackageManagerService.java66
-rw-r--r--services/core/java/com/android/server/pm/Settings.java39
-rw-r--r--services/core/java/com/android/server/pm/SharedUserSetting.java5
-rw-r--r--services/core/java/com/android/server/pm/StagingManager.java6
-rw-r--r--services/core/java/com/android/server/pm/permission/DefaultPermissionGrantPolicy.java15
-rw-r--r--services/core/java/com/android/server/power/AttentionDetector.java14
-rw-r--r--services/core/java/com/android/server/role/RoleManagerService.java11
-rw-r--r--services/core/java/com/android/server/telecom/TelecomLoaderService.java67
-rw-r--r--services/core/java/com/android/server/wm/ActivityStarter.java14
-rw-r--r--services/core/java/com/android/server/wm/ActivityTaskManagerService.java3
-rw-r--r--services/core/java/com/android/server/wm/DisplayContent.java63
-rw-r--r--services/core/java/com/android/server/wm/DisplayRotation.java23
-rw-r--r--services/core/java/com/android/server/wm/LockTaskController.java24
-rw-r--r--services/core/java/com/android/server/wm/RootWindowContainer.java7
-rw-r--r--services/core/jni/com_android_server_input_InputManagerService.cpp34
-rw-r--r--services/core/xsd/vts/Android.bp1
-rw-r--r--services/core/xsd/vts/ValidateDefaultPermissions.cpp43
-rw-r--r--services/java/com/android/server/SystemServer.java7
-rw-r--r--services/net/java/android/net/IpMemoryStore.java33
-rw-r--r--services/net/java/android/net/IpMemoryStoreClient.java108
-rw-r--r--services/net/java/android/net/ip/IpClientManager.java273
-rw-r--r--services/tests/servicestests/src/com/android/server/StorageManagerServiceTest.java223
-rw-r--r--services/tests/wmtests/src/com/android/server/wm/DisplayContentTests.java47
-rw-r--r--services/tests/wmtests/src/com/android/server/wm/DisplayRotationTests.java39
-rw-r--r--services/tests/wmtests/src/com/android/server/wm/LockTaskControllerTest.java76
-rw-r--r--services/usage/java/com/android/server/usage/UsageStatsDatabase.java124
-rw-r--r--services/usage/java/com/android/server/usage/UsageStatsService.java56
-rw-r--r--services/usage/java/com/android/server/usage/UserUsageStatsService.java88
-rw-r--r--services/usb/java/com/android/server/usb/UsbAlsaManager.java54
-rw-r--r--services/voiceinteraction/java/com/android/server/voiceinteraction/VoiceInteractionSessionConnection.java2
-rwxr-xr-xtelephony/java/android/telephony/CarrierConfigManager.java10
-rw-r--r--telephony/java/android/telephony/TelephonyManager.java12
-rw-r--r--telephony/java/android/telephony/ims/ImsSsData.java2
-rw-r--r--telephony/java/com/android/internal/telephony/ITelephony.aidl12
-rw-r--r--tests/net/java/android/net/IpMemoryStoreTest.java277
-rw-r--r--tests/net/java/com/android/server/ConnectivityServiceTest.java3
-rw-r--r--tests/net/java/com/android/server/IpSecServiceParameterizedTest.java27
-rw-r--r--tests/net/java/com/android/server/net/ipmemorystore/NetworkAttributesTest.java2
-rwxr-xr-xtools/apilint/apilint147
-rw-r--r--tools/apilint/apilint.py53
-rw-r--r--tools/apilint/apilint_test.py18
491 files changed, 9332 insertions, 10277 deletions
diff --git a/cmds/incidentd/Android.bp b/cmds/incidentd/Android.bp
index 534a38f14136..25e0328b4f38 100644
--- a/cmds/incidentd/Android.bp
+++ b/cmds/incidentd/Android.bp
@@ -60,12 +60,6 @@ cc_binary {
"libservices",
"libutils",
"libprotobuf-cpp-lite",
- "libcrypto",
- "libkeystore_aidl",
- "libkeystore_binder",
- "libkeystore_parcelables",
- "android.hardware.keymaster@4.0",
- "libkeymaster4support",
],
static_libs: [
@@ -119,8 +113,6 @@ cc_test {
"src/incidentd_util.cpp",
"src/proto_util.cpp",
"src/report_directory.cpp",
- "src/cipher/IncidentKeyStore.cpp",
- "src/cipher/ProtoEncryption.cpp",
"src/**/*.proto",
],
@@ -142,12 +134,6 @@ cc_test {
"libprotoutil",
"libservices",
"libutils",
- "libcrypto",
- "libkeystore_aidl",
- "libkeystore_binder",
- "libkeystore_parcelables",
- "android.hardware.keymaster@4.0",
- "libkeymaster4support",
],
target: {
diff --git a/cmds/incidentd/src/Privacy.cpp b/cmds/incidentd/src/Privacy.cpp
index 0cc358fd2746..0a187e166135 100644
--- a/cmds/incidentd/src/Privacy.cpp
+++ b/cmds/incidentd/src/Privacy.cpp
@@ -28,8 +28,6 @@ namespace incidentd {
using namespace android::os;
using std::strstream;
-static const bool kEncryptionEnabled = false;
-
uint64_t encode_field_id(const Privacy* p) { return (uint64_t)p->type << 32 | p->field_id; }
string Privacy::toString() const {
@@ -52,10 +50,6 @@ const Privacy* lookup(const Privacy* p, uint32_t fieldId) {
return NULL;
}
-bool sectionEncryption(int section_id) {
- return kEncryptionEnabled ? (section_id == 3025) /*restricted image section*/ : false;
-}
-
static bool isAllowed(const uint8_t policy, const uint8_t check) {
switch (check) {
case PRIVACY_POLICY_LOCAL:
diff --git a/cmds/incidentd/src/Privacy.h b/cmds/incidentd/src/Privacy.h
index 9cde748bc44c..763edb03e485 100644
--- a/cmds/incidentd/src/Privacy.h
+++ b/cmds/incidentd/src/Privacy.h
@@ -90,9 +90,6 @@ private:
uint8_t mPolicy;
};
-// TODO: Add privacy flag in incident.proto and auto generate it inside Privacy.
-bool sectionEncryption(int section_id);
-
/**
* If a privacy policy is other than the defined values, update it to a real one.
*/
diff --git a/cmds/incidentd/src/PrivacyFilter.cpp b/cmds/incidentd/src/PrivacyFilter.cpp
index ca6fb3708ef1..d00ecdde5c63 100644
--- a/cmds/incidentd/src/PrivacyFilter.cpp
+++ b/cmds/incidentd/src/PrivacyFilter.cpp
@@ -16,20 +16,19 @@
#define DEBUG false
#include "Log.h"
+#include "incidentd_util.h"
#include "PrivacyFilter.h"
+#include "proto_util.h"
#include "incidentd_util.h"
#include "proto_util.h"
#include "Section.h"
#include <android-base/file.h>
-#include <android/util/ProtoFileReader.h>
#include <android/util/protobuf.h>
+#include <android/util/ProtoFileReader.h>
#include <log/log.h>
-#include "cipher/IncidentKeyStore.h"
-#include "cipher/ProtoEncryption.h"
-
namespace android {
namespace os {
namespace incidentd {
@@ -146,8 +145,6 @@ public:
*/
status_t writeData(int fd);
- sp<ProtoReader> getData() { return mData; }
-
private:
/**
* The global set of field --> required privacy level mapping.
@@ -259,47 +256,8 @@ void PrivacyFilter::addFd(const sp<FilterFd>& output) {
mOutputs.push_back(output);
}
-static void write_section_to_file(int sectionId, FieldStripper& fieldStripper, sp<FilterFd> output,
- bool encryptIfNeeded) {
- status_t err;
-
- if (sectionEncryption(sectionId) && encryptIfNeeded) {
- ProtoEncryptor encryptor(fieldStripper.getData());
- size_t encryptedSize = encryptor.encrypt();
-
- if (encryptedSize <= 0) {
- output->onWriteError(BAD_VALUE);
- return;
- }
- err = write_section_header(output->getFd(), sectionId, encryptedSize);
- VLOG("Encrypted: write section header size %lu", (unsigned long)encryptedSize);
-
- encryptor.flush(output->getFd());
-
- if (err != NO_ERROR) {
- output->onWriteError(err);
- return;
- }
- } else {
- err = write_section_header(output->getFd(), sectionId, fieldStripper.dataSize());
- VLOG("No encryption: write section header size %lu",
- (unsigned long)fieldStripper.dataSize());
-
- if (err != NO_ERROR) {
- output->onWriteError(err);
- return;
- }
-
- err = fieldStripper.writeData(output->getFd());
- if (err != NO_ERROR) {
- output->onWriteError(err);
- return;
- }
- }
-}
-
-status_t PrivacyFilter::writeData(const FdBuffer& buffer, uint8_t bufferLevel, size_t* maxSize,
- bool encryptIfNeeded) {
+status_t PrivacyFilter::writeData(const FdBuffer& buffer, uint8_t bufferLevel,
+ size_t* maxSize) {
status_t err;
if (maxSize != NULL) {
@@ -309,9 +267,9 @@ status_t PrivacyFilter::writeData(const FdBuffer& buffer, uint8_t bufferLevel, s
// Order the writes by privacy filter, with increasing levels of filtration,k
// so we can do the filter once, and then write many times.
sort(mOutputs.begin(), mOutputs.end(),
- [](const sp<FilterFd>& a, const sp<FilterFd>& b) -> bool {
- return a->getPrivacyPolicy() < b->getPrivacyPolicy();
- });
+ [](const sp<FilterFd>& a, const sp<FilterFd>& b) -> bool {
+ return a->getPrivacyPolicy() < b->getPrivacyPolicy();
+ });
uint8_t privacyPolicy = PRIVACY_POLICY_LOCAL; // a.k.a. no filtering
FieldStripper fieldStripper(mRestrictions, buffer.data()->read(), bufferLevel);
@@ -330,7 +288,17 @@ status_t PrivacyFilter::writeData(const FdBuffer& buffer, uint8_t bufferLevel, s
// Write the resultant buffer to the fd, along with the header.
ssize_t dataSize = fieldStripper.dataSize();
if (dataSize > 0) {
- write_section_to_file(mSectionId, fieldStripper, output, encryptIfNeeded);
+ err = write_section_header(output->getFd(), mSectionId, dataSize);
+ if (err != NO_ERROR) {
+ output->onWriteError(err);
+ continue;
+ }
+
+ err = fieldStripper.writeData(output->getFd());
+ if (err != NO_ERROR) {
+ output->onWriteError(err);
+ continue;
+ }
}
if (maxSize != NULL) {
@@ -382,18 +350,8 @@ status_t filter_and_write_report(int to, int from, uint8_t bufferLevel,
// Read this section from the reader into an FdBuffer
size_t sectionSize = reader->readRawVarint();
-
FdBuffer sectionData;
-
- // Write data to FdBuffer, if the section was encrypted, decrypt first.
- if (sectionEncryption(fieldId)) {
- VLOG("sectionSize %lu", (unsigned long)sectionSize);
- ProtoDecryptor decryptor(reader, sectionSize);
- err = decryptor.decryptAndFlush(&sectionData);
- } else {
- err = sectionData.write(reader, sectionSize);
- }
-
+ err = sectionData.write(reader, sectionSize);
if (err != NO_ERROR) {
ALOGW("filter_and_write_report FdBuffer.write failed (this shouldn't happen): %s",
strerror(-err));
@@ -401,8 +359,7 @@ status_t filter_and_write_report(int to, int from, uint8_t bufferLevel,
}
// Do the filter and write.
- err = filter.writeData(sectionData, bufferLevel, nullptr,
- false /* do not encrypt again*/);
+ err = filter.writeData(sectionData, bufferLevel, nullptr);
if (err != NO_ERROR) {
ALOGW("filter_and_write_report filter.writeData had an error: %s", strerror(-err));
return err;
@@ -411,7 +368,6 @@ status_t filter_and_write_report(int to, int from, uint8_t bufferLevel,
// We don't need this field. Incident does not have any direct children
// other than sections. So just skip them.
write_field_or_skip(NULL, reader, fieldTag, true);
- VLOG("Skip this.... section %d", fieldId);
}
}
diff --git a/cmds/incidentd/src/PrivacyFilter.h b/cmds/incidentd/src/PrivacyFilter.h
index d426db966a9a..76b28498a0ac 100644
--- a/cmds/incidentd/src/PrivacyFilter.h
+++ b/cmds/incidentd/src/PrivacyFilter.h
@@ -82,14 +82,8 @@ public:
* was written (i.e. after filtering).
*
* The buffer is assumed to have already been filtered to bufferLevel.
- *
- * This function can be called when persisting data to disk or when sending
- * data to client. In the former case, we need to encrypt the data when that
- * section requires encryption. In the latter case, we shouldn't send the
- * unencrypted data to client.
*/
- status_t writeData(const FdBuffer& buffer, uint8_t bufferLevel, size_t* maxSize,
- bool encryptIfNeeded);
+ status_t writeData(const FdBuffer& buffer, uint8_t bufferLevel, size_t* maxSize);
private:
int mSectionId;
diff --git a/cmds/incidentd/src/Reporter.cpp b/cmds/incidentd/src/Reporter.cpp
index dc4065bce39b..02b6bbe6c9b1 100644
--- a/cmds/incidentd/src/Reporter.cpp
+++ b/cmds/incidentd/src/Reporter.cpp
@@ -465,8 +465,7 @@ status_t ReportWriter::writeSection(const FdBuffer& buffer) {
}
});
- return filter.writeData(buffer, PRIVACY_POLICY_LOCAL, &mMaxSectionDataFilteredSize,
- true /*encrypt if needed*/);
+ return filter.writeData(buffer, PRIVACY_POLICY_LOCAL, &mMaxSectionDataFilteredSize);
}
diff --git a/cmds/incidentd/src/cipher/IncidentKeyStore.cpp b/cmds/incidentd/src/cipher/IncidentKeyStore.cpp
deleted file mode 100644
index ae0a92094d0b..000000000000
--- a/cmds/incidentd/src/cipher/IncidentKeyStore.cpp
+++ /dev/null
@@ -1,87 +0,0 @@
-/*
- * Copyright (C) 2019 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "Log.h"
-
-#include "IncidentKeyStore.h"
-
-#include <sys/stat.h>
-
-static constexpr size_t AES_KEY_BYTES = 32;
-static constexpr size_t GCM_MAC_BYTES = 16;
-constexpr char kKeyname[] = "IncidentKey";
-
-namespace android {
-namespace os {
-namespace incidentd {
-
-using namespace keystore;
-using std::string;
-
-IncidentKeyStore& IncidentKeyStore::getInstance() {
- static IncidentKeyStore sInstance(new keystore::KeystoreClientImpl);
- return sInstance;
-}
-
-bool IncidentKeyStore::encrypt(const string& data, int32_t flags, string* output) {
- std::lock_guard<std::mutex> lock(mMutex);
- if (data.empty()) {
- ALOGW("IncidentKeyStore: Encrypt empty data?!");
- return false;
- }
- if (!mClient->doesKeyExist(kKeyname)) {
- auto gen_result = generateKeyLocked(kKeyname, 0);
- if (!gen_result.isOk()) {
- ALOGE("IncidentKeyStore: Key generate failed.");
- return false;
- }
- }
- if (!mClient->encryptWithAuthentication(kKeyname, data, flags, output)) {
- ALOGE("IncidentKeyStore: Encryption failed.");
- return false;
- }
- return true;
-}
-
-bool IncidentKeyStore::decrypt(const std::string& input, string* output) {
- std::lock_guard<std::mutex> lock(mMutex);
- if (input.empty()) {
- ALOGE("IncidentKeyStore: Decrypt empty input?");
- return false;
- }
- if (!mClient->decryptWithAuthentication(kKeyname, input, output)) {
- ALOGE("IncidentKeyStore: Decryption failed.");
- return false;
- }
- return true;
-}
-
-KeyStoreNativeReturnCode IncidentKeyStore::generateKeyLocked(const std::string& name,
- int32_t flags) {
- auto paramBuilder = AuthorizationSetBuilder()
- .AesEncryptionKey(AES_KEY_BYTES * 8)
- .GcmModeMinMacLen(GCM_MAC_BYTES * 8)
- .Authorization(TAG_NO_AUTH_REQUIRED);
-
- AuthorizationSet hardware_enforced_characteristics;
- AuthorizationSet software_enforced_characteristics;
- return mClient->generateKey(name, paramBuilder, flags, &hardware_enforced_characteristics,
- &software_enforced_characteristics);
-}
-
-} // namespace incidentd
-} // namespace os
-} // namespace android
diff --git a/cmds/incidentd/src/cipher/IncidentKeyStore.h b/cmds/incidentd/src/cipher/IncidentKeyStore.h
deleted file mode 100644
index 27611cd7faad..000000000000
--- a/cmds/incidentd/src/cipher/IncidentKeyStore.h
+++ /dev/null
@@ -1,53 +0,0 @@
-/*
- * Copyright (C) 2019 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-#pragma once
-
-#include <keystore/keystore_client_impl.h>
-
-namespace android {
-namespace os {
-namespace incidentd {
-
-class IncidentKeyStore {
-public:
- static IncidentKeyStore& getInstance();
-
- IncidentKeyStore(keystore::KeystoreClient* client) : mClient(client) {}
-
- /**
- * Encrypt the plainText and output the encrypted message.
- *
- * Returns true on success and false otherwise.
- * If the key has not been created yet, it will generate the key in KeyMaster.
- */
- bool encrypt(const std::string& plainText, int32_t flags, std::string* output);
-
- /**
- * Decrypt and output the decrypted message.
- *
- * Returns true on success and false otherwise.
- */
- bool decrypt(const std::string& encryptedData, std::string* output);
-
-private:
- std::unique_ptr<keystore::KeystoreClient> mClient;
- std::mutex mMutex;
- keystore::KeyStoreNativeReturnCode generateKeyLocked(const std::string& name, int32_t flags);
-};
-
-} // namespace incidentd
-} // namespace os
-} // namespace android
diff --git a/cmds/incidentd/src/cipher/ProtoEncryption.cpp b/cmds/incidentd/src/cipher/ProtoEncryption.cpp
deleted file mode 100644
index 493796d2af4d..000000000000
--- a/cmds/incidentd/src/cipher/ProtoEncryption.cpp
+++ /dev/null
@@ -1,139 +0,0 @@
-/*
- * Copyright (C) 2019 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#define DEBUG true // STOPSHIP if true
-#include "Log.h"
-
-#include "ProtoEncryption.h"
-
-#include <android/util/protobuf.h>
-
-#include "IncidentKeyStore.h"
-
-namespace android {
-namespace os {
-namespace incidentd {
-
-using android::util::FIELD_COUNT_REPEATED;
-using android::util::FIELD_TYPE_STRING;
-using android::util::ProtoOutputStream;
-using android::util::ProtoReader;
-using std::string;
-
-static const int FIELD_ID_BLOCK = 1;
-
-size_t ProtoEncryptor::encrypt() {
- string block;
- int i = 0;
- // Read at most sBlockSize at a time and encrypt.
- while (mReader->readBuffer() != NULL) {
- size_t readBytes =
- mReader->currentToRead() > sBlockSize ? sBlockSize : mReader->currentToRead();
- block.resize(readBytes);
- std::memcpy(block.data(), mReader->readBuffer(), readBytes);
-
- string encrypted;
- if (IncidentKeyStore::getInstance().encrypt(block, 0, &encrypted)) {
- mOutputStream.write(FIELD_TYPE_STRING | FIELD_ID_BLOCK | FIELD_COUNT_REPEATED,
- encrypted);
- VLOG("Block %d Encryption: original %lld now %lld", i++, (long long)readBytes,
- (long long)encrypted.length());
- mReader->move(readBytes);
- } else {
- return 0;
- }
- }
- return mOutputStream.size();
-}
-
-status_t ProtoEncryptor::flush(int fd) {
- if (!mOutputStream.flush(fd)) {
- return BAD_VALUE;
- }
- return NO_ERROR;
-}
-
-status_t ProtoDecryptor::readOneBlock(string* output) {
- if (!mReader->hasNext()) {
- return NO_ERROR;
- }
- uint64_t fieldTag = mReader->readRawVarint();
- uint32_t fieldId = read_field_id(fieldTag);
- uint8_t wireType = read_wire_type(fieldTag);
- if (wireType == WIRE_TYPE_LENGTH_DELIMITED) {
- // Read this section from the reader into an FdBuffer
- size_t sectionSize = mReader->readRawVarint();
- output->resize(sectionSize);
- size_t pos = 0;
- while (pos < sectionSize && mReader->readBuffer() != NULL) {
- size_t toRead = (sectionSize - pos) > mReader->currentToRead()
- ? mReader->currentToRead()
- : (sectionSize - pos);
- std::memcpy(&((output->data())[pos]), mReader->readBuffer(), toRead);
- pos += toRead;
- mReader->move(toRead);
- }
- if (pos != sectionSize) {
- return BAD_VALUE;
- ALOGE("Failed to read one block");
- }
- } else {
- return BAD_VALUE;
- }
- return NO_ERROR;
-}
-
-status_t ProtoDecryptor::decryptAndFlush(FdBuffer* out) {
- size_t mStartBytes = mReader->bytesRead();
- size_t bytesRead = 0;
- int i = 0;
- status_t err = NO_ERROR;
- // Let's read until we read mTotalSize. If any error occurs before that, make sure to move the
- // read pointer so the caller can continue to read the following sections.
- while (bytesRead < mTotalSize) {
- string block;
- err = readOneBlock(&block);
- bytesRead = mReader->bytesRead() - mStartBytes;
-
- if (err != NO_ERROR) {
- break;
- }
-
- if (block.length() == 0) {
- VLOG("Done reading all blocks");
- break;
- }
-
- string decryptedBlock;
- if ((IncidentKeyStore::getInstance()).decrypt(block, &decryptedBlock)) {
- VLOG("Block %d Original Size %lu Decrypted size %lu", i++,
- (unsigned long)block.length(), (unsigned long)decryptedBlock.length());
- out->write(reinterpret_cast<uint8_t*>(decryptedBlock.data()), decryptedBlock.length());
- } else {
- err = BAD_VALUE;
- break;
- }
- }
-
- if (bytesRead < mTotalSize) {
- mReader->move(mTotalSize - bytesRead);
- }
- return err;
-}
-
-} // namespace incidentd
-} // namespace os
-} // namespace android
diff --git a/cmds/incidentd/src/cipher/ProtoEncryption.h b/cmds/incidentd/src/cipher/ProtoEncryption.h
deleted file mode 100644
index 5b72ca88ec64..000000000000
--- a/cmds/incidentd/src/cipher/ProtoEncryption.h
+++ /dev/null
@@ -1,80 +0,0 @@
-/*
- * Copyright (C) 2019 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-#pragma once
-
-#include <android/util/ProtoOutputStream.h>
-#include <android/util/ProtoReader.h>
-#include <frameworks/base/cmds/incidentd/src/cipher/cipher_blocks.pb.h>
-
-#include "FdBuffer.h"
-
-namespace android {
-namespace os {
-namespace incidentd {
-
-// PlainText IncidentReport format
-// [section1_header(id, size, type)][section1_data] ...
-
-// Let's say section1 needs encryption
-// After encryption, it becomes
-// [section1_header(id, encrypted_size, type)][[cipher_block][cipher_block][cipher_block]..]
-
-// When clients read the report, it's decrypted, and written in its original format
-
-/**
- * Takes a ProtoReader, encrypts its whole content -- which is one section, and flush to
- * a file descriptor.
- * The underlying encryption is done using Keystore binder APIs. We encrypt the data
- * in blocks, and write to the file in android.os.incidentd.CipherBlocks format.
- */
-class ProtoEncryptor {
-public:
- ProtoEncryptor(const sp<android::util::ProtoReader>& reader) : mReader(reader){};
-
- // Encrypt the data from ProtoReader, and store in CipherBlocks format.
- // return the size of CipherBlocks.
- size_t encrypt();
-
- status_t flush(int fd);
-
-private:
- static const size_t sBlockSize = 8 * 1024;
- const sp<android::util::ProtoReader> mReader;
- android::util::ProtoOutputStream mOutputStream;
-};
-
-// Read data from ProtoReader, which is in CipherBlocks proto format. Parse and decrypt
-// block by block.
-class ProtoDecryptor {
-public:
- ProtoDecryptor(const sp<android::util::ProtoReader>& reader, size_t size)
- : mReader(reader), mTotalSize(size){};
- status_t decryptAndFlush(FdBuffer* out);
-
-private:
- const sp<android::util::ProtoReader> mReader;
-
- // Total size in bytes we should read from ProtoReader.
- const size_t mTotalSize;
-
- // Read one cipher block from ProtoReader, instead of reading the whole content
- // and parse to CipherBlocks which could be huge.
- status_t readOneBlock(std::string* output);
-};
-
-} // namespace incidentd
-} // namespace os
-} // namespace android
diff --git a/cmds/incidentd/tests/IncidentKeyStore_test.cpp b/cmds/incidentd/tests/IncidentKeyStore_test.cpp
deleted file mode 100644
index 2250fda90e01..000000000000
--- a/cmds/incidentd/tests/IncidentKeyStore_test.cpp
+++ /dev/null
@@ -1,66 +0,0 @@
-/*
- * Copyright (C) 2019 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "cipher/IncidentKeyStore.h"
-
-#include <binder/ProcessState.h>
-#include <gtest/gtest.h>
-
-#include <fstream>
-
-using namespace android::os::incidentd;
-
-class IncidentKeyStoreTest : public ::testing::Test {
-protected:
- std::unique_ptr<IncidentKeyStore> incidentKeyStore;
- void SetUp() override {
- android::ProcessState::self()->startThreadPool();
- incidentKeyStore = std::make_unique<IncidentKeyStore>(
- static_cast<keystore::KeystoreClient*>(new keystore::KeystoreClientImpl));
- };
- void TearDown() override { incidentKeyStore = nullptr; };
-};
-
-TEST_F(IncidentKeyStoreTest, test_encrypt_decrypt) {
- std::string plaintext;
- plaintext.resize(4 * 1024, 'a');
-
- std::string encrypted;
- EXPECT_TRUE(incidentKeyStore->encrypt(plaintext, 0, &encrypted));
- std::string decrypted;
- EXPECT_TRUE(incidentKeyStore->decrypt(encrypted, &decrypted));
-
- EXPECT_FALSE(encrypted.empty());
- EXPECT_EQ(plaintext, decrypted);
-}
-
-TEST_F(IncidentKeyStoreTest, test_encrypt_empty_hash) {
- std::string hash = "";
-
- std::string encrypted;
- EXPECT_FALSE(incidentKeyStore->encrypt(hash, 0, &encrypted));
-
- EXPECT_TRUE(encrypted.empty());
-}
-
-TEST_F(IncidentKeyStoreTest, test_decrypt_empty_hash) {
- std::string hash = "";
-
- std::string decrypted;
- EXPECT_FALSE(incidentKeyStore->decrypt(hash, &decrypted));
-
- EXPECT_TRUE(decrypted.empty());
-} \ No newline at end of file
diff --git a/cmds/incidentd/tests/ProtoEncryption_test.cpp b/cmds/incidentd/tests/ProtoEncryption_test.cpp
deleted file mode 100644
index 6742e034d70d..000000000000
--- a/cmds/incidentd/tests/ProtoEncryption_test.cpp
+++ /dev/null
@@ -1,85 +0,0 @@
-/*
- * Copyright (C) 2019 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#include "Log.h"
-
-#include "cipher/ProtoEncryption.h"
-
-#include <android-base/file.h>
-#include <gtest/gtest.h>
-
-#include "FdBuffer.h"
-#include "android/util/ProtoFileReader.h"
-
-using namespace android::os::incidentd;
-using android::sp;
-using std::string;
-using ::testing::Test;
-
-const std::string kTestPath = GetExecutableDirectory();
-const std::string kTestDataPath = kTestPath + "/testdata/";
-
-TEST(ProtoEncryptionTest, test_encrypt_decrypt) {
- const std::string plaintextFile = kTestDataPath + "plaintext.txt";
- const std::string encryptedFile = kTestDataPath + "encrypted.txt";
- size_t msg1Size = 20 * 1024;
-
- // Create a file with plain text.
- {
- unique_fd fd(
- open(plaintextFile.c_str(), O_WRONLY | O_CREAT | O_CLOEXEC, S_IRUSR | S_IWUSR));
- ASSERT_NE(fd.get(), -1);
- string content;
- content.resize(msg1Size, 'a');
- WriteFully(fd, content.data(), msg1Size);
- }
-
- // Read the plain text and encrypted
- {
- unique_fd readFd(open(plaintextFile.c_str(), O_RDONLY | O_CLOEXEC));
- unique_fd encryptedFd(
- open(encryptedFile.c_str(), O_WRONLY | O_CREAT | O_CLOEXEC, S_IRUSR | S_IWUSR));
-
- ASSERT_NE(readFd.get(), -1);
- ASSERT_NE(encryptedFd.get(), -1);
-
- sp<ProtoFileReader> reader = new ProtoFileReader(readFd.get());
- ProtoEncryptor encryptor(reader);
- EXPECT_TRUE(encryptor.encrypt() > msg1Size);
-
- encryptor.flush(encryptedFd.get());
- }
-
- // Read the encrypted file, and decrypt
- unique_fd encryptedFd(open(encryptedFile.c_str(), O_RDONLY | O_CLOEXEC));
- ASSERT_NE(encryptedFd.get(), -1);
- FdBuffer output;
- sp<ProtoFileReader> reader2 = new ProtoFileReader(encryptedFd.get());
- ProtoDecryptor decryptor(reader2, reader2->size());
- decryptor.decryptAndFlush(&output);
-
- auto decryptedReader = output.data()->read();
-
- // Check the content.
- int count = 0;
- while (decryptedReader->hasNext()) {
- if (decryptedReader->next() == 'a') {
- count++;
- }
- }
-
- EXPECT_EQ(msg1Size, count);
-} \ No newline at end of file
diff --git a/cmds/screencap/screencap.cpp b/cmds/screencap/screencap.cpp
index c4976675dc04..0bb1af13643c 100644
--- a/cmds/screencap/screencap.cpp
+++ b/cmds/screencap/screencap.cpp
@@ -86,20 +86,6 @@ static sk_sp<SkColorSpace> dataSpaceToColorSpace(ui::Dataspace d)
}
}
-static ui::Dataspace pickBestDataspace(ui::ColorMode colorMode)
-{
- switch (colorMode) {
- case ui::ColorMode::SRGB:
- return ui::Dataspace::V0_SRGB;
- case ui::ColorMode::DISPLAY_P3:
- case ui::ColorMode::BT2100_PQ:
- case ui::ColorMode::BT2100_HLG:
- return ui::Dataspace::DISPLAY_P3;
- default:
- return ui::Dataspace::V0_SRGB;
- }
-}
-
static uint32_t dataSpaceToInt(ui::Dataspace d)
{
switch (d) {
@@ -181,14 +167,6 @@ int main(int argc, char** argv)
uint32_t w, s, h, f;
size_t size = 0;
- // Maps orientations from DisplayInfo to ISurfaceComposer
- static const uint32_t ORIENTATION_MAP[] = {
- ISurfaceComposer::eRotateNone, // 0 == DISPLAY_ORIENTATION_0
- ISurfaceComposer::eRotate270, // 1 == DISPLAY_ORIENTATION_90
- ISurfaceComposer::eRotate180, // 2 == DISPLAY_ORIENTATION_180
- ISurfaceComposer::eRotate90, // 3 == DISPLAY_ORIENTATION_270
- };
-
// setThreadPoolMaxThreadCount(0) actually tells the kernel it's
// not allowed to spawn any additional threads, but we still spawn
// a binder thread from userspace when we call startThreadPool().
@@ -196,34 +174,10 @@ int main(int argc, char** argv)
ProcessState::self()->setThreadPoolMaxThreadCount(0);
ProcessState::self()->startThreadPool();
- const sp<IBinder> display = SurfaceComposerClient::getPhysicalDisplayToken(*displayId);
- if (display == nullptr) {
- fprintf(stderr, "Failed to get token for invalid display %"
- ANDROID_PHYSICAL_DISPLAY_ID_FORMAT "\n", *displayId);
- return 1;
- }
-
- Vector<DisplayInfo> configs;
- SurfaceComposerClient::getDisplayConfigs(display, &configs);
- int activeConfig = SurfaceComposerClient::getActiveConfig(display);
- if (static_cast<size_t>(activeConfig) >= configs.size()) {
- fprintf(stderr, "Active config %d not inside configs (size %zu)\n",
- activeConfig, configs.size());
- return 1;
- }
- uint8_t displayOrientation = configs[activeConfig].orientation;
- uint32_t captureOrientation = ORIENTATION_MAP[displayOrientation];
-
+ ui::Dataspace outDataspace;
sp<GraphicBuffer> outBuffer;
- ui::Dataspace reqDataspace =
- pickBestDataspace(SurfaceComposerClient::getActiveColorMode(display));
- // Due to the fact that we hard code the way we write pixels into screenshot,
- // we hard code RGBA_8888 here.
- ui::PixelFormat reqPixelFormat = ui::PixelFormat::RGBA_8888;
- status_t result = ScreenshotClient::capture(display, reqDataspace, reqPixelFormat, Rect(),
- 0 /* reqWidth */, 0 /* reqHeight */, false,
- captureOrientation, &outBuffer);
+ status_t result = ScreenshotClient::capture(*displayId, &outDataspace, &outBuffer);
if (result != NO_ERROR) {
close(fd);
return 1;
@@ -233,10 +187,10 @@ int main(int argc, char** argv)
if (base == nullptr || result != NO_ERROR) {
String8 reason;
- if (base == nullptr) {
- reason = "Failed to write to buffer";
+ if (result != NO_ERROR) {
+ reason.appendFormat(" Error Code: %d", result);
} else {
- reason.appendFormat("Error Code: %d", result);
+ reason = "Failed to write to buffer";
}
fprintf(stderr, "Failed to take screenshot (%s)\n", reason.c_str());
close(fd);
@@ -252,7 +206,7 @@ int main(int argc, char** argv)
if (png) {
const SkImageInfo info =
SkImageInfo::Make(w, h, flinger2skia(f), kPremul_SkAlphaType,
- dataSpaceToColorSpace(reqDataspace));
+ dataSpaceToColorSpace(outDataspace));
SkPixmap pixmap(info, base, s * bytesPerPixel(f));
struct FDWStream final : public SkWStream {
size_t fBytesWritten = 0;
@@ -269,7 +223,7 @@ int main(int argc, char** argv)
notifyMediaScanner(fn);
}
} else {
- uint32_t c = dataSpaceToInt(reqDataspace);
+ uint32_t c = dataSpaceToInt(outDataspace);
write(fd, &w, 4);
write(fd, &h, 4);
write(fd, &f, 4);
diff --git a/cmds/statsd/src/atoms.proto b/cmds/statsd/src/atoms.proto
index 033dbf7aa4a5..84bb11f54d0d 100644
--- a/cmds/statsd/src/atoms.proto
+++ b/cmds/statsd/src/atoms.proto
@@ -6140,6 +6140,12 @@ message GpuStatsGlobalInfo {
// Api version of the system GLES driver.
optional int32 gles_version = 11;
+
+ // Total count of the angle driver gets loaded.
+ optional int64 angle_loading_count = 12;
+
+ // Total count of the angle driver fails to be loaded.
+ optional int64 angle_loading_failure_count = 13;
}
/**
@@ -6172,6 +6178,10 @@ message GpuStatsAppInfo {
// Vulkan driver loading time info.
optional GpuDriverLoadingTime vk_driver_loading_time = 4
[(android.os.statsd.log_mode) = MODE_BYTES];
+
+ // Angle driver loading time info.
+ optional GpuDriverLoadingTime angle_driver_loading_time = 5
+ [(android.os.statsd.log_mode) = MODE_BYTES];
}
/*
diff --git a/cmds/statsd/src/external/GpuStatsPuller.cpp b/cmds/statsd/src/external/GpuStatsPuller.cpp
index 876383c16863..f727d6d6f79e 100644
--- a/cmds/statsd/src/external/GpuStatsPuller.cpp
+++ b/cmds/statsd/src/external/GpuStatsPuller.cpp
@@ -68,6 +68,8 @@ static bool pullGpuStatsGlobalInfo(const sp<IGpuService>& gpuService,
if (!event->write(info.vulkanVersion)) return false;
if (!event->write(info.cpuVulkanVersion)) return false;
if (!event->write(info.glesVersion)) return false;
+ if (!event->write((int64_t)info.angleLoadingCount)) return false;
+ if (!event->write((int64_t)info.angleLoadingFailureCount)) return false;
event->init();
data->emplace_back(event);
}
@@ -92,6 +94,7 @@ static bool pullGpuStatsAppInfo(const sp<IGpuService>& gpuService,
if (!event->write((int64_t)info.driverVersionCode)) return false;
if (!event->write(int64VectorToProtoByteString(info.glDriverLoadingTime))) return false;
if (!event->write(int64VectorToProtoByteString(info.vkDriverLoadingTime))) return false;
+ if (!event->write(int64VectorToProtoByteString(info.angleDriverLoadingTime))) return false;
event->init();
data->emplace_back(event);
}
diff --git a/cmds/statsd/tests/external/GpuStatsPuller_test.cpp b/cmds/statsd/tests/external/GpuStatsPuller_test.cpp
index 2acfb8354905..63fb4edd36e7 100644
--- a/cmds/statsd/tests/external/GpuStatsPuller_test.cpp
+++ b/cmds/statsd/tests/external/GpuStatsPuller_test.cpp
@@ -32,27 +32,31 @@ namespace os {
namespace statsd {
// clang-format off
-static const std::string DRIVER_PACKAGE_NAME = "TEST_DRIVER";
-static const std::string DRIVER_VERSION_NAME = "TEST_DRIVER_VERSION";
-static const std::string APP_PACKAGE_NAME = "TEST_APP";
-static const int64_t TIMESTAMP_WALLCLOCK = 111;
-static const int64_t TIMESTAMP_ELAPSED = 222;
-static const int64_t DRIVER_VERSION_CODE = 333;
-static const int64_t DRIVER_BUILD_TIME = 444;
-static const int64_t GL_LOADING_COUNT = 3;
-static const int64_t GL_LOADING_FAILURE_COUNT = 1;
-static const int64_t VK_LOADING_COUNT = 4;
-static const int64_t VK_LOADING_FAILURE_COUNT = 0;
-static const int64_t GL_DRIVER_LOADING_TIME_0 = 555;
-static const int64_t GL_DRIVER_LOADING_TIME_1 = 666;
-static const int64_t VK_DRIVER_LOADING_TIME_0 = 777;
-static const int64_t VK_DRIVER_LOADING_TIME_1 = 888;
-static const int64_t VK_DRIVER_LOADING_TIME_2 = 999;
-static const int32_t VULKAN_VERSION = 1;
-static const int32_t CPU_VULKAN_VERSION = 2;
-static const int32_t GLES_VERSION = 3;
-static const size_t NUMBER_OF_VALUES_GLOBAL = 11;
-static const size_t NUMBER_OF_VALUES_APP = 4;
+static const std::string DRIVER_PACKAGE_NAME = "TEST_DRIVER";
+static const std::string DRIVER_VERSION_NAME = "TEST_DRIVER_VERSION";
+static const std::string APP_PACKAGE_NAME = "TEST_APP";
+static const int64_t TIMESTAMP_WALLCLOCK = 111;
+static const int64_t TIMESTAMP_ELAPSED = 222;
+static const int64_t DRIVER_VERSION_CODE = 333;
+static const int64_t DRIVER_BUILD_TIME = 444;
+static const int64_t GL_LOADING_COUNT = 3;
+static const int64_t GL_LOADING_FAILURE_COUNT = 1;
+static const int64_t VK_LOADING_COUNT = 4;
+static const int64_t VK_LOADING_FAILURE_COUNT = 0;
+static const int64_t ANGLE_LOADING_COUNT = 2;
+static const int64_t ANGLE_LOADING_FAILURE_COUNT = 1;
+static const int64_t GL_DRIVER_LOADING_TIME_0 = 555;
+static const int64_t GL_DRIVER_LOADING_TIME_1 = 666;
+static const int64_t VK_DRIVER_LOADING_TIME_0 = 777;
+static const int64_t VK_DRIVER_LOADING_TIME_1 = 888;
+static const int64_t VK_DRIVER_LOADING_TIME_2 = 999;
+static const int64_t ANGLE_DRIVER_LOADING_TIME_0 = 1010;
+static const int64_t ANGLE_DRIVER_LOADING_TIME_1 = 1111;
+static const int32_t VULKAN_VERSION = 1;
+static const int32_t CPU_VULKAN_VERSION = 2;
+static const int32_t GLES_VERSION = 3;
+static const size_t NUMBER_OF_VALUES_GLOBAL = 13;
+static const size_t NUMBER_OF_VALUES_APP = 5;
// clang-format on
class MockGpuStatsPuller : public GpuStatsPuller {
@@ -99,6 +103,8 @@ TEST_F(GpuStatsPuller_test, PullGpuStatsGlobalInfo) {
EXPECT_TRUE(event->write(VULKAN_VERSION));
EXPECT_TRUE(event->write(CPU_VULKAN_VERSION));
EXPECT_TRUE(event->write(GLES_VERSION));
+ EXPECT_TRUE(event->write(ANGLE_LOADING_COUNT));
+ EXPECT_TRUE(event->write(ANGLE_LOADING_FAILURE_COUNT));
event->init();
inData.emplace_back(event);
MockGpuStatsPuller mockPuller(android::util::GPU_STATS_GLOBAL_INFO, &inData);
@@ -119,6 +125,8 @@ TEST_F(GpuStatsPuller_test, PullGpuStatsGlobalInfo) {
EXPECT_EQ(VULKAN_VERSION, outData[0]->getValues()[8].mValue.int_value);
EXPECT_EQ(CPU_VULKAN_VERSION, outData[0]->getValues()[9].mValue.int_value);
EXPECT_EQ(GLES_VERSION, outData[0]->getValues()[10].mValue.int_value);
+ EXPECT_EQ(ANGLE_LOADING_COUNT, outData[0]->getValues()[11].mValue.long_value);
+ EXPECT_EQ(ANGLE_LOADING_FAILURE_COUNT, outData[0]->getValues()[12].mValue.long_value);
}
TEST_F(GpuStatsPuller_test, PullGpuStatsAppInfo) {
@@ -134,8 +142,12 @@ TEST_F(GpuStatsPuller_test, PullGpuStatsAppInfo) {
vkDriverLoadingTime.emplace_back(VK_DRIVER_LOADING_TIME_0);
vkDriverLoadingTime.emplace_back(VK_DRIVER_LOADING_TIME_1);
vkDriverLoadingTime.emplace_back(VK_DRIVER_LOADING_TIME_2);
+ std::vector<int64_t> angleDriverLoadingTime;
+ angleDriverLoadingTime.emplace_back(ANGLE_DRIVER_LOADING_TIME_0);
+ angleDriverLoadingTime.emplace_back(ANGLE_DRIVER_LOADING_TIME_1);
EXPECT_TRUE(event->write(int64VectorToProtoByteString(glDriverLoadingTime)));
EXPECT_TRUE(event->write(int64VectorToProtoByteString(vkDriverLoadingTime)));
+ EXPECT_TRUE(event->write(int64VectorToProtoByteString(angleDriverLoadingTime)));
event->init();
inData.emplace_back(event);
MockGpuStatsPuller mockPuller(android::util::GPU_STATS_APP_INFO, &inData);
@@ -151,6 +163,8 @@ TEST_F(GpuStatsPuller_test, PullGpuStatsAppInfo) {
outData[0]->getValues()[2].mValue.str_value);
EXPECT_EQ(int64VectorToProtoByteString(vkDriverLoadingTime),
outData[0]->getValues()[3].mValue.str_value);
+ EXPECT_EQ(int64VectorToProtoByteString(angleDriverLoadingTime),
+ outData[0]->getValues()[4].mValue.str_value);
}
} // namespace statsd
diff --git a/config/boot-image-profile.txt b/config/boot-image-profile.txt
index 8c2b59df3b57..09a854662740 100644
--- a/config/boot-image-profile.txt
+++ b/config/boot-image-profile.txt
@@ -9193,13 +9193,6 @@ HPLandroid/media/MediaMetadata$Builder;-><init>(Landroid/media/MediaMetadata;)V
HSPLandroid/media/MediaMetadata$Builder;->build()Landroid/media/MediaMetadata;
HPLandroid/media/MediaMetadata;->size()I
HSPLandroid/media/MediaMetadata;->writeToParcel(Landroid/os/Parcel;I)V
-HSPLandroid/media/MediaParceledListSlice$2;-><init>()V
-HSPLandroid/media/MediaParceledListSlice$2;->createFromParcel(Landroid/os/Parcel;)Landroid/media/MediaParceledListSlice;
-HSPLandroid/media/MediaParceledListSlice$2;->createFromParcel(Landroid/os/Parcel;)Ljava/lang/Object;
-HSPLandroid/media/MediaParceledListSlice;-><init>(Landroid/os/Parcel;)V
-HPLandroid/media/MediaParceledListSlice;-><init>(Ljava/util/List;)V
-HSPLandroid/media/MediaParceledListSlice;->getList()Ljava/util/List;
-HSPLandroid/media/MediaParceledListSlice;->writeToParcel(Landroid/os/Parcel;I)V
HSPLandroid/media/MediaPlayer$2$1;->getSubtitleLooper()Landroid/os/Looper;
HSPLandroid/media/MediaPlayer$2$1;->setSubtitleWidget(Landroid/media/SubtitleTrack$RenderingWidget;)V
HSPLandroid/media/MediaPlayer$2;->run()V
@@ -9446,7 +9439,7 @@ HPLandroid/media/session/ISessionController$Stub;->onTransact(ILandroid/os/Parce
HPLandroid/media/session/ISessionControllerCallback$Stub$Proxy;->asBinder()Landroid/os/IBinder;
HPLandroid/media/session/ISessionControllerCallback$Stub$Proxy;->onMetadataChanged(Landroid/media/MediaMetadata;)V
HPLandroid/media/session/ISessionControllerCallback$Stub$Proxy;->onPlaybackStateChanged(Landroid/media/session/PlaybackState;)V
-HPLandroid/media/session/ISessionControllerCallback$Stub$Proxy;->onQueueChanged(Landroid/media/MediaParceledListSlice;)V
+HPLandroid/media/session/ISessionControllerCallback$Stub$Proxy;->onQueueChanged(Landroid/media/ParceledListSlice;)V
HPLandroid/media/session/ISessionControllerCallback$Stub$Proxy;->onSessionDestroyed()V
HSPLandroid/media/session/ISessionManager$Stub$Proxy;->getSessions(Landroid/content/ComponentName;I)Ljava/util/List;
HSPLandroid/media/session/ISessionManager$Stub;-><init>()V
diff --git a/core/java/android/app/ActivityThread.java b/core/java/android/app/ActivityThread.java
index bfc8b1204373..ca04536af4c0 100644
--- a/core/java/android/app/ActivityThread.java
+++ b/core/java/android/app/ActivityThread.java
@@ -3393,6 +3393,9 @@ public final class ActivityThread extends ClientTransactionHandler {
}
WindowManagerGlobal.initialize();
+ // Hint the GraphicsEnvironment that an activity is launching on the process.
+ GraphicsEnvironment.hintActivityLaunch();
+
final Activity a = performLaunchActivity(r, customIntent);
if (a != null) {
diff --git a/core/java/android/app/DownloadManager.java b/core/java/android/app/DownloadManager.java
index be281c2a3efe..584115adcd4b 100644
--- a/core/java/android/app/DownloadManager.java
+++ b/core/java/android/app/DownloadManager.java
@@ -539,8 +539,9 @@ public class DownloadManager {
*
* <p> For applications targeting {@link android.os.Build.VERSION_CODES#Q} or above,
* {@link android.Manifest.permission#WRITE_EXTERNAL_STORAGE WRITE_EXTERNAL_STORAGE}
- * permission is not needed and the {@code dirType} must
- * be {@link Environment#DIRECTORY_DOWNLOADS}.
+ * permission is not needed and the {@code dirType} must be one of the known public
+ * directories like {@link Environment#DIRECTORY_DOWNLOADS},
+ * {@link Environment#DIRECTORY_PICTURES}, {@link Environment#DIRECTORY_MOVIES}, etc.
*
* @param dirType the directory type to pass to {@link Environment#getExternalStoragePublicDirectory(String)}
* @param subPath the path within the external directory, including the
@@ -594,11 +595,8 @@ public class DownloadManager {
* should be called before {@link DownloadManager#enqueue(Request)} is called.
*
* @deprecated Starting in Q, this value is ignored. Files downloaded to
- * public Downloads directory (as returned by
- * {@link Environment#getExternalStoragePublicDirectory(String)} with
- * {@link Environment#DIRECTORY_DOWNLOADS}) will be scanned by MediaScanner
- * and files downloaded to directories owned by applications
- * (e.g. {@link Context#getExternalFilesDir(String)}) will not be scanned.
+ * directories owned by applications (e.g. {@link Context#getExternalFilesDir(String)})
+ * will not be scanned by MediaScanner and the rest will be scanned.
*/
@Deprecated
public void allowScanningByMediaScanner() {
@@ -783,11 +781,11 @@ public class DownloadManager {
* @param isVisible whether to display this download in the Downloads UI
* @return this object
*
- * @deprecated Starting in Q, this value is ignored. Files downloaded to
+ * @deprecated Starting in Q, this value is ignored. Only files downloaded to
* public Downloads directory (as returned by
* {@link Environment#getExternalStoragePublicDirectory(String)} with
* {@link Environment#DIRECTORY_DOWNLOADS}) will be visible in system's Downloads UI
- * and files downloaded to directories owned by applications
+ * and the rest will not be visible.
* (e.g. {@link Context#getExternalFilesDir(String)}) will not be visible.
*/
@Deprecated
diff --git a/core/java/android/content/pm/PackageManager.java b/core/java/android/content/pm/PackageManager.java
index 40561f02d55f..bdab1e28d20a 100644
--- a/core/java/android/content/pm/PackageManager.java
+++ b/core/java/android/content/pm/PackageManager.java
@@ -725,6 +725,7 @@ public abstract class PackageManager {
INSTALL_APEX,
INSTALL_ENABLE_ROLLBACK,
INSTALL_ALLOW_DOWNGRADE,
+ INSTALL_STAGED,
})
@Retention(RetentionPolicy.SOURCE)
public @interface InstallFlags {}
@@ -894,6 +895,14 @@ public abstract class PackageManager {
*/
public static final int INSTALL_ALLOW_DOWNGRADE = 0x00100000;
+ /**
+ * Flag parameter for {@link #installPackage} to indicate that this package
+ * is being installed as part of a staged install.
+ *
+ * @hide
+ */
+ public static final int INSTALL_STAGED = 0x00200000;
+
/** @hide */
@IntDef(flag = true, prefix = { "DONT_KILL_APP" }, value = {
DONT_KILL_APP
diff --git a/core/java/android/content/pm/PackageManagerInternal.java b/core/java/android/content/pm/PackageManagerInternal.java
index e14d7e895f17..5a69e6bdef30 100644
--- a/core/java/android/content/pm/PackageManagerInternal.java
+++ b/core/java/android/content/pm/PackageManagerInternal.java
@@ -174,6 +174,22 @@ public abstract class PackageManagerInternal {
}
/**
+ * Provider for default dialer
+ */
+ public interface DefaultDialerProvider {
+
+ /**
+ * Get the package name of the default dialer.
+ *
+ * @param userId the user id
+ *
+ * @return the package name of the default dialer, or {@code null} if none
+ */
+ @Nullable
+ String getDefaultDialer(@UserIdInt int userId);
+ }
+
+ /**
* Provider for default home
*/
public interface DefaultHomeProvider {
@@ -230,14 +246,6 @@ public abstract class PackageManagerInternal {
public abstract void setSyncAdapterPackagesprovider(SyncAdapterPackagesProvider provider);
/**
- * Called when the package for the default dialer changed
- *
- * @param packageName the new dialer package
- * @param userId user for which the change was made
- */
- public void onDefaultDialerAppChanged(String packageName, int userId) {}
-
- /**
* Called when the package for the default SMS handler changed
*
* @param packageName the new sms package
@@ -932,6 +940,13 @@ public abstract class PackageManagerInternal {
public abstract void setDefaultBrowserProvider(@NonNull DefaultBrowserProvider provider);
/**
+ * Sets the default dialer provider.
+ *
+ * @param provider the provider
+ */
+ public abstract void setDefaultDialerProvider(@NonNull DefaultDialerProvider provider);
+
+ /**
* Sets the default home provider.
*
* @param provider the provider
diff --git a/core/java/android/content/pm/PackageParser.java b/core/java/android/content/pm/PackageParser.java
index 1784d8ad3c6c..7522bfb25b7a 100644
--- a/core/java/android/content/pm/PackageParser.java
+++ b/core/java/android/content/pm/PackageParser.java
@@ -238,24 +238,6 @@ public class PackageParser {
CHILD_PACKAGE_TAGS.add(TAG_EAT_COMMENT);
}
- // STOPSHIP(b/112545973): remove once feature enabled by default
- private static final Set<String> FORCE_AUDIO_PACKAGES;
- private static final Set<String> FORCE_VIDEO_PACKAGES;
- private static final Set<String> FORCE_IMAGES_PACKAGES;
- static {
- FORCE_AUDIO_PACKAGES = parsePackageList(
- SystemProperties.get(StorageManager.PROP_FORCE_AUDIO));
- FORCE_VIDEO_PACKAGES = parsePackageList(
- SystemProperties.get(StorageManager.PROP_FORCE_VIDEO));
- FORCE_IMAGES_PACKAGES = parsePackageList(
- SystemProperties.get(StorageManager.PROP_FORCE_IMAGES));
- }
-
- private static Set<String> parsePackageList(String pkgs) {
- if (TextUtils.isEmpty(pkgs)) return Collections.emptySet();
- return new ArraySet<String>(Arrays.asList(pkgs.split(",")));
- }
-
private static final boolean LOG_UNSAFE_BROADCASTS = false;
/**
@@ -2554,34 +2536,6 @@ public class PackageParser {
adjustPackageToBeUnresizeableAndUnpipable(pkg);
}
- // If the storage model feature flag is disabled, we need to fiddle
- // around with permission definitions to return us to pre-Q behavior.
- // STOPSHIP(b/112545973): remove once feature enabled by default
- if (!StorageManager.hasIsolatedStorage()) {
- if ("android".equals(pkg.packageName)) {
- final ArraySet<String> newPermissions = new ArraySet<>();
- newPermissions.add(android.Manifest.permission.ACCESS_MEDIA_LOCATION);
- newPermissions.add(android.Manifest.permission.WRITE_OBB);
-
- for (int i = pkg.permissions.size() - 1; i >= 0; i--) {
- final Permission p = pkg.permissions.get(i);
- if (newPermissions.contains(p.info.name)) {
- pkg.permissions.remove(i);
- }
- }
- }
- } else {
- if (FORCE_AUDIO_PACKAGES.contains(pkg.packageName)) {
- pkg.requestedPermissions.add(android.Manifest.permission.READ_EXTERNAL_STORAGE);
- }
- if (FORCE_VIDEO_PACKAGES.contains(pkg.packageName)) {
- pkg.requestedPermissions.add(android.Manifest.permission.READ_EXTERNAL_STORAGE);
- }
- if (FORCE_IMAGES_PACKAGES.contains(pkg.packageName)) {
- pkg.requestedPermissions.add(android.Manifest.permission.READ_EXTERNAL_STORAGE);
- }
- }
-
return pkg;
}
diff --git a/core/java/android/net/ConnectivityManager.java b/core/java/android/net/ConnectivityManager.java
index 0e10de8c4e3f..a69ca99500d6 100644
--- a/core/java/android/net/ConnectivityManager.java
+++ b/core/java/android/net/ConnectivityManager.java
@@ -3449,6 +3449,10 @@ public class ConnectivityManager {
final NetworkCallback callback;
synchronized (sCallbacks) {
callback = sCallbacks.get(request);
+ if (message.what == CALLBACK_UNAVAIL) {
+ sCallbacks.remove(request);
+ callback.networkRequest = ALREADY_UNREGISTERED;
+ }
}
if (DBG) {
Log.d(TAG, getCallbackName(message.what) + " for network " + network);
@@ -3995,8 +3999,10 @@ public class ConnectivityManager {
synchronized (sCallbacks) {
Preconditions.checkArgument(networkCallback.networkRequest != null,
"NetworkCallback was not registered");
- Preconditions.checkArgument(networkCallback.networkRequest != ALREADY_UNREGISTERED,
- "NetworkCallback was already unregistered");
+ if (networkCallback.networkRequest == ALREADY_UNREGISTERED) {
+ Log.d(TAG, "NetworkCallback was already unregistered");
+ return;
+ }
for (Map.Entry<NetworkRequest, NetworkCallback> e : sCallbacks.entrySet()) {
if (e.getValue() == networkCallback) {
reqs.add(e.getKey());
diff --git a/core/java/android/net/IpSecManager.java b/core/java/android/net/IpSecManager.java
index 7d34381f73fa..83813da80c44 100644
--- a/core/java/android/net/IpSecManager.java
+++ b/core/java/android/net/IpSecManager.java
@@ -19,11 +19,13 @@ import static com.android.internal.util.Preconditions.checkNotNull;
import android.annotation.IntDef;
import android.annotation.NonNull;
+import android.annotation.RequiresFeature;
import android.annotation.RequiresPermission;
import android.annotation.SystemApi;
import android.annotation.SystemService;
import android.annotation.TestApi;
import android.content.Context;
+import android.content.pm.PackageManager;
import android.os.Binder;
import android.os.ParcelFileDescriptor;
import android.os.RemoteException;
@@ -749,6 +751,7 @@ public final class IpSecManager {
* @hide
*/
@SystemApi
+ @RequiresFeature(PackageManager.FEATURE_IPSEC_TUNNELS)
@RequiresPermission(android.Manifest.permission.MANAGE_IPSEC_TUNNELS)
public void addAddress(@NonNull InetAddress address, int prefixLen) throws IOException {
try {
@@ -771,6 +774,7 @@ public final class IpSecManager {
* @hide
*/
@SystemApi
+ @RequiresFeature(PackageManager.FEATURE_IPSEC_TUNNELS)
@RequiresPermission(android.Manifest.permission.MANAGE_IPSEC_TUNNELS)
public void removeAddress(@NonNull InetAddress address, int prefixLen) throws IOException {
try {
@@ -886,6 +890,7 @@ public final class IpSecManager {
*/
@SystemApi
@NonNull
+ @RequiresFeature(PackageManager.FEATURE_IPSEC_TUNNELS)
@RequiresPermission(android.Manifest.permission.MANAGE_IPSEC_TUNNELS)
public IpSecTunnelInterface createIpSecTunnelInterface(@NonNull InetAddress localAddress,
@NonNull InetAddress remoteAddress, @NonNull Network underlyingNetwork)
@@ -916,6 +921,7 @@ public final class IpSecManager {
* @hide
*/
@SystemApi
+ @RequiresFeature(PackageManager.FEATURE_IPSEC_TUNNELS)
@RequiresPermission(android.Manifest.permission.MANAGE_IPSEC_TUNNELS)
public void applyTunnelModeTransform(@NonNull IpSecTunnelInterface tunnel,
@PolicyDirection int direction, @NonNull IpSecTransform transform) throws IOException {
diff --git a/core/java/android/net/IpSecTransform.java b/core/java/android/net/IpSecTransform.java
index e519fdf65e50..36111f2a372d 100644
--- a/core/java/android/net/IpSecTransform.java
+++ b/core/java/android/net/IpSecTransform.java
@@ -21,9 +21,11 @@ import static com.android.internal.util.Preconditions.checkNotNull;
import android.annotation.IntDef;
import android.annotation.NonNull;
+import android.annotation.RequiresFeature;
import android.annotation.RequiresPermission;
import android.annotation.SystemApi;
import android.content.Context;
+import android.content.pm.PackageManager;
import android.os.Binder;
import android.os.Handler;
import android.os.IBinder;
@@ -483,6 +485,7 @@ public final class IpSecTransform implements AutoCloseable {
*/
@SystemApi
@NonNull
+ @RequiresFeature(PackageManager.FEATURE_IPSEC_TUNNELS)
@RequiresPermission(android.Manifest.permission.MANAGE_IPSEC_TUNNELS)
public IpSecTransform buildTunnelModeTransform(
@NonNull InetAddress sourceAddress,
diff --git a/core/java/android/os/GraphicsEnvironment.java b/core/java/android/os/GraphicsEnvironment.java
index 1868d0596acc..5039b31ed9ff 100644
--- a/core/java/android/os/GraphicsEnvironment.java
+++ b/core/java/android/os/GraphicsEnvironment.java
@@ -108,6 +108,12 @@ public class GraphicsEnvironment {
}
/**
+ * Hint for GraphicsEnvironment that an activity is launching on the process.
+ * Then the app process is allowed to send stats to GpuStats module.
+ */
+ public static native void hintActivityLaunch();
+
+ /**
* Allow to query whether an application will use Game Driver.
*/
public static boolean shouldUseGameDriver(Context context, Bundle coreSettings,
diff --git a/core/java/android/os/Process.java b/core/java/android/os/Process.java
index b82b5ef3f0ba..e50ab6cfc017 100644
--- a/core/java/android/os/Process.java
+++ b/core/java/android/os/Process.java
@@ -511,7 +511,6 @@ public class Process {
* @param appDataDir null-ok the data directory of the app.
* @param invokeWith null-ok the command to invoke with.
* @param packageName null-ok the name of the package this process belongs to.
- * @param packagesForUid null-ok all the packages with the same uid as this process.
* @param useSystemGraphicsDriver whether the process uses system graphics driver.
*
* @param zygoteArgs Additional arguments to supply to the zygote process.
@@ -532,14 +531,12 @@ public class Process {
@Nullable String appDataDir,
@Nullable String invokeWith,
@Nullable String packageName,
- @Nullable String[] packagesForUid,
- @Nullable String sandboxId,
boolean useSystemGraphicsDriver,
@Nullable String[] zygoteArgs) {
return ZYGOTE_PROCESS.start(processClass, niceName, uid, gid, gids,
runtimeFlags, mountExternal, targetSdkVersion, seInfo,
abi, instructionSet, appDataDir, invokeWith, packageName,
- packagesForUid, sandboxId, /*useUsapPool=*/ true,
+ /*useUsapPool=*/ true,
useSystemGraphicsDriver, zygoteArgs);
}
@@ -556,14 +553,12 @@ public class Process {
@Nullable String appDataDir,
@Nullable String invokeWith,
@Nullable String packageName,
- @Nullable String[] packagesForUid,
- @Nullable String sandboxId,
boolean useSystemGraphicsDriver,
@Nullable String[] zygoteArgs) {
return WebViewZygote.getProcess().start(processClass, niceName, uid, gid, gids,
runtimeFlags, mountExternal, targetSdkVersion, seInfo,
abi, instructionSet, appDataDir, invokeWith, packageName,
- packagesForUid, sandboxId, /*useUsapPool=*/ false,
+ /*useUsapPool=*/ false,
useSystemGraphicsDriver, zygoteArgs);
}
diff --git a/core/java/android/os/ZygoteProcess.java b/core/java/android/os/ZygoteProcess.java
index 85361587119d..2b170c2a6587 100644
--- a/core/java/android/os/ZygoteProcess.java
+++ b/core/java/android/os/ZygoteProcess.java
@@ -306,7 +306,6 @@ public class ZygoteProcess {
* @param appDataDir null-ok the data directory of the app.
* @param invokeWith null-ok the command to invoke with.
* @param packageName null-ok the name of the package this process belongs to.
- * @param packagesForUid null-ok all the packages with the same uid as this process.
* @param zygoteArgs Additional arguments to supply to the zygote process.
* @param useSystemGraphicsDriver whether the process uses system graphics driver.
*
@@ -324,8 +323,6 @@ public class ZygoteProcess {
@Nullable String appDataDir,
@Nullable String invokeWith,
@Nullable String packageName,
- @Nullable String[] packagesForUid,
- @Nullable String sandboxId,
boolean useUsapPool,
boolean useSystemGraphicsDriver,
@Nullable String[] zygoteArgs) {
@@ -338,8 +335,7 @@ public class ZygoteProcess {
return startViaZygote(processClass, niceName, uid, gid, gids,
runtimeFlags, mountExternal, targetSdkVersion, seInfo,
abi, instructionSet, appDataDir, invokeWith, /*startChildZygote=*/ false,
- packageName, packagesForUid, sandboxId,
- useUsapPool, useSystemGraphicsDriver, zygoteArgs);
+ packageName, useUsapPool, useSystemGraphicsDriver, zygoteArgs);
} catch (ZygoteStartFailedEx ex) {
Log.e(LOG_TAG,
"Starting VM process through Zygote failed");
@@ -532,7 +528,6 @@ public class ZygoteProcess {
* @param startChildZygote Start a sub-zygote. This creates a new zygote process
* that has its state cloned from this zygote process.
* @param packageName null-ok the name of the package this process belongs to.
- * @param packagesForUid null-ok all the packages with the same uid as this process.
* @param extraArgs Additional arguments to supply to the zygote process.
* @return An object that describes the result of the attempt to start the process.
* @throws ZygoteStartFailedEx if process start failed for any reason
@@ -550,8 +545,6 @@ public class ZygoteProcess {
@Nullable String invokeWith,
boolean startChildZygote,
@Nullable String packageName,
- @Nullable String[] packagesForUid,
- @Nullable String sandboxId,
boolean useUsapPool,
boolean useSystemGraphicsDriver,
@Nullable String[] extraArgs)
@@ -625,14 +618,6 @@ public class ZygoteProcess {
argsForZygote.add("--package-name=" + packageName);
}
- if (packagesForUid != null && packagesForUid.length > 0) {
- argsForZygote.add("--packages-for-uid=" + String.join(",", packagesForUid));
- }
-
- if (sandboxId != null) {
- argsForZygote.add("--sandbox-id=" + sandboxId);
- }
-
argsForZygote.add(processClass);
if (extraArgs != null) {
@@ -1149,7 +1134,6 @@ public class ZygoteProcess {
gids, runtimeFlags, 0 /* mountExternal */, 0 /* targetSdkVersion */, seInfo,
abi, instructionSet, null /* appDataDir */, null /* invokeWith */,
true /* startChildZygote */, null /* packageName */,
- null /* packagesForUid */, null /* sandboxId */,
false /* useUsapPool */, false /*useSystemGraphicsDriver*/,
extraArgs);
} catch (ZygoteStartFailedEx ex) {
diff --git a/core/java/android/os/storage/IStorageManager.aidl b/core/java/android/os/storage/IStorageManager.aidl
index 9db41116d20a..92fecaddff22 100644
--- a/core/java/android/os/storage/IStorageManager.aidl
+++ b/core/java/android/os/storage/IStorageManager.aidl
@@ -188,8 +188,6 @@ interface IStorageManager {
void allocateBytes(String volumeUuid, long bytes, int flags, String callingPackage) = 78;
void runIdleMaintenance() = 79;
void abortIdleMaintenance() = 80;
- String translateAppToSystem(String path, int pid, int uid) = 81;
- String translateSystemToApp(String path, int pid, int uid) = 82;
void commitChanges() = 83;
boolean supportsCheckpoint() = 84;
void startCheckpoint(int numTries) = 85;
diff --git a/core/java/android/os/storage/StorageManager.java b/core/java/android/os/storage/StorageManager.java
index b9fc186e1c1e..ee62af57b9a0 100644
--- a/core/java/android/os/storage/StorageManager.java
+++ b/core/java/android/os/storage/StorageManager.java
@@ -155,13 +155,6 @@ public class StorageManager {
public static final String PROP_ISOLATED_STORAGE_SNAPSHOT = "sys.isolated_storage_snapshot";
/** {@hide} */
- public static final String PROP_FORCE_AUDIO = "persist.fw.force_audio";
- /** {@hide} */
- public static final String PROP_FORCE_VIDEO = "persist.fw.force_video";
- /** {@hide} */
- public static final String PROP_FORCE_IMAGES = "persist.fw.force_images";
-
- /** {@hide} */
public static final String UUID_PRIVATE_INTERNAL = null;
/** {@hide} */
public static final String UUID_PRIMARY_PHYSICAL = "primary_physical";
@@ -291,9 +284,6 @@ public class StorageManager {
public static final int ENCRYPTION_STATE_ERROR_CORRUPT =
IVold.ENCRYPTION_STATE_ERROR_CORRUPT;
- /** @hide Prefix used in sandboxIds for apps with sharedUserIds */
- public static final String SHARED_SANDBOX_PREFIX = "shared-";
-
private static volatile IStorageManager sStorageManager = null;
private final Context mContext;
@@ -1618,15 +1608,7 @@ public class StorageManager {
* @hide
*/
public File translateAppToSystem(File file, int pid, int uid) {
- // We can only translate absolute paths
- if (!file.isAbsolute()) return file;
-
- try {
- return new File(mStorageManager.translateAppToSystem(file.getAbsolutePath(),
- pid, uid));
- } catch (RemoteException e) {
- throw e.rethrowFromSystemServer();
- }
+ return file;
}
/**
@@ -1636,15 +1618,7 @@ public class StorageManager {
* @hide
*/
public File translateSystemToApp(File file, int pid, int uid) {
- // We can only translate absolute paths
- if (!file.isAbsolute()) return file;
-
- try {
- return new File(mStorageManager.translateSystemToApp(file.getAbsolutePath(),
- pid, uid));
- } catch (RemoteException e) {
- throw e.rethrowFromSystemServer();
- }
+ return file;
}
/**
diff --git a/core/java/android/os/storage/StorageManagerInternal.java b/core/java/android/os/storage/StorageManagerInternal.java
index f1c313838731..942bf94b1db6 100644
--- a/core/java/android/os/storage/StorageManagerInternal.java
+++ b/core/java/android/os/storage/StorageManagerInternal.java
@@ -16,8 +16,6 @@
package android.os.storage;
-import android.annotation.NonNull;
-import android.annotation.Nullable;
import android.os.IVold;
/**
@@ -85,30 +83,6 @@ public abstract class StorageManagerInternal {
public abstract int getExternalStorageMountMode(int uid, String packageName);
/**
- * Create storage sandbox for the given package.
- *
- * <p> This will involve calling into vold to setup appropriate bind mounts.
- *
- * @param packageName The package for which the sandbox needs to be created.
- * @param appId The appId for the given package.
- * @param sharedUserId The sharedUserId for given package if it specified
- * {@code android:sharedUserId} in the manifest, otherwise {@code null}
- * @param userId The userId in which the sandbox needs to be created.
- */
- public abstract void prepareSandboxForApp(@NonNull String packageName, int appId,
- @Nullable String sharedUserId, int userId);
-
- /**
- * Delete storage sandbox for the given package.
- *
- * @param packageName The package for which the sandbox needs to be destroyed.
- * @param sharedUserId The sharedUserId if specified by the package.
- * @param userId The userId in which the sandbox needs to be destroyed.
- */
- public abstract void destroySandboxForApp(@NonNull String packageName,
- @Nullable String sharedUserId, int userId);
-
- /**
* A listener for reset events in the StorageManagerService.
*/
public interface ResetListener {
@@ -127,9 +101,4 @@ public abstract class StorageManagerInternal {
* @param listener The listener that will be notified on reset events.
*/
public abstract void addResetListener(ResetListener listener);
-
- /**
- * Return the sandboxId for the given package on external storage.
- */
- public abstract String getSandboxId(String packageName);
}
diff --git a/core/java/android/provider/Settings.java b/core/java/android/provider/Settings.java
index 57223ab7efc4..2aae39d9f58a 100644
--- a/core/java/android/provider/Settings.java
+++ b/core/java/android/provider/Settings.java
@@ -8273,6 +8273,16 @@ public final class Settings {
BOOLEAN_VALIDATOR;
/**
+ * Whether or not the face unlock education screen has been shown to the user.
+ * @hide
+ */
+ public static final String FACE_UNLOCK_EDUCATION_INFO_DISPLAYED =
+ "face_unlock_education_info_displayed";
+
+ private static final Validator FACE_UNLOCK_EDUCATION_INFO_DISPLAYED_VALIDATOR =
+ BOOLEAN_VALIDATOR;
+
+ /**
* Whether or not debugging is enabled.
* @hide
*/
@@ -9079,6 +9089,8 @@ public final class Settings {
VALIDATORS.put(FACE_UNLOCK_APP_ENABLED, FACE_UNLOCK_APP_ENABLED_VALIDATOR);
VALIDATORS.put(FACE_UNLOCK_ALWAYS_REQUIRE_CONFIRMATION,
FACE_UNLOCK_ALWAYS_REQUIRE_CONFIRMATION_VALIDATOR);
+ VALIDATORS.put(FACE_UNLOCK_EDUCATION_INFO_DISPLAYED,
+ FACE_UNLOCK_EDUCATION_INFO_DISPLAYED_VALIDATOR);
VALIDATORS.put(ASSIST_GESTURE_ENABLED, ASSIST_GESTURE_ENABLED_VALIDATOR);
VALIDATORS.put(ASSIST_GESTURE_SILENCE_ALERTS_ENABLED,
ASSIST_GESTURE_SILENCE_ALERTS_ENABLED_VALIDATOR);
@@ -9165,6 +9177,7 @@ public final class Settings {
CLONE_TO_MANAGED_PROFILE.add(ACCESSIBILITY_ENABLED);
CLONE_TO_MANAGED_PROFILE.add(ALLOW_MOCK_LOCATION);
CLONE_TO_MANAGED_PROFILE.add(ALLOWED_GEOLOCATION_ORIGINS);
+ CLONE_TO_MANAGED_PROFILE.add(CONTENT_CAPTURE_ENABLED);
CLONE_TO_MANAGED_PROFILE.add(ENABLED_ACCESSIBILITY_SERVICES);
CLONE_TO_MANAGED_PROFILE.add(LOCATION_CHANGER);
CLONE_TO_MANAGED_PROFILE.add(LOCATION_MODE);
diff --git a/core/java/android/view/RenderNodeAnimator.java b/core/java/android/view/RenderNodeAnimator.java
index 04ac92292740..c2f96013142b 100644
--- a/core/java/android/view/RenderNodeAnimator.java
+++ b/core/java/android/view/RenderNodeAnimator.java
@@ -24,7 +24,6 @@ import android.graphics.CanvasProperty;
import android.graphics.Paint;
import android.graphics.RecordingCanvas;
import android.graphics.RenderNode;
-import android.os.Build;
import android.os.Handler;
import android.os.Looper;
import android.util.SparseIntArray;
@@ -289,7 +288,8 @@ public class RenderNodeAnimator extends Animator {
throw new UnsupportedOperationException();
}
- @UnsupportedAppUsage(maxTargetSdk = Build.VERSION_CODES.P)
+ /** @hide */
+ @UnsupportedAppUsage
public void setTarget(View view) {
mViewTarget = view;
setTarget(mViewTarget.mRenderNode);
@@ -301,7 +301,7 @@ public class RenderNodeAnimator extends Animator {
}
/** @hide */
- @UnsupportedAppUsage(maxTargetSdk = Build.VERSION_CODES.O)
+ @UnsupportedAppUsage
public void setTarget(DisplayListCanvas canvas) {
setTarget((RecordingCanvas) canvas);
}
diff --git a/core/java/android/view/Window.java b/core/java/android/view/Window.java
index cbcc057811fd..9436633c0c4b 100644
--- a/core/java/android/view/Window.java
+++ b/core/java/android/view/Window.java
@@ -1090,6 +1090,7 @@ public abstract class Window {
*
* @hide
*/
+ @UnsupportedAppUsage
public void addPrivateFlags(int flags) {
setPrivateFlags(flags, flags);
}
diff --git a/core/java/android/view/autofill/AutofillManager.java b/core/java/android/view/autofill/AutofillManager.java
index 5872d3f7f785..35ea8964a342 100644
--- a/core/java/android/view/autofill/AutofillManager.java
+++ b/core/java/android/view/autofill/AutofillManager.java
@@ -48,6 +48,7 @@ import android.service.autofill.FillEventHistory;
import android.service.autofill.UserData;
import android.util.ArrayMap;
import android.util.ArraySet;
+import android.util.DebugUtils;
import android.util.Log;
import android.util.Slog;
import android.util.SparseArray;
@@ -229,7 +230,8 @@ public final class AutofillManager {
/** @hide */ public static final int FLAG_ADD_CLIENT_VERBOSE = 0x4;
/** @hide */ public static final int FLAG_ADD_CLIENT_ENABLED_FOR_AUGMENTED_AUTOFILL_ONLY = 0x8;
- /** @hide */ public static final int FLAG_SESSION_FOR_AUGMENTED_AUTOFILL_ONLY = 0x1;
+ // NOTE: flag below is used by the session start receiver only, hence it can have values above
+ /** @hide */ public static final int RECEIVER_FLAG_SESSION_FOR_AUGMENTED_AUTOFILL_ONLY = 0x1;
/** @hide */
public static final int DEFAULT_LOGGING_LEVEL = Build.IS_DEBUGGABLE
@@ -521,7 +523,7 @@ public final class AutofillManager {
private boolean mForAugmentedAutofillOnly;
/**
- * When set, standard autofill is enabled, but sessions can still be created for augmented
+ * When set, standard autofill is disabled, but sessions can still be created for augmented
* autofill only.
*/
@GuardedBy("mLock")
@@ -969,6 +971,13 @@ public final class AutofillManager {
startSessionLocked(id, null, value, flags);
} else {
// Update focus on existing session.
+ if (mForAugmentedAutofillOnly && (flags & FLAG_MANUAL_REQUEST) != 0) {
+ if (sDebug) {
+ Log.d(TAG, "notifyViewEntered(" + id + "): resetting "
+ + "mForAugmentedAutofillOnly on manual request");
+ }
+ mForAugmentedAutofillOnly = false;
+ }
updateSessionLocked(id, null, value, ACTION_VIEW_ENTERED, flags);
}
addEnteredIdLocked(id);
@@ -1126,6 +1135,13 @@ public final class AutofillManager {
startSessionLocked(id, bounds, null, flags);
} else {
// Update focus on existing session.
+ if (mForAugmentedAutofillOnly && (flags & FLAG_MANUAL_REQUEST) != 0) {
+ if (sDebug) {
+ Log.d(TAG, "notifyViewEntered(" + id + "): resetting "
+ + "mForAugmentedAutofillOnly on manual request");
+ }
+ mForAugmentedAutofillOnly = false;
+ }
updateSessionLocked(id, bounds, null, ACTION_VIEW_ENTERED, flags);
}
addEnteredIdLocked(id);
@@ -1695,6 +1711,16 @@ public final class AutofillManager {
+ ", enabledAugmentedOnly=" + mEnabledForAugmentedAutofillOnly
+ ", enteredIds=" + mEnteredIds);
}
+ // We need to reset the augmented-only state when a manual request is made, as it's possible
+ // that the service returned null for the first request and now the user is manually
+ // requesting autofill to trigger a custom UI provided by the service.
+ if (mForAugmentedAutofillOnly && !mEnabledForAugmentedAutofillOnly
+ && (flags & FLAG_MANUAL_REQUEST) != 0) {
+ if (sVerbose) {
+ Log.v(TAG, "resetting mForAugmentedAutofillOnly on manual autofill request");
+ }
+ mForAugmentedAutofillOnly = false;
+ }
if (mState != STATE_UNKNOWN && !isFinishedLocked() && (flags & FLAG_MANUAL_REQUEST) == 0) {
if (sVerbose) {
Log.v(TAG, "not automatically starting session for " + id
@@ -1717,7 +1743,7 @@ public final class AutofillManager {
mState = STATE_ACTIVE;
}
final int extraFlags = receiver.getOptionalExtraIntResult(0);
- if ((extraFlags & FLAG_SESSION_FOR_AUGMENTED_AUTOFILL_ONLY) != 0) {
+ if ((extraFlags & RECEIVER_FLAG_SESSION_FOR_AUGMENTED_AUTOFILL_ONLY) != 0) {
if (sDebug) Log.d(TAG, "startSession(" + componentName + "): for augmented only");
mForAugmentedAutofillOnly = true;
}
@@ -2011,10 +2037,20 @@ public final class AutofillManager {
public static final int SET_STATE_FLAG_DEBUG = 0x08;
/** @hide */
public static final int SET_STATE_FLAG_VERBOSE = 0x10;
+ /** @hide */
+ public static final int SET_STATE_FLAG_FOR_AUTOFILL_ONLY = 0x20;
private void setState(int flags) {
- if (sVerbose) Log.v(TAG, "setState(" + flags + ")");
+ if (sVerbose) {
+ Log.v(TAG, "setState(" + flags + ": " + DebugUtils.flagsToString(AutofillManager.class,
+ "SET_STATE_FLAG_", flags) + ")");
+ }
synchronized (mLock) {
+ if ((flags & SET_STATE_FLAG_FOR_AUTOFILL_ONLY) != 0) {
+ mForAugmentedAutofillOnly = true;
+ // NOTE: returning right away as this is the only flag set, at least currently...
+ return;
+ }
mEnabled = (flags & SET_STATE_FLAG_ENABLED) != 0;
if (!mEnabled || (flags & SET_STATE_FLAG_RESET_SESSION) != 0) {
// Reset the session state
@@ -2390,7 +2426,7 @@ public final class AutofillManager {
}
}
- if (sessionFinishedState != 0) {
+ if (sessionFinishedState != STATE_UNKNOWN) {
// Callback call was "hijacked" to also update the session state.
setSessionFinished(sessionFinishedState, /* autofillableIds= */ null);
}
diff --git a/core/java/com/android/internal/os/BatteryStatsImpl.java b/core/java/com/android/internal/os/BatteryStatsImpl.java
index 72f6c122fe3a..c04a249670fa 100644
--- a/core/java/com/android/internal/os/BatteryStatsImpl.java
+++ b/core/java/com/android/internal/os/BatteryStatsImpl.java
@@ -12028,7 +12028,7 @@ public class BatteryStatsImpl extends BatteryStats {
// if the device is now charging, it means that this is either called
// 1. directly when level >= 90
// 2. or from within the runnable that we deferred
- // For 1. if we have an existing callback, remove it, since we will immediatelly send a
+ // For 1. if we have an existing callback, remove it, since we will immediately send a
// ACTION_CHARGING
// For 2. we remove existing callback so we don't send multiple ACTION_CHARGING
mHandler.removeCallbacks(mDeferSetCharging);
@@ -12369,7 +12369,6 @@ public class BatteryStatsImpl extends BatteryStats {
// If the battery level is at least 90%, always consider the device to be
// charging even if it happens to go down a level.
changed |= setChargingLocked(true);
- mLastChargeStepLevel = level;
} else if (!mCharging) {
if (mLastChargeStepLevel < level) {
// We have not reported that we are charging, but the level has gone up,
@@ -12395,17 +12394,16 @@ public class BatteryStatsImpl extends BatteryStats {
changed |= setChargingLocked(false);
}
}
- mLastChargeStepLevel = level;
if (mLastChargeStepLevel != level && mMaxChargeStepLevel < level) {
mChargeStepTracker.addLevelSteps(level - mLastChargeStepLevel,
modeBits, elapsedRealtime);
mDailyChargeStepTracker.addLevelSteps(level - mLastChargeStepLevel,
modeBits, elapsedRealtime);
- mLastChargeStepLevel = level;
mMaxChargeStepLevel = level;
mInitStepMode = mCurStepMode;
mModStepMode = 0;
}
+ mLastChargeStepLevel = level;
}
if (changed) {
addHistoryRecordLocked(elapsedRealtime, uptime);
diff --git a/core/java/com/android/internal/os/Zygote.java b/core/java/com/android/internal/os/Zygote.java
index 99175b8becfe..2736c6a7149f 100644
--- a/core/java/com/android/internal/os/Zygote.java
+++ b/core/java/com/android/internal/os/Zygote.java
@@ -234,14 +234,13 @@ public final class Zygote {
public static int forkAndSpecialize(int uid, int gid, int[] gids, int runtimeFlags,
int[][] rlimits, int mountExternal, String seInfo, String niceName, int[] fdsToClose,
int[] fdsToIgnore, boolean startChildZygote, String instructionSet, String appDataDir,
- String packageName, String[] packagesForUID, String sandboxId, int targetSdkVersion) {
+ int targetSdkVersion) {
ZygoteHooks.preFork();
// Resets nice priority for zygote process.
resetNicePriority();
int pid = nativeForkAndSpecialize(
uid, gid, gids, runtimeFlags, rlimits, mountExternal, seInfo, niceName, fdsToClose,
- fdsToIgnore, startChildZygote, instructionSet, appDataDir, packageName,
- packagesForUID, sandboxId);
+ fdsToIgnore, startChildZygote, instructionSet, appDataDir);
// Enable tracing as soon as possible for the child process.
if (pid == 0) {
Zygote.disableExecuteOnly(targetSdkVersion);
@@ -257,8 +256,7 @@ public final class Zygote {
private static native int nativeForkAndSpecialize(int uid, int gid, int[] gids,
int runtimeFlags, int[][] rlimits, int mountExternal, String seInfo, String niceName,
int[] fdsToClose, int[] fdsToIgnore, boolean startChildZygote, String instructionSet,
- String appDataDir, String packageName, String[] packagesForUID,
- String sandboxId);
+ String appDataDir);
/**
* Specialize an unspecialized app process. The current VM must have been started
@@ -283,11 +281,9 @@ public final class Zygote {
*/
public static void specializeAppProcess(int uid, int gid, int[] gids, int runtimeFlags,
int[][] rlimits, int mountExternal, String seInfo, String niceName,
- boolean startChildZygote, String instructionSet, String appDataDir, String packageName,
- String[] packagesForUID, String sandboxId) {
+ boolean startChildZygote, String instructionSet, String appDataDir) {
nativeSpecializeAppProcess(uid, gid, gids, runtimeFlags, rlimits, mountExternal, seInfo,
- niceName, startChildZygote, instructionSet, appDataDir,
- packageName, packagesForUID, sandboxId);
+ niceName, startChildZygote, instructionSet, appDataDir);
// Enable tracing as soon as possible for the child process.
Trace.setTracingEnabled(true, runtimeFlags);
@@ -306,8 +302,7 @@ public final class Zygote {
private static native void nativeSpecializeAppProcess(int uid, int gid, int[] gids,
int runtimeFlags, int[][] rlimits, int mountExternal, String seInfo, String niceName,
- boolean startChildZygote, String instructionSet, String appDataDir, String packageName,
- String[] packagesForUID, String sandboxId);
+ boolean startChildZygote, String instructionSet, String appDataDir);
/**
* Called to do any initialization before starting an application.
@@ -607,8 +602,7 @@ public final class Zygote {
specializeAppProcess(args.mUid, args.mGid, args.mGids,
args.mRuntimeFlags, rlimits, args.mMountExternal,
args.mSeInfo, args.mNiceName, args.mStartChildZygote,
- args.mInstructionSet, args.mAppDataDir, args.mPackageName,
- args.mPackagesForUid, args.mSandboxId);
+ args.mInstructionSet, args.mAppDataDir);
disableExecuteOnly(args.mTargetSdkVersion);
diff --git a/core/java/com/android/internal/os/ZygoteArguments.java b/core/java/com/android/internal/os/ZygoteArguments.java
index 28642d8ba80c..2564f6b4d610 100644
--- a/core/java/com/android/internal/os/ZygoteArguments.java
+++ b/core/java/com/android/internal/os/ZygoteArguments.java
@@ -119,12 +119,6 @@ class ZygoteArguments {
/** from --package-name */
String mPackageName;
- /** from --packages-for-uid */
- String[] mPackagesForUid;
-
- /** from --sandbox-id */
- String mSandboxId;
-
/**
* Any args after and including the first non-option arg (or after a '--')
*/
@@ -411,13 +405,6 @@ class ZygoteArguments {
throw new IllegalArgumentException("Duplicate arg specified");
}
mPackageName = arg.substring(arg.indexOf('=') + 1);
- } else if (arg.startsWith("--packages-for-uid=")) {
- mPackagesForUid = arg.substring(arg.indexOf('=') + 1).split(",");
- } else if (arg.startsWith("--sandbox-id=")) {
- if (mSandboxId != null) {
- throw new IllegalArgumentException("Duplicate arg specified");
- }
- mSandboxId = arg.substring(arg.indexOf('=') + 1);
} else if (arg.startsWith("--usap-pool-enabled=")) {
mUsapPoolStatusSpecified = true;
mUsapPoolEnabled = Boolean.parseBoolean(arg.substring(arg.indexOf('=') + 1));
diff --git a/core/java/com/android/internal/os/ZygoteConnection.java b/core/java/com/android/internal/os/ZygoteConnection.java
index 2987b4e56fec..785256eb6351 100644
--- a/core/java/com/android/internal/os/ZygoteConnection.java
+++ b/core/java/com/android/internal/os/ZygoteConnection.java
@@ -267,8 +267,7 @@ class ZygoteConnection {
pid = Zygote.forkAndSpecialize(parsedArgs.mUid, parsedArgs.mGid, parsedArgs.mGids,
parsedArgs.mRuntimeFlags, rlimits, parsedArgs.mMountExternal, parsedArgs.mSeInfo,
parsedArgs.mNiceName, fdsToClose, fdsToIgnore, parsedArgs.mStartChildZygote,
- parsedArgs.mInstructionSet, parsedArgs.mAppDataDir, parsedArgs.mPackageName,
- parsedArgs.mPackagesForUid, parsedArgs.mSandboxId, parsedArgs.mTargetSdkVersion);
+ parsedArgs.mInstructionSet, parsedArgs.mAppDataDir, parsedArgs.mTargetSdkVersion);
try {
if (pid == 0) {
diff --git a/core/java/com/android/internal/policy/DecorView.java b/core/java/com/android/internal/policy/DecorView.java
index 5c1268ded94a..9a10210739e1 100644
--- a/core/java/com/android/internal/policy/DecorView.java
+++ b/core/java/com/android/internal/policy/DecorView.java
@@ -1174,12 +1174,16 @@ public class DecorView extends FrameLayout implements RootViewSurfaceTaker, Wind
// If we didn't request fullscreen layout, but we still got it because of the
// mForceWindowDrawsBarBackgrounds flag, also consume top inset.
+ // If we should always consume system bars, only consume that if the app wanted to go to
+ // fullscreen, as othrewise we can expect the app to handle it.
+ boolean fullscreen = (sysUiVisibility & SYSTEM_UI_FLAG_FULLSCREEN) != 0
+ || (attrs.flags & FLAG_FULLSCREEN) != 0;
boolean consumingStatusBar = (sysUiVisibility & SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN) == 0
&& (attrs.flags & FLAG_LAYOUT_IN_SCREEN) == 0
&& (attrs.flags & FLAG_LAYOUT_INSET_DECOR) == 0
&& mForceWindowDrawsBarBackgrounds
&& mLastTopInset != 0
- || mLastShouldAlwaysConsumeSystemBars;
+ || (mLastShouldAlwaysConsumeSystemBars && fullscreen);
int consumedTop = consumingStatusBar ? mLastTopInset : 0;
int consumedRight = consumingNavBar ? mLastRightInset : 0;
@@ -1226,6 +1230,10 @@ public class DecorView extends FrameLayout implements RootViewSurfaceTaker, Wind
* are set.
*/
private void updateBackgroundDrawable() {
+ // Background insets can be null if super constructor calls setBackgroundDrawable.
+ if (mBackgroundInsets == null) {
+ mBackgroundInsets = Insets.NONE;
+ }
if (mBackgroundInsets.equals(mLastBackgroundInsets)
&& mLastOriginalBackgroundDrawable == mOriginalBackgroundDrawable) {
return;
@@ -1549,10 +1557,14 @@ public class DecorView extends FrameLayout implements RootViewSurfaceTaker, Wind
return;
}
- setPadding(mFramePadding.left + mBackgroundPadding.left,
- mFramePadding.top + mBackgroundPadding.top,
- mFramePadding.right + mBackgroundPadding.right,
- mFramePadding.bottom + mBackgroundPadding.bottom);
+ // Fields can be null if super constructor calls setBackgroundDrawable.
+ Rect framePadding = mFramePadding != null ? mFramePadding : new Rect();
+ Rect backgroundPadding = mBackgroundPadding != null ? mBackgroundPadding : new Rect();
+
+ setPadding(framePadding.left + backgroundPadding.left,
+ framePadding.top + backgroundPadding.top,
+ framePadding.right + backgroundPadding.right,
+ framePadding.bottom + backgroundPadding.bottom);
requestLayout();
invalidate();
@@ -1572,8 +1584,8 @@ public class DecorView extends FrameLayout implements RootViewSurfaceTaker, Wind
if (bg != null) {
if (fg == null) {
opacity = bg.getOpacity();
- } else if (mFramePadding.left <= 0 && mFramePadding.top <= 0
- && mFramePadding.right <= 0 && mFramePadding.bottom <= 0) {
+ } else if (framePadding.left <= 0 && framePadding.top <= 0
+ && framePadding.right <= 0 && framePadding.bottom <= 0) {
// If the frame padding is zero, then we can be opaque
// if either the frame -or- the background is opaque.
int fop = fg.getOpacity();
diff --git a/core/jni/android_os_GraphicsEnvironment.cpp b/core/jni/android_os_GraphicsEnvironment.cpp
index 74ebb95b58c7..be9aee410d40 100644
--- a/core/jni/android_os_GraphicsEnvironment.cpp
+++ b/core/jni/android_os_GraphicsEnvironment.cpp
@@ -85,6 +85,10 @@ void setDebugLayersGLES_native(JNIEnv* env, jobject clazz, jstring layers) {
}
}
+void hintActivityLaunch_native(JNIEnv* env, jobject clazz) {
+ android::GraphicsEnv::getInstance().hintActivityLaunch();
+}
+
const JNINativeMethod g_methods[] = {
{ "getCanLoadSystemLibraries", "()I", reinterpret_cast<void*>(getCanLoadSystemLibraries_native) },
{ "setDriverPathAndSphalLibraries", "(Ljava/lang/String;Ljava/lang/String;)V", reinterpret_cast<void*>(setDriverPathAndSphalLibraries_native) },
@@ -94,6 +98,7 @@ const JNINativeMethod g_methods[] = {
{ "setLayerPaths", "(Ljava/lang/ClassLoader;Ljava/lang/String;)V", reinterpret_cast<void*>(setLayerPaths_native) },
{ "setDebugLayers", "(Ljava/lang/String;)V", reinterpret_cast<void*>(setDebugLayers_native) },
{ "setDebugLayersGLES", "(Ljava/lang/String;)V", reinterpret_cast<void*>(setDebugLayersGLES_native) },
+ { "hintActivityLaunch", "()V", reinterpret_cast<void*>(hintActivityLaunch_native) },
};
const char* const kGraphicsEnvironmentName = "android/os/GraphicsEnvironment";
diff --git a/core/jni/com_android_internal_os_Zygote.cpp b/core/jni/com_android_internal_os_Zygote.cpp
index 3d3203ed72dc..8ff16912e932 100644
--- a/core/jni/com_android_internal_os_Zygote.cpp
+++ b/core/jni/com_android_internal_os_Zygote.cpp
@@ -116,9 +116,6 @@ typedef const std::function<void(std::string)>& fail_fn_t;
static pid_t gSystemServerPid = 0;
-static const char kIsolatedStorage[] = "persist.sys.isolated_storage";
-static const char kIsolatedStorageSnapshot[] = "sys.isolated_storage_snapshot";
-
static constexpr const char* kZygoteClassName = "com/android/internal/os/Zygote";
static jclass gZygoteClass;
static jmethodID gCallPostForkSystemServerHooks;
@@ -623,249 +620,10 @@ static int UnmountTree(const char* path) {
return 0;
}
-static void CreateDir(const std::string& dir,
- mode_t mode, uid_t uid, gid_t gid,
- fail_fn_t fail_fn) {
- if (TEMP_FAILURE_RETRY(access(dir.c_str(), F_OK)) == 0) {
- return;
- } else if (errno != ENOENT) {
- fail_fn(CREATE_ERROR("Failed to stat %s: %s", dir.c_str(), strerror(errno)));
- }
- if (fs_prepare_dir(dir.c_str(), mode, uid, gid) != 0) {
- fail_fn(CREATE_ERROR("fs_prepare_dir failed on %s: %s",
- dir.c_str(), strerror(errno)));
- }
-}
-
-static void CreatePkgSandboxTarget(userid_t user_id, fail_fn_t fail_fn) {
- ATRACE_CALL();
-
- // Create /mnt/user/0/package
- std::string pkg_sandbox_dir = StringPrintf("/mnt/user/%d", user_id);
- CreateDir(pkg_sandbox_dir, 0751, AID_ROOT, AID_ROOT, fail_fn);
-
- StringAppendF(&pkg_sandbox_dir, "/package");
- CreateDir(pkg_sandbox_dir, 0755, AID_ROOT, AID_ROOT, fail_fn);
-}
-
-static void BindMount(const std::string& source_dir, const std::string& target_dir,
- fail_fn_t fail_fn) {
- if (TEMP_FAILURE_RETRY(mount(source_dir.c_str(), target_dir.c_str(), nullptr,
- MS_BIND, nullptr)) == -1) {
- fail_fn(CREATE_ERROR("Failed to mount %s to %s: %s",
- source_dir.c_str(), target_dir.c_str(), strerror(errno)));
- }
-}
-
-static void MountPkgSpecificDir(const std::string& mnt_source_root,
- const std::string& mnt_target_root,
- const std::string& package_name,
- uid_t uid,
- const char* dir_name,
- fail_fn_t fail_fn) {
- ATRACE_CALL();
-
- std::string mnt_source_dir = StringPrintf("%s/Android/%s/%s",
- mnt_source_root.c_str(), dir_name, package_name.c_str());
-
- std::string mnt_target_dir = StringPrintf("%s/Android/%s/%s",
- mnt_target_root.c_str(), dir_name, package_name.c_str());
-
- BindMount(mnt_source_dir, mnt_target_dir, fail_fn);
-}
-
-static void CreateSubDirs(int parent_fd, const std::string& parent_path,
- const std::vector<std::string>& sub_dirs,
- fail_fn_t fail_fn) {
- ATRACE_CALL();
-
- for (auto& dir_name : sub_dirs) {
- struct stat sb;
- if (TEMP_FAILURE_RETRY(fstatat(parent_fd, dir_name.c_str(), &sb, 0)) == 0) {
- if (S_ISDIR(sb.st_mode)) {
- continue;
- } else if (TEMP_FAILURE_RETRY(unlinkat(parent_fd, dir_name.c_str(), 0)) == -1) {
- fail_fn(CREATE_ERROR("Failed to unlinkat on %s/%s: %s",
- parent_path.c_str(), dir_name.c_str(), strerror(errno)));
- }
- } else if (errno != ENOENT) {
- fail_fn(CREATE_ERROR("Failed to fstatat on %s/%s: %s",
- parent_path.c_str(), dir_name.c_str(), strerror(errno)));
- }
- if (TEMP_FAILURE_RETRY(mkdirat(parent_fd, dir_name.c_str(), 0700)) == -1 && errno != EEXIST) {
- fail_fn(CREATE_ERROR("Failed to mkdirat on %s/%s: %s",
- parent_path.c_str(), dir_name.c_str(), strerror(errno)));
- }
- }
-}
-
-static void EnsurePkgSpecificDirs(const std::string& path,
- const std::vector<std::string>& package_names,
- bool create_sandbox_dir,
- fail_fn_t fail_fn) {
- ATRACE_CALL();
-
- std::string android_dir = StringPrintf("%s/Android", path.c_str());
- android::base::unique_fd android_fd(open(android_dir.c_str(),
- O_RDONLY | O_DIRECTORY | O_CLOEXEC));
- if (android_fd.get() < 0) {
- if (errno == ENOENT || errno == ENOTDIR) {
- if (errno == ENOTDIR && TEMP_FAILURE_RETRY(unlink(android_dir.c_str())) == -1) {
- fail_fn(CREATE_ERROR("Failed to unlink %s: %s",
- android_dir.c_str(), strerror(errno)));
- }
- if (TEMP_FAILURE_RETRY(mkdir(android_dir.c_str(), 0700)) == -1
- && errno != EEXIST) {
- fail_fn(CREATE_ERROR("Failed to mkdir %s: %s",
- android_dir.c_str(), strerror(errno)));
- }
- android_fd.reset(open(android_dir.c_str(), O_RDONLY | O_DIRECTORY | O_CLOEXEC));
- }
-
- if (android_fd.get() < 0) {
- fail_fn(CREATE_ERROR("Failed to open %s: %s", android_dir.c_str(), strerror(errno)));
- }
- }
-
- std::vector<std::string> data_media_obb_dirs = {"data", "media", "obb"};
- if (create_sandbox_dir) {
- data_media_obb_dirs.push_back("sandbox");
- }
- CreateSubDirs(android_fd.get(), android_dir, data_media_obb_dirs, fail_fn);
- if (create_sandbox_dir) {
- data_media_obb_dirs.pop_back();
- }
- for (auto& dir_name : data_media_obb_dirs) {
- std::string data_dir = StringPrintf("%s/%s", android_dir.c_str(), dir_name.c_str());
- android::base::unique_fd data_fd(openat(android_fd, dir_name.c_str(),
- O_RDONLY | O_DIRECTORY | O_CLOEXEC));
- if (data_fd.get() < 0) {
- fail_fn(CREATE_ERROR("Failed to openat %s/%s: %s",
- android_dir.c_str(), dir_name.c_str(), strerror(errno)));
- }
- CreateSubDirs(data_fd.get(), data_dir, package_names, fail_fn);
- }
-}
-
-static void CreatePkgSandboxSource(const std::string& sandbox_source, fail_fn_t fail_fn) {
- ATRACE_CALL();
-
- struct stat sb;
- if (TEMP_FAILURE_RETRY(stat(sandbox_source.c_str(), &sb)) == 0) {
- if (S_ISDIR(sb.st_mode)) {
- return;
- } else if (TEMP_FAILURE_RETRY(unlink(sandbox_source.c_str())) == -1) {
- fail_fn(CREATE_ERROR("Failed to unlink %s: %s",
- sandbox_source.c_str(), strerror(errno)));
- }
- } else if (errno != ENOENT) {
- fail_fn(CREATE_ERROR("Failed to stat %s: %s",
- sandbox_source.c_str(), strerror(errno)));
- }
- if (TEMP_FAILURE_RETRY(mkdir(sandbox_source.c_str(), 0700)) == -1 && errno != EEXIST) {
- fail_fn(CREATE_ERROR("Failed to mkdir %s: %s",
- sandbox_source.c_str(), strerror(errno)));
- }
-}
-
-static void PreparePkgSpecificDirs(const std::vector<std::string>& package_names,
- bool mount_all_obbs, const std::string& sandbox_id,
- userid_t user_id, uid_t uid, fail_fn_t fail_fn) {
- ATRACE_CALL();
-
- std::unique_ptr<DIR, decltype(&closedir)> dirp(opendir("/storage"), closedir);
- if (!dirp) {
- fail_fn(CREATE_ERROR("Failed to opendir /storage: %s", strerror(errno)));
- }
- struct dirent* ent;
- while ((ent = readdir(dirp.get()))) {
- if (!strcmp(ent->d_name, ".") || !strcmp(ent->d_name, "..") || !strcmp(ent->d_name, "self")) {
- continue;
- }
- std::string label(ent->d_name);
-
- std::string mnt_source = StringPrintf("/mnt/runtime/write/%s", label.c_str());
- std::string mnt_target = StringPrintf("/storage/%s", label.c_str());
- if (label == "emulated") {
- StringAppendF(&mnt_source, "/%d", user_id);
- StringAppendF(&mnt_target, "/%d", user_id);
- }
-
- if (TEMP_FAILURE_RETRY(access(mnt_source.c_str(), F_OK)) == -1) {
- ALOGE("Can't access %s: %s", mnt_source.c_str(), strerror(errno));
- continue;
- } else if (TEMP_FAILURE_RETRY(access(mnt_target.c_str(), F_OK)) == -1) {
- ALOGE("Can't access %s: %s", mnt_target.c_str(), strerror(errno));
- continue;
- }
-
- // Ensure /mnt/runtime/write/emulated/0/Android/{data,media,obb}
- EnsurePkgSpecificDirs(mnt_source, package_names, true, fail_fn);
-
- std::string sandbox_source = StringPrintf("%s/Android/sandbox/%s",
- mnt_source.c_str(), sandbox_id.c_str());
- CreatePkgSandboxSource(sandbox_source, fail_fn);
- BindMount(sandbox_source, mnt_target, fail_fn);
-
- // Ensure /storage/emulated/0/Android/{data,media,obb}
- EnsurePkgSpecificDirs(mnt_target, package_names, false, fail_fn);
- for (auto& package : package_names) {
- MountPkgSpecificDir(mnt_source, mnt_target, package, uid, "data", fail_fn);
- MountPkgSpecificDir(mnt_source, mnt_target, package, uid, "media", fail_fn);
- if (!mount_all_obbs) {
- MountPkgSpecificDir(mnt_source, mnt_target, package, uid, "obb", fail_fn);
- }
- }
-
- if (mount_all_obbs) {
- StringAppendF(&mnt_source, "/Android/obb");
- StringAppendF(&mnt_target, "/Android/obb");
- BindMount(mnt_source, mnt_target, fail_fn);
- }
- }
-}
-
-static void HandleMountModeInstaller(int mount_mode,
- userid_t user_id,
- const std::string& sandbox_id,
- fail_fn_t fail_fn) {
- ATRACE_CALL();
-
- std::string obb_mount_dir = StringPrintf("/mnt/user/%d/obb_mount", user_id);
- std::string obb_mount_file = StringPrintf("%s/%s", obb_mount_dir.c_str(), sandbox_id.c_str());
- if (mount_mode == MOUNT_EXTERNAL_INSTALLER) {
- if (TEMP_FAILURE_RETRY(access(obb_mount_file.c_str(), F_OK)) != -1) {
- return;
- } else if (errno != ENOENT) {
- fail_fn(CREATE_ERROR("Failed to access %s: %s", obb_mount_file.c_str(), strerror(errno)));
- }
- if (fs_prepare_dir(obb_mount_dir.c_str(), 0700, AID_ROOT, AID_ROOT) != 0) {
- fail_fn(CREATE_ERROR("Failed to fs_prepare_dir %s: %s",
- obb_mount_dir.c_str(), strerror(errno)));
- }
- const android::base::unique_fd fd(TEMP_FAILURE_RETRY(
- open(obb_mount_file.c_str(), O_RDWR | O_CREAT, 0600)));
- if (fd.get() < 0) {
- fail_fn(CREATE_ERROR("Failed to create %s: %s", obb_mount_file.c_str(), strerror(errno)));
- }
- } else {
- if (TEMP_FAILURE_RETRY(access(obb_mount_file.c_str(), F_OK)) != -1) {
- if (TEMP_FAILURE_RETRY(unlink(obb_mount_file.c_str())) == -1) {
- fail_fn(CREATE_ERROR("Failed to unlink %s: %s",
- obb_mount_dir.c_str(), strerror(errno)));
- }
- } else if (errno != ENOENT) {
- fail_fn(CREATE_ERROR("Failed to access %s: %s", obb_mount_file.c_str(), strerror(errno)));
- }
- }
-}
-
// Create a private mount namespace and bind mount appropriate emulated
// storage for the given user.
static void MountEmulatedStorage(uid_t uid, jint mount_mode,
- bool force_mount_namespace, const std::string& package_name,
- const std::vector<std::string>& packages_for_uid,
- const std::string& sandbox_id,
+ bool force_mount_namespace,
fail_fn_t fail_fn) {
// See storage config details at http://source.android.com/tech/storage/
ATRACE_CALL();
@@ -896,73 +654,25 @@ static void MountEmulatedStorage(uid_t uid, jint mount_mode,
return;
}
- if (/* DISABLES CODE */ (false)
- && GetBoolProperty(kIsolatedStorageSnapshot, GetBoolProperty(kIsolatedStorage, true))) {
- if (mount_mode == MOUNT_EXTERNAL_FULL || mount_mode == MOUNT_EXTERNAL_LEGACY) {
- storage_source = (mount_mode == MOUNT_EXTERNAL_FULL)
- ? "/mnt/runtime/full" : "/mnt/runtime/write";
- if (TEMP_FAILURE_RETRY(mount(storage_source.string(), "/storage",
- NULL, MS_BIND | MS_REC | MS_SLAVE, NULL)) == -1) {
- fail_fn(CREATE_ERROR("Failed to mount %s to /storage: %s",
- storage_source.string(),
- strerror(errno)));
- }
-
- // Mount user-specific symlink helper into place
- userid_t user_id = multiuser_get_user_id(uid);
- const String8 user_source(String8::format("/mnt/user/%d", user_id));
- if (fs_prepare_dir(user_source.string(), 0751, 0, 0) == -1) {
- fail_fn(CREATE_ERROR("fs_prepare_dir failed on %s (%s)",
- user_source.string(), strerror(errno)));
- }
-
- if (TEMP_FAILURE_RETRY(mount(user_source.string(), "/storage/self", nullptr, MS_BIND,
- nullptr)) == -1) {
- fail_fn(CREATE_ERROR("Failed to mount %s to /storage/self: %s",
- user_source.string(),
- strerror(errno)));
- }
- } else {
- if (package_name.empty() || sandbox_id.empty()) {
- return;
- }
-
- userid_t user_id = multiuser_get_user_id(uid);
- CreatePkgSandboxTarget(user_id, fail_fn);
-
- std::string pkg_sandbox_dir = StringPrintf("/mnt/user/%d/package", user_id);
- if (TEMP_FAILURE_RETRY(mount(pkg_sandbox_dir.c_str(), "/storage",
- nullptr, MS_BIND | MS_REC | MS_SLAVE, nullptr)) == -1) {
- fail_fn(CREATE_ERROR("Failed to mount %s to /storage: %s",
- pkg_sandbox_dir.c_str(), strerror(errno)));
- }
-
- HandleMountModeInstaller(mount_mode, user_id, sandbox_id, fail_fn);
-
- PreparePkgSpecificDirs(packages_for_uid,
- mount_mode == MOUNT_EXTERNAL_INSTALLER, sandbox_id, user_id, uid, fail_fn);
- }
- } else {
- if (TEMP_FAILURE_RETRY(mount(storage_source.string(), "/storage", nullptr,
- MS_BIND | MS_REC | MS_SLAVE, nullptr)) == -1) {
- fail_fn(CREATE_ERROR("Failed to mount %s to /storage: %s",
- storage_source.string(),
- strerror(errno)));
- }
+ if (TEMP_FAILURE_RETRY(mount(storage_source.string(), "/storage", nullptr,
+ MS_BIND | MS_REC | MS_SLAVE, nullptr)) == -1) {
+ fail_fn(CREATE_ERROR("Failed to mount %s to /storage: %s",
+ storage_source.string(),
+ strerror(errno)));
+ }
- // Mount user-specific symlink helper into place
- userid_t user_id = multiuser_get_user_id(uid);
- const String8 user_source(String8::format("/mnt/user/%d", user_id));
- if (fs_prepare_dir(user_source.string(), 0751, 0, 0) == -1) {
- fail_fn(CREATE_ERROR("fs_prepare_dir failed on %s",
- user_source.string()));
- }
+ // Mount user-specific symlink helper into place
+ userid_t user_id = multiuser_get_user_id(uid);
+ const String8 user_source(String8::format("/mnt/user/%d", user_id));
+ if (fs_prepare_dir(user_source.string(), 0751, 0, 0) == -1) {
+ fail_fn(CREATE_ERROR("fs_prepare_dir failed on %s",
+ user_source.string()));
+ }
- if (TEMP_FAILURE_RETRY(mount(user_source.string(), "/storage/self",
- nullptr, MS_BIND, nullptr)) == -1) {
- fail_fn(CREATE_ERROR("Failed to mount %s to /storage/self: %s",
- user_source.string(), strerror(errno)));
- }
+ if (TEMP_FAILURE_RETRY(mount(user_source.string(), "/storage/self",
+ nullptr, MS_BIND, nullptr)) == -1) {
+ fail_fn(CREATE_ERROR("Failed to mount %s to /storage/self: %s",
+ user_source.string(), strerror(errno)));
}
}
@@ -1136,45 +846,6 @@ static std::optional<std::vector<int>> ExtractJIntArray(JNIEnv* env,
}
/**
- * A helper method for converting managed string arrays to native vectors. A
- * fatal error is generated if a problem is encountered in extracting a non-null array.
- *
- * @param env Managed runtime environment
- * @param process_name A native representation of the process name
- * @param managed_process_name A managed representation of the process name
- * @param managed_array The managed string array to extract
- *
- * @return An empty option if the managed array is null. A optional-wrapped
- * vector otherwise.
- */
-static std::optional<std::vector<std::string>> ExtractJStringArray(JNIEnv* env,
- const char* process_name,
- jstring managed_process_name,
- jobjectArray managed_array) {
- if (managed_array == nullptr) {
- return std::nullopt;
- } else {
- jsize element_count = env->GetArrayLength(managed_array);
- std::vector<std::string> native_string_vector;
- native_string_vector.reserve(element_count);
-
- for (jsize array_index = 0; array_index < element_count; ++array_index) {
- jstring managed_string = (jstring) env->GetObjectArrayElement(managed_array, array_index);
- auto native_string = ExtractJString(env, process_name, managed_process_name, managed_string);
-
- if (LIKELY(native_string.has_value())) {
- native_string_vector.emplace_back(std::move(native_string.value()));
- } else {
- ZygoteFailure(env, process_name, managed_process_name,
- "Null string found in managed string array.");
- }
- }
-
- return std::move(native_string_vector);
- }
-}
-
-/**
* A utility function for blocking signals.
*
* @param signum Signal number to block
@@ -1287,9 +958,7 @@ static void SpecializeCommon(JNIEnv* env, uid_t uid, gid_t gid, jintArray gids,
jint mount_external, jstring managed_se_info,
jstring managed_nice_name, bool is_system_server,
bool is_child_zygote, jstring managed_instruction_set,
- jstring managed_app_data_dir, jstring managed_package_name,
- jobjectArray managed_pacakges_for_uid,
- jstring managed_sandbox_id) {
+ jstring managed_app_data_dir) {
const char* process_name = is_system_server ? "system_server" : "zygote";
auto fail_fn = std::bind(ZygoteFailure, env, process_name, managed_nice_name, _1);
auto extract_fn = std::bind(ExtractJString, env, process_name, managed_nice_name, _1);
@@ -1298,8 +967,6 @@ static void SpecializeCommon(JNIEnv* env, uid_t uid, gid_t gid, jintArray gids,
auto nice_name = extract_fn(managed_nice_name);
auto instruction_set = extract_fn(managed_instruction_set);
auto app_data_dir = extract_fn(managed_app_data_dir);
- auto package_name = extract_fn(managed_package_name);
- auto sandbox_id = extract_fn(managed_sandbox_id);
// Keep capabilities across UID change, unless we're staying root.
if (uid != 0) {
@@ -1325,20 +992,7 @@ static void SpecializeCommon(JNIEnv* env, uid_t uid, gid_t gid, jintArray gids,
ALOGW("Native bridge will not be used because managed_app_data_dir == nullptr.");
}
- if (!package_name.has_value()) {
- if (is_system_server) {
- package_name.emplace("android");
- } else {
- package_name.emplace("");
- }
- }
-
- std::vector<std::string> packages_for_uid =
- ExtractJStringArray(env, process_name, managed_nice_name, managed_pacakges_for_uid).
- value_or(std::vector<std::string>());
-
- MountEmulatedStorage(uid, mount_external, use_native_bridge, package_name.value(),
- packages_for_uid, sandbox_id.value_or(""), fail_fn);
+ MountEmulatedStorage(uid, mount_external, use_native_bridge, fail_fn);
// If this zygote isn't root, it won't be able to create a process group,
// since the directory is owned by root.
@@ -1681,8 +1335,7 @@ static jint com_android_internal_os_Zygote_nativeForkAndSpecialize(
jint runtime_flags, jobjectArray rlimits,
jint mount_external, jstring se_info, jstring nice_name,
jintArray managed_fds_to_close, jintArray managed_fds_to_ignore, jboolean is_child_zygote,
- jstring instruction_set, jstring app_data_dir, jstring package_name,
- jobjectArray packages_for_uid, jstring sandbox_id) {
+ jstring instruction_set, jstring app_data_dir) {
jlong capabilities = CalculateCapabilities(env, uid, gid, gids, is_child_zygote);
if (UNLIKELY(managed_fds_to_close == nullptr)) {
@@ -1713,8 +1366,7 @@ static jint com_android_internal_os_Zygote_nativeForkAndSpecialize(
SpecializeCommon(env, uid, gid, gids, runtime_flags, rlimits,
capabilities, capabilities,
mount_external, se_info, nice_name, false,
- is_child_zygote == JNI_TRUE, instruction_set, app_data_dir,
- package_name, packages_for_uid, sandbox_id);
+ is_child_zygote == JNI_TRUE, instruction_set, app_data_dir);
}
return pid;
}
@@ -1740,7 +1392,7 @@ static jint com_android_internal_os_Zygote_nativeForkSystemServer(
SpecializeCommon(env, uid, gid, gids, runtime_flags, rlimits,
permitted_capabilities, effective_capabilities,
MOUNT_EXTERNAL_DEFAULT, nullptr, nullptr, true,
- false, nullptr, nullptr, nullptr, nullptr, nullptr);
+ false, nullptr, nullptr);
} else if (pid > 0) {
// The zygote process checks whether the child process has died or not.
ALOGI("System server process %d has been created", pid);
@@ -1859,16 +1511,13 @@ static void com_android_internal_os_Zygote_nativeSpecializeAppProcess(
JNIEnv* env, jclass, jint uid, jint gid, jintArray gids,
jint runtime_flags, jobjectArray rlimits,
jint mount_external, jstring se_info, jstring nice_name,
- jboolean is_child_zygote, jstring instruction_set, jstring app_data_dir,
- jstring package_name, jobjectArray packages_for_uid,
- jstring sandbox_id) {
+ jboolean is_child_zygote, jstring instruction_set, jstring app_data_dir) {
jlong capabilities = CalculateCapabilities(env, uid, gid, gids, is_child_zygote);
SpecializeCommon(env, uid, gid, gids, runtime_flags, rlimits,
capabilities, capabilities,
mount_external, se_info, nice_name, false,
- is_child_zygote == JNI_TRUE, instruction_set, app_data_dir,
- package_name, packages_for_uid, sandbox_id);
+ is_child_zygote == JNI_TRUE, instruction_set, app_data_dir);
}
/**
@@ -2031,7 +1680,7 @@ static jboolean com_android_internal_os_Zygote_nativeDisableExecuteOnly(JNIEnv*
static const JNINativeMethod gMethods[] = {
{ "nativeForkAndSpecialize",
- "(II[II[[IILjava/lang/String;Ljava/lang/String;[I[IZLjava/lang/String;Ljava/lang/String;Ljava/lang/String;[Ljava/lang/String;Ljava/lang/String;)I",
+ "(II[II[[IILjava/lang/String;Ljava/lang/String;[I[IZLjava/lang/String;Ljava/lang/String;)I",
(void *) com_android_internal_os_Zygote_nativeForkAndSpecialize },
{ "nativeForkSystemServer", "(II[II[[IJJ)I",
(void *) com_android_internal_os_Zygote_nativeForkSystemServer },
@@ -2044,7 +1693,7 @@ static const JNINativeMethod gMethods[] = {
{ "nativeForkUsap", "(II[I)I",
(void *) com_android_internal_os_Zygote_nativeForkUsap },
{ "nativeSpecializeAppProcess",
- "(II[II[[IILjava/lang/String;Ljava/lang/String;ZLjava/lang/String;Ljava/lang/String;Ljava/lang/String;[Ljava/lang/String;Ljava/lang/String;)V",
+ "(II[II[[IILjava/lang/String;Ljava/lang/String;ZLjava/lang/String;Ljava/lang/String;)V",
(void *) com_android_internal_os_Zygote_nativeSpecializeAppProcess },
{ "nativeInitNativeState", "(Z)V",
(void *) com_android_internal_os_Zygote_nativeInitNativeState },
diff --git a/core/proto/android/app/settings_enums.proto b/core/proto/android/app/settings_enums.proto
index 1160b357a1fb..36eb4c46faa8 100644
--- a/core/proto/android/app/settings_enums.proto
+++ b/core/proto/android/app/settings_enums.proto
@@ -666,6 +666,11 @@ enum Action {
//ACTION: Log result for each card's eligibility check
ACTION_CONTEXTUAL_CARD_ELIGIBILITY = 1686;
+ // ACTION: Display white balance setting enabled or disabled.
+ // CATEGORY: SETTINGS
+ // OS: Q
+ ACTION_DISPLAY_WHITE_BALANCE_SETTING_CHANGED = 1703;
+
// ACTION: Share a Wi-Fi network by generating a QR code
ACTION_SETTINGS_SHARE_WIFI_QR_CODE = 1710;
@@ -674,6 +679,15 @@ enum Action {
// ACTION: Share Wi-Fi hotspot by generating a QR code
ACTION_SETTINGS_SHARE_WIFI_HOTSPOT_QR_CODE = 1712;
+
+ // ACTION: Settings > Initialize Search bar > Verify Slice > Invalid data
+ ACTION_VERIFY_SLICE_ERROR_INVALID_DATA = 1725;
+
+ // ACTION: Settings > Initialize Search bar > Verify Slice > Parsing error
+ ACTION_VERIFY_SLICE_PARSING_ERROR = 1726;
+
+ // ACTION: Settings > Initialize Search bar > Verify Slice > Other exception
+ ACTION_VERIFY_SLICE_OTHER_EXCEPTION = 1727;
}
/**
@@ -2341,11 +2355,6 @@ enum PageId {
// Open: Settings > app > bubble settings > confirmation dialog
DIALOG_APP_BUBBLE_SETTINGS = 1702;
- // ACTION: Display white balance setting enabled or disabled.
- // CATEGORY: SETTINGS
- // OS: Q
- ACTION_DISPLAY_WHITE_BALANCE_SETTING_CHANGED = 1703;
-
// OPEN: Settings > Pick SIM dialog
DIALOG_SIM_LIST = 1707;
diff --git a/core/res/res/anim/lock_in.xml b/core/res/res/anim/lock_in.xml
index e687f9f2d87e..c7014e80d33e 100755..100644
--- a/core/res/res/anim/lock_in.xml
+++ b/core/res/res/anim/lock_in.xml
@@ -1,5 +1,4 @@
-<!--
- Copyright (C) 2019 The Android Open Source Project
+<!-- Copyright (C) 2019 The Android Open Source Project
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
@@ -16,102 +15,116 @@
<animated-vector xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:aapt="http://schemas.android.com/aapt">
<aapt:attr name="android:drawable">
- <vector android:height="32dp" android:width="32dp" android:viewportHeight="32"
+ <vector android:height="42dp" android:width="32dp" android:viewportHeight="42"
android:viewportWidth="32">
<group android:name="_R_G">
- <group android:name="_R_G_L_2_G_N_2_N_1_T_0" android:translateX="16"
- android:translateY="16" android:scaleX="1.3" android:scaleY="1.3">
- <group android:name="_R_G_L_2_G_N_2_T_0" android:translateX="-2.25"
- android:translateY="0.75" android:pivotX="2.25" android:pivotY="2.25"
- android:scaleX="0" android:scaleY="0">
- <group android:name="_R_G_L_2_G_T_1" android:translateX="2.25"
- android:translateY="2.373" android:scaleX="0.12346"
- android:scaleY="0.12346">
- <group android:name="_R_G_L_2_G" android:translateY="32">
- <path android:name="_R_G_L_2_G_D_0_P_0" android:fillColor="#ff0000"
- android:fillAlpha="0" android:fillType="nonZero"
- android:trimPathStart="0.14" android:trimPathEnd="0.89"
- android:trimPathOffset="0"
- android:pathData=" M-28.21 -31.92 C-28.21,-31.92 -27.85,-48.38 -27.97,-55.48 C-28,-57.63 -23.5,-79.87 -0.75,-79.82 C22.77,-79.76 27.75,-59.37 27.72,-58.27 C27.55,-52.88 27.97,-31.67 27.97,-31.67 "/>
- <path android:name="_R_G_L_2_G_D_1_P_0"
- android:strokeColor="#000" android:strokeLineCap="round"
- android:strokeLineJoin="round" android:strokeWidth="16"
- android:strokeAlpha="1" android:trimPathStart="0.14"
- android:trimPathEnd="0.89" android:trimPathOffset="0"
- android:pathData=" M-28.21 -31.92 C-28.21,-31.92 -27.85,-48.38 -27.97,-55.48 C-28,-57.63 -23.5,-79.87 -0.75,-79.82 C22.77,-79.76 27.75,-59.37 27.72,-58.27 C27.55,-52.88 27.97,-31.67 27.97,-31.67 "/>
- </group>
- </group>
- </group>
+ <group android:name="_R_G_L_2_G" android:translateX="1.6669999999999998"
+ android:translateY="11.992999999999999" android:pivotX="14.333"
+ android:pivotY="13" android:scaleX="0" android:scaleY="0">
+ <path android:name="_R_G_L_2_G_D_0_P_0" android:strokeColor="#ffffff"
+ android:strokeLineCap="round" android:strokeLineJoin="round"
+ android:strokeWidth="2" android:strokeAlpha="1"
+ android:pathData=" M22.33 21 C22.33,21 6.33,21 6.33,21 C5.6,21 5,20.4 5,19.67 C5,19.67 5,6.33 5,6.33 C5,5.6 5.6,5 6.33,5 C6.33,5 22.33,5 22.33,5 C23.07,5 23.67,5.6 23.67,6.33 C23.67,6.33 23.67,19.67 23.67,19.67 C23.67,20.4 23.07,21 22.33,21c "/>
</group>
- <group android:name="_R_G_L_1_G_N_1_T_0" android:translateX="16"
- android:translateY="16" android:scaleX="1.3" android:scaleY="1.3">
- <group android:name="_R_G_L_1_G" android:translateX="-8.25"
- android:translateY="-4.25" android:pivotX="8.25" android:pivotY="7.25"
- android:scaleX="0" android:scaleY="0">
- <path android:name="_R_G_L_1_G_D_0_P_0" android:fillColor="#000"
+ <group android:name="_R_G_L_1_G_N_4_T_0" android:translateX="1.6669999999999998"
+ android:translateY="11.992999999999999" android:pivotX="14.333"
+ android:pivotY="13" android:scaleX="0" android:scaleY="0">
+ <group android:name="_R_G_L_1_G" android:translateX="11.583"
+ android:translateY="10.257">
+ <path android:name="_R_G_L_1_G_D_0_P_0" android:fillColor="#ffffff"
android:fillAlpha="1" android:fillType="nonZero"
- android:pathData=" M14.25 0.25 C14.25,0.25 12.75,0.25 12.75,0.25 C12.75,0.25 10.75,0.25 10.75,0.25 C10.75,0.25 5.75,0.25 5.75,0.25 C5.75,0.25 3.75,0.25 3.75,0.25 C3.75,0.25 2.25,0.25 2.25,0.25 C1.15,0.25 0.25,1.15 0.25,2.25 C0.25,2.25 0.25,12.25 0.25,12.25 C0.25,13.35 1.15,14.25 2.25,14.25 C2.25,14.25 14.25,14.25 14.25,14.25 C15.35,14.25 16.25,13.35 16.25,12.25 C16.25,12.25 16.25,2.25 16.25,2.25 C16.25,1.15 15.35,0.25 14.25,0.25c M14.25 12.25 C14.25,12.25 2.25,12.25 2.25,12.25 C2.25,12.25 2.25,2.25 2.25,2.25 C2.25,2.25 3.75,2.25 3.75,2.25 C3.75,2.25 12.75,2.25 12.75,2.25 C12.75,2.25 14.25,2.25 14.25,2.25 C14.25,2.25 14.25,12.25 14.25,12.25c "/>
+ android:pathData=" M2.75 0.25 C4.13,0.25 5.25,1.37 5.25,2.75 C5.25,4.13 4.13,5.25 2.75,5.25 C1.37,5.25 0.25,4.13 0.25,2.75 C0.25,1.37 1.37,0.25 2.75,0.25c "/>
</group>
</group>
- <group android:name="_R_G_L_0_G_N_1_T_0" android:translateX="16"
- android:translateY="16" android:scaleX="1.3" android:scaleY="1.3">
- <group android:name="_R_G_L_0_G" android:translateX="-2.25"
- android:translateY="0.75" android:pivotX="2.25" android:pivotY="2.25"
- android:scaleX="0" android:scaleY="0">
- <path android:name="_R_G_L_0_G_D_0_P_0" android:fillColor="#000"
- android:fillAlpha="1" android:fillType="nonZero"
- android:pathData=" M2.25 0.25 C3.35,0.25 4.25,1.15 4.25,2.25 C4.25,3.35 3.35,4.25 2.25,4.25 C1.15,4.25 0.25,3.35 0.25,2.25 C0.25,1.15 1.15,0.25 2.25,0.25c "/>
+ <group android:name="_R_G_L_0_G_N_4_T_0" android:translateX="1.6669999999999998"
+ android:translateY="11.992999999999999" android:pivotX="14.333"
+ android:pivotY="13" android:scaleX="0" android:scaleY="0">
+ <group android:name="_R_G_L_0_G_T_1" android:translateX="14.333"
+ android:translateY="3.172">
+ <group android:name="_R_G_L_0_G" android:translateX="-9.667"
+ android:translateY="-9.667">
+ <path android:name="_R_G_L_0_G_D_0_P_0" android:strokeColor="#ffffff"
+ android:strokeLineCap="round" android:strokeLineJoin="round"
+ android:strokeWidth="2" android:strokeAlpha="1"
+ android:trimPathStart="0.14" android:trimPathEnd="0.89"
+ android:trimPathOffset="0"
+ android:pathData=" M14.33 14.33 C14.33,14.33 14.33,9.67 14.33,9.67 C14.33,7.09 12.24,5 9.67,5 C7.09,5 5,7.09 5,9.67 C5,9.67 5,14.33 5,14.33 "/>
+ </group>
</group>
</group>
</group>
<group android:name="time_group"/>
</vector>
</aapt:attr>
- <target android:name="_R_G_L_2_G_D_0_P_0">
+ <target android:name="_R_G_L_2_G">
<aapt:attr name="android:animation">
<set android:ordering="together">
- <objectAnimator android:propertyName="trimPathStart" android:duration="50"
- android:startOffset="0" android:valueFrom="0.14"
- android:valueTo="0.14" android:valueType="floatType">
+ <objectAnimator android:propertyName="scaleX" android:duration="233"
+ android:startOffset="0" android:valueFrom="0" android:valueTo="1.02"
+ android:valueType="floatType">
<aapt:attr name="android:interpolator">
- <pathInterpolator
- android:pathData="M 0.0,0.0 c0.167,0.167 0.833,0.833 1.0,1.0"/>
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.001,0 0.438,1 1.0,1.0"/>
</aapt:attr>
</objectAnimator>
- <objectAnimator android:propertyName="trimPathStart" android:duration="67"
- android:startOffset="50" android:valueFrom="0.14"
- android:valueTo="0" android:valueType="floatType">
+ <objectAnimator android:propertyName="scaleY" android:duration="233"
+ android:startOffset="0" android:valueFrom="0" android:valueTo="1.02"
+ android:valueType="floatType">
<aapt:attr name="android:interpolator">
- <pathInterpolator
- android:pathData="M 0.0,0.0 c0.167,0.167 0.833,0.833 1.0,1.0"/>
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.001,0 0.438,1 1.0,1.0"/>
+ </aapt:attr>
+ </objectAnimator>
+ <objectAnimator android:propertyName="scaleX" android:duration="117"
+ android:startOffset="233" android:valueFrom="1.02"
+ android:valueTo="1" android:valueType="floatType">
+ <aapt:attr name="android:interpolator">
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.565,1 1.0,1.0"/>
+ </aapt:attr>
+ </objectAnimator>
+ <objectAnimator android:propertyName="scaleY" android:duration="117"
+ android:startOffset="233" android:valueFrom="1.02"
+ android:valueTo="1" android:valueType="floatType">
+ <aapt:attr name="android:interpolator">
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.565,1 1.0,1.0"/>
</aapt:attr>
</objectAnimator>
</set>
</aapt:attr>
</target>
- <target android:name="_R_G_L_2_G_D_0_P_0">
+ <target android:name="_R_G_L_1_G_N_4_T_0">
<aapt:attr name="android:animation">
<set android:ordering="together">
- <objectAnimator android:propertyName="trimPathEnd" android:duration="50"
- android:startOffset="0" android:valueFrom="0.89"
- android:valueTo="0.89" android:valueType="floatType">
+ <objectAnimator android:propertyName="scaleX" android:duration="233"
+ android:startOffset="0" android:valueFrom="0" android:valueTo="1.02"
+ android:valueType="floatType">
<aapt:attr name="android:interpolator">
- <pathInterpolator
- android:pathData="M 0.0,0.0 c0.167,0.167 0.833,0.833 1.0,1.0"/>
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.001,0 0.438,1 1.0,1.0"/>
</aapt:attr>
</objectAnimator>
- <objectAnimator android:propertyName="trimPathEnd" android:duration="67"
- android:startOffset="50" android:valueFrom="0.89"
+ <objectAnimator android:propertyName="scaleY" android:duration="233"
+ android:startOffset="0" android:valueFrom="0" android:valueTo="1.02"
+ android:valueType="floatType">
+ <aapt:attr name="android:interpolator">
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.001,0 0.438,1 1.0,1.0"/>
+ </aapt:attr>
+ </objectAnimator>
+ <objectAnimator android:propertyName="scaleX" android:duration="117"
+ android:startOffset="233" android:valueFrom="1.02"
android:valueTo="1" android:valueType="floatType">
<aapt:attr name="android:interpolator">
- <pathInterpolator
- android:pathData="M 0.0,0.0 c0.167,0.167 0.833,0.833 1.0,1.0"/>
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.565,1 1.0,1.0"/>
+ </aapt:attr>
+ </objectAnimator>
+ <objectAnimator android:propertyName="scaleY" android:duration="117"
+ android:startOffset="233" android:valueFrom="1.02"
+ android:valueTo="1" android:valueType="floatType">
+ <aapt:attr name="android:interpolator">
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.565,1 1.0,1.0"/>
</aapt:attr>
</objectAnimator>
</set>
</aapt:attr>
</target>
- <target android:name="_R_G_L_2_G_D_1_P_0">
+ <target android:name="_R_G_L_0_G_D_0_P_0">
<aapt:attr name="android:animation">
<set android:ordering="together">
<objectAnimator android:propertyName="trimPathStart" android:duration="50"
@@ -133,7 +146,7 @@
</set>
</aapt:attr>
</target>
- <target android:name="_R_G_L_2_G_D_1_P_0">
+ <target android:name="_R_G_L_0_G_D_0_P_0">
<aapt:attr name="android:animation">
<set android:ordering="together">
<objectAnimator android:propertyName="trimPathEnd" android:duration="50"
@@ -155,130 +168,48 @@
</set>
</aapt:attr>
</target>
- <target android:name="_R_G_L_2_G_T_1">
- <aapt:attr name="android:animation">
- <set android:ordering="together">
- <objectAnimator android:propertyName="translateXY" android:duration="150"
- android:startOffset="0" android:propertyXName="translateX"
- android:propertyYName="translateY"
- android:pathData="M 2.25,2.373C 2.25,1.2001604776382402 2.25,-3.49116047763824 2.25,-4.664">
- <aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.001,0 0.2,1 1.0,1.0"/>
- </aapt:attr>
- </objectAnimator>
- </set>
- </aapt:attr>
- </target>
- <target android:name="_R_G_L_2_G_N_2_T_0">
+ <target android:name="_R_G_L_0_G_T_1">
<aapt:attr name="android:animation">
<set android:ordering="together">
- <objectAnimator android:propertyName="scaleX" android:duration="233"
- android:startOffset="0" android:valueFrom="0"
- android:valueTo="1.0125" android:valueType="floatType">
- <aapt:attr name="android:interpolator">
- <pathInterpolator
- android:pathData="M 0.0,0.0 c0.043,0.556 0.667,1 1.0,1.0"/>
- </aapt:attr>
- </objectAnimator>
- <objectAnimator android:propertyName="scaleY" android:duration="233"
- android:startOffset="0" android:valueFrom="0"
- android:valueTo="1.0125" android:valueType="floatType">
- <aapt:attr name="android:interpolator">
- <pathInterpolator
- android:pathData="M 0.0,0.0 c0.043,0.556 0.667,1 1.0,1.0"/>
- </aapt:attr>
- </objectAnimator>
- <objectAnimator android:propertyName="scaleX" android:duration="117"
- android:startOffset="233" android:valueFrom="1.0125"
- android:valueTo="1" android:valueType="floatType">
- <aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.667,1 1.0,1.0"/>
- </aapt:attr>
- </objectAnimator>
- <objectAnimator android:propertyName="scaleY" android:duration="117"
- android:startOffset="233" android:valueFrom="1.0125"
- android:valueTo="1" android:valueType="floatType">
+ <objectAnimator android:propertyName="translateY" android:duration="150"
+ android:startOffset="0" android:valueFrom="3.172"
+ android:valueTo="0.34" android:valueType="floatType">
<aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.667,1 1.0,1.0"/>
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.23,-0.46 0.2,1 1.0,1.0"/>
</aapt:attr>
</objectAnimator>
</set>
</aapt:attr>
</target>
- <target android:name="_R_G_L_2_G_N_2_N_1_T_0">
- <aapt:attr name="android:animation">
- <set android:ordering="together">
- <objectAnimator android:propertyName="scaleX" android:duration="0"
- android:startOffset="50" android:valueFrom="0" android:valueTo="1.3"
- android:valueType="floatType"/>
- </set>
- </aapt:attr>
- </target>
- <target android:name="_R_G_L_1_G">
+ <target android:name="_R_G_L_0_G_N_4_T_0">
<aapt:attr name="android:animation">
<set android:ordering="together">
<objectAnimator android:propertyName="scaleX" android:duration="233"
- android:startOffset="0" android:valueFrom="0"
- android:valueTo="1.025" android:valueType="floatType">
+ android:startOffset="0" android:valueFrom="0" android:valueTo="1.02"
+ android:valueType="floatType">
<aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.001,0 0.2,1 1.0,1.0"/>
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.001,0 0.438,1 1.0,1.0"/>
</aapt:attr>
</objectAnimator>
<objectAnimator android:propertyName="scaleY" android:duration="233"
- android:startOffset="0" android:valueFrom="0"
- android:valueTo="1.025" android:valueType="floatType">
+ android:startOffset="0" android:valueFrom="0" android:valueTo="1.02"
+ android:valueType="floatType">
<aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.001,0 0.2,1 1.0,1.0"/>
- </aapt:attr>
- </objectAnimator>
- <objectAnimator android:propertyName="scaleX" android:duration="117"
- android:startOffset="233" android:valueFrom="1.025"
- android:valueTo="1" android:valueType="floatType">
- <aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.4,0 0.2,1 1.0,1.0"/>
- </aapt:attr>
- </objectAnimator>
- <objectAnimator android:propertyName="scaleY" android:duration="117"
- android:startOffset="233" android:valueFrom="1.025"
- android:valueTo="1" android:valueType="floatType">
- <aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.4,0 0.2,1 1.0,1.0"/>
- </aapt:attr>
- </objectAnimator>
- </set>
- </aapt:attr>
- </target>
- <target android:name="_R_G_L_0_G">
- <aapt:attr name="android:animation">
- <set android:ordering="together">
- <objectAnimator android:propertyName="scaleX" android:duration="233"
- android:startOffset="0" android:valueFrom="0"
- android:valueTo="1.0125" android:valueType="floatType">
- <aapt:attr name="android:interpolator">
- <pathInterpolator
- android:pathData="M 0.0,0.0 c0.043,0.556 0.667,1 1.0,1.0"/>
- </aapt:attr>
- </objectAnimator>
- <objectAnimator android:propertyName="scaleY" android:duration="233"
- android:startOffset="0" android:valueFrom="0"
- android:valueTo="1.0125" android:valueType="floatType">
- <aapt:attr name="android:interpolator">
- <pathInterpolator
- android:pathData="M 0.0,0.0 c0.043,0.556 0.667,1 1.0,1.0"/>
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.001,0 0.438,1 1.0,1.0"/>
</aapt:attr>
</objectAnimator>
<objectAnimator android:propertyName="scaleX" android:duration="117"
- android:startOffset="233" android:valueFrom="1.0125"
+ android:startOffset="233" android:valueFrom="1.02"
android:valueTo="1" android:valueType="floatType">
<aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.667,1 1.0,1.0"/>
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.565,1 1.0,1.0"/>
</aapt:attr>
</objectAnimator>
<objectAnimator android:propertyName="scaleY" android:duration="117"
- android:startOffset="233" android:valueFrom="1.0125"
+ android:startOffset="233" android:valueFrom="1.02"
android:valueTo="1" android:valueType="floatType">
<aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.667,1 1.0,1.0"/>
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.565,1 1.0,1.0"/>
</aapt:attr>
</objectAnimator>
</set>
diff --git a/core/res/res/anim/lock_lock.xml b/core/res/res/anim/lock_lock.xml
index 8fc4f05319d3..3b8c4855fc8f 100755..100644
--- a/core/res/res/anim/lock_lock.xml
+++ b/core/res/res/anim/lock_lock.xml
@@ -1,5 +1,4 @@
-<!--
- Copyright (C) 2019 The Android Open Source Project
+<!-- Copyright (C) 2019 The Android Open Source Project
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
@@ -14,90 +13,114 @@
limitations under the License.
-->
<animated-vector xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:aapt="http://schemas.android.com/aapt">
+ xmlns:aapt="http://schemas.android.com/aapt">
<aapt:attr name="android:drawable">
- <vector android:height="32dp" android:width="32dp" android:viewportHeight="32"
- android:viewportWidth="32">
+ <vector
+ android:width="32dp"
+ android:height="40dp"
+ android:viewportWidth="32"
+ android:viewportHeight="40">
<group android:name="_R_G">
- <group android:name="_R_G_L_2_G_N_1_T_0" android:translateX="16"
- android:translateY="16" android:scaleX="1.3" android:scaleY="1.3">
- <group android:name="_R_G_L_2_G_T_1" android:translateX="0"
- android:translateY="3">
- <group android:name="_R_G_L_2_G" android:translateX="-8.25"
- android:translateY="-7.25">
- <path android:name="_R_G_L_2_G_D_0_P_0" android:fillColor="#000"
- android:fillAlpha="1" android:fillType="nonZero"
- android:pathData=" M14.25 0.25 C14.25,0.25 12.75,0.25 12.75,0.25 C12.75,0.25 10.75,0.25 10.75,0.25 C10.75,0.25 5.75,0.25 5.75,0.25 C5.75,0.25 3.75,0.25 3.75,0.25 C3.75,0.25 2.25,0.25 2.25,0.25 C1.15,0.25 0.25,1.15 0.25,2.25 C0.25,2.25 0.25,12.25 0.25,12.25 C0.25,13.35 1.15,14.25 2.25,14.25 C2.25,14.25 14.25,14.25 14.25,14.25 C15.35,14.25 16.25,13.35 16.25,12.25 C16.25,12.25 16.25,2.25 16.25,2.25 C16.25,1.15 15.35,0.25 14.25,0.25c M14.25 12.25 C14.25,12.25 2.25,12.25 2.25,12.25 C2.25,12.25 2.25,2.25 2.25,2.25 C2.25,2.25 3.75,2.25 3.75,2.25 C3.75,2.25 12.75,2.25 12.75,2.25 C12.75,2.25 14.25,2.25 14.25,2.25 C14.25,2.25 14.25,12.25 14.25,12.25c "/>
- </group>
+ <group
+ android:name="_R_G_L_2_G_T_1"
+ android:translateX="16"
+ android:translateY="23.993">
+ <group
+ android:name="_R_G_L_2_G"
+ android:translateX="-14.333"
+ android:translateY="-13">
+ <path
+ android:name="_R_G_L_2_G_D_0_P_0"
+ android:pathData=" M22.33 21 C22.33,21 6.33,21 6.33,21 C5.6,21 5,20.4 5,19.67 C5,19.67 5,6.33 5,6.33 C5,5.6 5.6,5 6.33,5 C6.33,5 22.33,5 22.33,5 C23.07,5 23.67,5.6 23.67,6.33 C23.67,6.33 23.67,19.67 23.67,19.67 C23.67,20.4 23.07,21 22.33,21c "
+ android:strokeWidth="2"
+ android:strokeAlpha="1"
+ android:strokeColor="#ffffff" />
</group>
</group>
- <group android:name="_R_G_L_1_G_N_4_N_1_T_0" android:translateX="16"
- android:translateY="16" android:scaleX="1.3" android:scaleY="1.3">
- <group android:name="_R_G_L_1_G_N_4_T_1" android:translateX="0"
- android:translateY="3">
- <group android:name="_R_G_L_1_G_N_4_T_0" android:translateX="-8.25"
- android:translateY="-7.25">
- <group android:name="_R_G_L_1_G" android:translateX="6"
- android:translateY="5" android:pivotX="2.25"
- android:pivotY="2.25" android:scaleX="1" android:scaleY="1">
- <path android:name="_R_G_L_1_G_D_0_P_0" android:fillColor="#000"
- android:fillAlpha="1" android:fillType="nonZero"
- android:pathData=" M2.25 0.25 C3.35,0.25 4.25,1.15 4.25,2.25 C4.25,3.35 3.35,4.25 2.25,4.25 C1.15,4.25 0.25,3.35 0.25,2.25 C0.25,1.15 1.15,0.25 2.25,0.25c "/>
- </group>
+ <group
+ android:name="_R_G_L_1_G_N_4_T_1"
+ android:translateX="16"
+ android:translateY="23.993">
+ <group
+ android:name="_R_G_L_1_G_N_4_T_0"
+ android:translateX="-14.333"
+ android:translateY="-13">
+ <group
+ android:name="_R_G_L_1_G"
+ android:pivotX="2.75"
+ android:pivotY="2.75"
+ android:scaleX="1"
+ android:scaleY="1"
+ android:translateX="11.583"
+ android:translateY="10.257">
+ <path
+ android:name="_R_G_L_1_G_D_0_P_0"
+ android:fillAlpha="1"
+ android:fillColor="#ffffff"
+ android:fillType="nonZero"
+ android:pathData=" M2.75 0.25 C4.13,0.25 5.25,1.37 5.25,2.75 C5.25,4.13 4.13,5.25 2.75,5.25 C1.37,5.25 0.25,4.13 0.25,2.75 C0.25,1.37 1.37,0.25 2.75,0.25c " />
</group>
</group>
</group>
- <group android:name="_R_G_L_0_G_N_4_N_1_T_0" android:translateX="16"
- android:translateY="16" android:scaleX="1.3" android:scaleY="1.3">
- <group android:name="_R_G_L_0_G_N_4_T_1" android:translateX="0"
- android:translateY="3">
- <group android:name="_R_G_L_0_G_N_4_T_0" android:translateX="-8.25"
- android:translateY="-7.25">
- <group android:name="_R_G_L_0_G" android:translateX="-16.219"
- android:translateY="32.25" android:pivotX="27.965"
- android:pivotY="-32" android:scaleX="0.125"
- android:scaleY="0.125">
- <path android:name="_R_G_L_0_G_D_0_P_0" android:fillColor="#ff0000"
- android:fillAlpha="0" android:fillType="nonZero"
- android:pathData=" M79.79 -48.55 C79.79,-48.55 79.75,-53.75 79.78,-55.48 C79.83,-57.62 79.08,-78.36 53.07,-78.83 C29.5,-79.25 25.2,-59.38 25.22,-58.27 C25.25,-56.25 24.97,-31.17 24.97,-31.17 "/>
- <path android:name="_R_G_L_0_G_D_1_P_0"
- android:strokeColor="#000" android:strokeLineCap="round"
- android:strokeLineJoin="round" android:strokeWidth="16"
- android:strokeAlpha="1"
- android:pathData=" M79.79 -48.55 C79.79,-48.55 79.75,-53.75 79.78,-55.48 C79.83,-57.62 79.08,-78.36 53.07,-78.83 C29.5,-79.25 25.2,-59.38 25.22,-58.27 C25.25,-56.25 24.97,-31.17 24.97,-31.17 "/>
- </group>
+ <group
+ android:name="_R_G_L_0_G_N_4_T_1"
+ android:translateX="16"
+ android:translateY="23.993">
+ <group
+ android:name="_R_G_L_0_G_N_4_T_0"
+ android:translateX="-14.333"
+ android:translateY="-13">
+ <group
+ android:name="_R_G_L_0_G"
+ android:translateX="4.666"
+ android:translateY="-9.327">
+ <path
+ android:name="_R_G_L_0_G_D_0_P_0"
+ android:pathData=" M14.33 14.33 C14.33,14.33 14.32,9.42 14.32,9.42 C14.32,7.4 15.67,5.01 18.65,5 C21.76,4.99 23.07,7.37 23.05,9.47 C23.05,9.47 23.06,9.77 23.06,9.77 "
+ android:strokeWidth="2"
+ android:strokeAlpha="1"
+ android:strokeColor="#ffffff" />
</group>
</group>
</group>
</group>
- <group android:name="time_group"/>
+ <group android:name="time_group" />
</vector>
</aapt:attr>
<target android:name="_R_G_L_2_G_T_1">
<aapt:attr name="android:animation">
<set android:ordering="together">
- <objectAnimator android:propertyName="translateXY" android:duration="400"
- android:startOffset="0" android:propertyXName="translateX"
- android:propertyYName="translateY"
- android:pathData="M 0,3C 0,3.09895833581686 0,3 0,3">
+ <objectAnimator
+ android:duration="400"
+ android:propertyName="translateY"
+ android:startOffset="0"
+ android:valueFrom="23.993"
+ android:valueTo="23.993"
+ android:valueType="floatType">
<aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.667,1 1.0,1.0"/>
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.167,0 0.667,1 1.0,1.0" />
</aapt:attr>
</objectAnimator>
- <objectAnimator android:propertyName="translateXY" android:duration="67"
- android:startOffset="400" android:propertyXName="translateX"
- android:propertyYName="translateY"
- android:pathData="M 0,3C 0,3.09895833581686 0,3.594 0,3.594">
+ <objectAnimator
+ android:duration="67"
+ android:propertyName="translateY"
+ android:startOffset="400"
+ android:valueFrom="23.993"
+ android:valueTo="25.368"
+ android:valueType="floatType">
<aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.667,1 1.0,1.0"/>
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.58,0 0.549,1 1.0,1.0" />
</aapt:attr>
</objectAnimator>
- <objectAnimator android:propertyName="translateXY" android:duration="83"
- android:startOffset="467" android:propertyXName="translateX"
- android:propertyYName="translateY"
- android:pathData="M 0,3.594C 0,3.594 0,3.09895833581686 0,3">
+ <objectAnimator
+ android:duration="83"
+ android:propertyName="translateY"
+ android:startOffset="467"
+ android:valueFrom="25.368"
+ android:valueTo="23.993"
+ android:valueType="floatType">
<aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.667,1 1.0,1.0"/>
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.388,0 0.228,1 1.0,1.0" />
</aapt:attr>
</objectAnimator>
</set>
@@ -106,46 +129,70 @@
<target android:name="_R_G_L_1_G">
<aapt:attr name="android:animation">
<set android:ordering="together">
- <objectAnimator android:propertyName="scaleX" android:duration="450"
- android:startOffset="0" android:valueFrom="1" android:valueTo="1"
- android:valueType="floatType">
+ <objectAnimator
+ android:duration="450"
+ android:propertyName="scaleX"
+ android:startOffset="0"
+ android:valueFrom="1"
+ android:valueTo="1"
+ android:valueType="floatType">
<aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.667,1 1.0,1.0"/>
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.667,1 1.0,1.0" />
</aapt:attr>
</objectAnimator>
- <objectAnimator android:propertyName="scaleY" android:duration="450"
- android:startOffset="0" android:valueFrom="1" android:valueTo="1"
- android:valueType="floatType">
+ <objectAnimator
+ android:duration="450"
+ android:propertyName="scaleY"
+ android:startOffset="0"
+ android:valueFrom="1"
+ android:valueTo="1"
+ android:valueType="floatType">
<aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.667,1 1.0,1.0"/>
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.667,1 1.0,1.0" />
</aapt:attr>
</objectAnimator>
- <objectAnimator android:propertyName="scaleX" android:duration="67"
- android:startOffset="450" android:valueFrom="1"
- android:valueTo="1.1" android:valueType="floatType">
+ <objectAnimator
+ android:duration="67"
+ android:propertyName="scaleX"
+ android:startOffset="450"
+ android:valueFrom="1"
+ android:valueTo="1.1"
+ android:valueType="floatType">
<aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.667,1 1.0,1.0"/>
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.667,1 1.0,1.0" />
</aapt:attr>
</objectAnimator>
- <objectAnimator android:propertyName="scaleY" android:duration="67"
- android:startOffset="450" android:valueFrom="1"
- android:valueTo="1.1" android:valueType="floatType">
+ <objectAnimator
+ android:duration="67"
+ android:propertyName="scaleY"
+ android:startOffset="450"
+ android:valueFrom="1"
+ android:valueTo="1.1"
+ android:valueType="floatType">
<aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.667,1 1.0,1.0"/>
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.667,1 1.0,1.0" />
</aapt:attr>
</objectAnimator>
- <objectAnimator android:propertyName="scaleX" android:duration="183"
- android:startOffset="517" android:valueFrom="1.1"
- android:valueTo="1" android:valueType="floatType">
+ <objectAnimator
+ android:duration="183"
+ android:propertyName="scaleX"
+ android:startOffset="517"
+ android:valueFrom="1.1"
+ android:valueTo="1"
+ android:valueType="floatType">
<aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.667,1 1.0,1.0"/>
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.667,1 1.0,1.0" />
</aapt:attr>
</objectAnimator>
- <objectAnimator android:propertyName="scaleY" android:duration="183"
- android:startOffset="517" android:valueFrom="1.1"
- android:valueTo="1" android:valueType="floatType">
+ <objectAnimator
+ android:duration="183"
+ android:propertyName="scaleY"
+ android:startOffset="517"
+ android:valueFrom="1.1"
+ android:valueTo="1"
+ android:valueType="floatType">
<aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.667,1 1.0,1.0"/>
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.667,1 1.0,1.0" />
</aapt:attr>
</objectAnimator>
</set>
@@ -154,28 +201,37 @@
<target android:name="_R_G_L_1_G_N_4_T_1">
<aapt:attr name="android:animation">
<set android:ordering="together">
- <objectAnimator android:propertyName="translateXY" android:duration="400"
- android:startOffset="0" android:propertyXName="translateX"
- android:propertyYName="translateY"
- android:pathData="M 0,3C 0,3.09895833581686 0,3 0,3">
+ <objectAnimator
+ android:duration="400"
+ android:propertyName="translateY"
+ android:startOffset="0"
+ android:valueFrom="23.993"
+ android:valueTo="23.993"
+ android:valueType="floatType">
<aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.667,1 1.0,1.0"/>
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.167,0 0.667,1 1.0,1.0" />
</aapt:attr>
</objectAnimator>
- <objectAnimator android:propertyName="translateXY" android:duration="67"
- android:startOffset="400" android:propertyXName="translateX"
- android:propertyYName="translateY"
- android:pathData="M 0,3C 0,3.09895833581686 0,3.594 0,3.594">
+ <objectAnimator
+ android:duration="67"
+ android:propertyName="translateY"
+ android:startOffset="400"
+ android:valueFrom="23.993"
+ android:valueTo="25.368"
+ android:valueType="floatType">
<aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.667,1 1.0,1.0"/>
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.58,0 0.549,1 1.0,1.0" />
</aapt:attr>
</objectAnimator>
- <objectAnimator android:propertyName="translateXY" android:duration="83"
- android:startOffset="467" android:propertyXName="translateX"
- android:propertyYName="translateY"
- android:pathData="M 0,3.594C 0,3.594 0,3.09895833581686 0,3">
+ <objectAnimator
+ android:duration="83"
+ android:propertyName="translateY"
+ android:startOffset="467"
+ android:valueFrom="25.368"
+ android:valueTo="23.993"
+ android:valueType="floatType">
<aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.667,1 1.0,1.0"/>
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.388,0 0.228,1 1.0,1.0" />
</aapt:attr>
</objectAnimator>
</set>
@@ -184,64 +240,26 @@
<target android:name="_R_G_L_0_G_D_0_P_0">
<aapt:attr name="android:animation">
<set android:ordering="together">
- <objectAnimator android:propertyName="pathData" android:duration="317"
- android:startOffset="0"
- android:valueFrom="M79.79 -48.55 C79.79,-48.55 79.75,-53.75 79.78,-55.48 C79.83,-57.62 79.08,-78.36 53.07,-78.83 C29.5,-79.25 25.2,-59.38 25.22,-58.27 C25.25,-56.25 24.97,-31.17 24.97,-31.17 "
- android:valueTo="M-27.97 -55.05 C-27.97,-55.05 -28,-60.25 -27.97,-61.98 C-27.92,-64.13 -23.5,-86.37 -0.75,-86.32 C22.77,-86.26 27.75,-65.87 27.72,-64.77 C27.55,-59.38 27.97,-31.67 27.97,-31.67 "
- android:valueType="pathType">
- <aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.974,0 0.458,1 1.0,1.0"/>
- </aapt:attr>
- </objectAnimator>
- <objectAnimator android:propertyName="pathData" android:duration="133"
- android:startOffset="317"
- android:valueFrom="M-27.97 -55.05 C-27.97,-55.05 -28,-60.25 -27.97,-61.98 C-27.92,-64.13 -23.5,-86.37 -0.75,-86.32 C22.77,-86.26 27.75,-65.87 27.72,-64.77 C27.55,-59.38 27.97,-31.67 27.97,-31.67 "
- android:valueTo="M-28.21 -28.42 C-28.21,-28.42 -27.85,-44.88 -27.97,-51.98 C-28,-54.13 -23.5,-76.37 -0.75,-76.32 C22.77,-76.26 27.75,-55.87 27.72,-54.77 C27.55,-49.38 27.97,-28.17 27.97,-28.17 "
- android:valueType="pathType">
- <aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.4,0 0.2,1 1.0,1.0"/>
- </aapt:attr>
- </objectAnimator>
- <objectAnimator android:propertyName="pathData" android:duration="250"
- android:startOffset="450"
- android:valueFrom="M-28.21 -28.42 C-28.21,-28.42 -27.85,-44.88 -27.97,-51.98 C-28,-54.13 -23.5,-76.37 -0.75,-76.32 C22.77,-76.26 27.75,-55.87 27.72,-54.77 C27.55,-49.38 27.97,-28.17 27.97,-28.17 "
- android:valueTo="M-28.21 -31.92 C-28.21,-31.92 -27.85,-48.38 -27.97,-55.48 C-28,-57.63 -23.5,-79.87 -0.75,-79.82 C22.77,-79.76 27.75,-59.37 27.72,-58.27 C27.55,-52.88 27.97,-31.67 27.97,-31.67 "
- android:valueType="pathType">
- <aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.414,0 0.647,1 1.0,1.0"/>
- </aapt:attr>
- </objectAnimator>
- </set>
- </aapt:attr>
- </target>
- <target android:name="_R_G_L_0_G_D_1_P_0">
- <aapt:attr name="android:animation">
- <set android:ordering="together">
- <objectAnimator android:propertyName="pathData" android:duration="317"
- android:startOffset="0"
- android:valueFrom="M79.79 -48.55 C79.79,-48.55 79.75,-53.75 79.78,-55.48 C79.83,-57.62 79.08,-78.36 53.07,-78.83 C29.5,-79.25 25.2,-59.38 25.22,-58.27 C25.25,-56.25 24.97,-31.17 24.97,-31.17 "
- android:valueTo="M-27.97 -55.05 C-27.97,-55.05 -28,-60.25 -27.97,-61.98 C-27.92,-64.13 -23.5,-86.37 -0.75,-86.32 C22.77,-86.26 27.75,-65.87 27.72,-64.77 C27.55,-59.38 27.97,-31.67 27.97,-31.67 "
- android:valueType="pathType">
- <aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.974,0 0.458,1 1.0,1.0"/>
- </aapt:attr>
- </objectAnimator>
- <objectAnimator android:propertyName="pathData" android:duration="133"
- android:startOffset="317"
- android:valueFrom="M-27.97 -55.05 C-27.97,-55.05 -28,-60.25 -27.97,-61.98 C-27.92,-64.13 -23.5,-86.37 -0.75,-86.32 C22.77,-86.26 27.75,-65.87 27.72,-64.77 C27.55,-59.38 27.97,-31.67 27.97,-31.67 "
- android:valueTo="M-28.21 -28.42 C-28.21,-28.42 -27.85,-44.88 -27.97,-51.98 C-28,-54.13 -23.5,-76.37 -0.75,-76.32 C22.77,-76.26 27.75,-55.87 27.72,-54.77 C27.55,-49.38 27.97,-28.17 27.97,-28.17 "
- android:valueType="pathType">
+ <objectAnimator
+ android:duration="317"
+ android:propertyName="pathData"
+ android:startOffset="0"
+ android:valueFrom="M14.33 14.33 C14.33,14.33 14.32,9.42 14.32,9.42 C14.32,7.4 15.67,5.01 18.65,5 C21.76,4.99 23.07,7.37 23.05,9.47 C23.05,9.47 23.06,9.77 23.06,9.77 "
+ android:valueTo="M14.33 14.33 C14.33,14.33 14.29,6.17 14.29,6.17 C14.29,3.59 12.2,1.5 9.63,1.5 C7.05,1.5 4.96,3.59 4.96,6.17 C4.96,6.17 4.96,7.33 4.96,7.33 "
+ android:valueType="pathType">
<aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.4,0 0.2,1 1.0,1.0"/>
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.692,0 0.298,1 1.0,1.0" />
</aapt:attr>
</objectAnimator>
- <objectAnimator android:propertyName="pathData" android:duration="250"
- android:startOffset="450"
- android:valueFrom="M-28.21 -28.42 C-28.21,-28.42 -27.85,-44.88 -27.97,-51.98 C-28,-54.13 -23.5,-76.37 -0.75,-76.32 C22.77,-76.26 27.75,-55.87 27.72,-54.77 C27.55,-49.38 27.97,-28.17 27.97,-28.17 "
- android:valueTo="M-28.21 -31.92 C-28.21,-31.92 -27.85,-48.38 -27.97,-55.48 C-28,-57.63 -23.5,-79.87 -0.75,-79.82 C22.77,-79.76 27.75,-59.37 27.72,-58.27 C27.55,-52.88 27.97,-31.67 27.97,-31.67 "
- android:valueType="pathType">
+ <objectAnimator
+ android:duration="133"
+ android:propertyName="pathData"
+ android:startOffset="317"
+ android:valueFrom="M14.33 14.33 C14.33,14.33 14.29,6.17 14.29,6.17 C14.29,3.59 12.2,1.5 9.63,1.5 C7.05,1.5 4.96,3.59 4.96,6.17 C4.96,6.17 4.96,7.33 4.96,7.33 "
+ android:valueTo="M14.33 14.33 C14.33,14.33 14.33,9.67 14.33,9.67 C14.33,7.09 12.24,5 9.67,5 C7.09,5 5,7.09 5,9.67 C5,9.67 5,14.33 5,14.33 "
+ android:valueType="pathType">
<aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.414,0 0.647,1 1.0,1.0"/>
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.561,0 0.44,1 1.0,1.0" />
</aapt:attr>
</objectAnimator>
</set>
@@ -250,28 +268,37 @@
<target android:name="_R_G_L_0_G_N_4_T_1">
<aapt:attr name="android:animation">
<set android:ordering="together">
- <objectAnimator android:propertyName="translateXY" android:duration="400"
- android:startOffset="0" android:propertyXName="translateX"
- android:propertyYName="translateY"
- android:pathData="M 0,3C 0,3.09895833581686 0,3 0,3">
+ <objectAnimator
+ android:duration="400"
+ android:propertyName="translateY"
+ android:startOffset="0"
+ android:valueFrom="23.993"
+ android:valueTo="23.993"
+ android:valueType="floatType">
<aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.667,1 1.0,1.0"/>
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.167,0 0.667,1 1.0,1.0" />
</aapt:attr>
</objectAnimator>
- <objectAnimator android:propertyName="translateXY" android:duration="67"
- android:startOffset="400" android:propertyXName="translateX"
- android:propertyYName="translateY"
- android:pathData="M 0,3C 0,3.09895833581686 0,3.594 0,3.594">
+ <objectAnimator
+ android:duration="67"
+ android:propertyName="translateY"
+ android:startOffset="400"
+ android:valueFrom="23.993"
+ android:valueTo="25.368"
+ android:valueType="floatType">
<aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.667,1 1.0,1.0"/>
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.58,0 0.549,1 1.0,1.0" />
</aapt:attr>
</objectAnimator>
- <objectAnimator android:propertyName="translateXY" android:duration="83"
- android:startOffset="467" android:propertyXName="translateX"
- android:propertyYName="translateY"
- android:pathData="M 0,3.594C 0,3.594 0,3.09895833581686 0,3">
+ <objectAnimator
+ android:duration="83"
+ android:propertyName="translateY"
+ android:startOffset="467"
+ android:valueFrom="25.368"
+ android:valueTo="23.993"
+ android:valueType="floatType">
<aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.667,1 1.0,1.0"/>
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.388,0 0.228,1 1.0,1.0" />
</aapt:attr>
</objectAnimator>
</set>
@@ -280,9 +307,13 @@
<target android:name="time_group">
<aapt:attr name="android:animation">
<set android:ordering="together">
- <objectAnimator android:propertyName="translateX" android:duration="717"
- android:startOffset="0" android:valueFrom="0" android:valueTo="1"
- android:valueType="floatType"/>
+ <objectAnimator
+ android:duration="717"
+ android:propertyName="translateX"
+ android:startOffset="0"
+ android:valueFrom="0"
+ android:valueTo="1"
+ android:valueType="floatType" />
</set>
</aapt:attr>
</target>
diff --git a/core/res/res/anim/lock_out.xml b/core/res/res/anim/lock_out.xml
deleted file mode 100755
index 2543d47772b8..000000000000
--- a/core/res/res/anim/lock_out.xml
+++ /dev/null
@@ -1,277 +0,0 @@
-<!--
- Copyright (C) 2019 The Android Open Source Project
-
- Licensed under the Apache License, Version 2.0 (the "License");
- you may not use this file except in compliance with the License.
- You may obtain a copy of the License at
-
- http://www.apache.org/licenses/LICENSE-2.0
-
- Unless required by applicable law or agreed to in writing, software
- distributed under the License is distributed on an "AS IS" BASIS,
- WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- See the License for the specific language governing permissions and
- limitations under the License.
--->
-<animated-vector xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:aapt="http://schemas.android.com/aapt">
- <aapt:attr name="android:drawable">
- <vector
- android:width="24dp"
- android:height="24dp"
- android:viewportWidth="24"
- android:viewportHeight="24">
- <group android:name="_R_G">
- <group android:name="_R_G_L_2_G_N_4_T_0_M">
- <group
- android:name="_R_G_L_2_G_N_4_T_0"
- android:pivotX="8.25"
- android:pivotY="7.25"
- android:scaleX="1"
- android:scaleY="1"
- android:translateX="3.75"
- android:translateY="7.75">
- <group
- android:name="_R_G_L_2_G"
- android:pivotY="-32"
- android:scaleX="0.125"
- android:scaleY="0.125"
- android:translateX="8.25"
- android:translateY="32.267">
- <path
- android:name="_R_G_L_2_G_D_0_P_0"
- android:fillAlpha="0"
- android:fillColor="#ff0000"
- android:fillType="nonZero"
- android:pathData=" M-28.21 -31.92 C-28.21,-31.92 -27.85,-48.38 -27.97,-55.48 C-28,-57.63 -23.5,-79.87 -0.75,-79.82 C22.77,-79.76 27.75,-59.37 27.72,-58.27 C27.55,-52.88 27.97,-31.67 27.97,-31.67 "
- android:trimPathStart="0"
- android:trimPathEnd="1"
- android:trimPathOffset="0" />
- <path
- android:name="_R_G_L_2_G_D_1_P_0"
- android:pathData=" M-28.21 -31.92 C-28.21,-31.92 -27.85,-48.38 -27.97,-55.48 C-28,-57.63 -23.5,-79.87 -0.75,-79.82 C22.77,-79.76 27.75,-59.37 27.72,-58.27 C27.55,-52.88 27.97,-31.67 27.97,-31.67 "
- android:strokeWidth="16"
- android:strokeAlpha="1"
- android:strokeColor="?attr/textColor"
- android:trimPathStart="0"
- android:trimPathEnd="1"
- android:trimPathOffset="0" />
- </group>
- </group>
- </group>
- <group
- android:name="_R_G_L_1_G"
- android:pivotX="8.25"
- android:pivotY="7.25"
- android:scaleX="1"
- android:scaleY="1"
- android:translateX="3.75"
- android:translateY="7.75">
- <path
- android:name="_R_G_L_1_G_D_0_P_0"
- android:fillAlpha="1"
- android:fillColor="?attr/textColor"
- android:fillType="nonZero"
- android:pathData=" M14.25 0.25 C14.25,0.25 12.75,0.25 12.75,0.25 C12.75,0.25 10.75,0.25 10.75,0.25 C10.75,0.25 5.75,0.25 5.75,0.25 C5.75,0.25 3.75,0.25 3.75,0.25 C3.75,0.25 2.25,0.25 2.25,0.25 C1.15,0.25 0.25,1.15 0.25,2.25 C0.25,2.25 0.25,12.25 0.25,12.25 C0.25,13.35 1.15,14.25 2.25,14.25 C2.25,14.25 14.25,14.25 14.25,14.25 C15.35,14.25 16.25,13.35 16.25,12.25 C16.25,12.25 16.25,2.25 16.25,2.25 C16.25,1.15 15.35,0.25 14.25,0.25c M14.25 12.25 C14.25,12.25 2.25,12.25 2.25,12.25 C2.25,12.25 2.25,2.25 2.25,2.25 C2.25,2.25 3.75,2.25 3.75,2.25 C3.75,2.25 12.75,2.25 12.75,2.25 C12.75,2.25 14.25,2.25 14.25,2.25 C14.25,2.25 14.25,12.25 14.25,12.25c " />
- </group>
- <group android:name="_R_G_L_0_G_N_4_T_0_M">
- <group
- android:name="_R_G_L_0_G_N_4_T_0"
- android:pivotX="8.25"
- android:pivotY="7.25"
- android:scaleX="1"
- android:scaleY="1"
- android:translateX="3.75"
- android:translateY="7.75">
- <group
- android:name="_R_G_L_0_G"
- android:translateX="6"
- android:translateY="5">
- <path
- android:name="_R_G_L_0_G_D_0_P_0"
- android:fillAlpha="1"
- android:fillColor="?attr/textColor"
- android:fillType="nonZero"
- android:pathData=" M2.25 0.25 C3.35,0.25 4.25,1.15 4.25,2.25 C4.25,3.35 3.35,4.25 2.25,4.25 C1.15,4.25 0.25,3.35 0.25,2.25 C0.25,1.15 1.15,0.25 2.25,0.25c " />
- </group>
- </group>
- </group>
- </group>
- <group android:name="time_group" />
- </vector>
- </aapt:attr>
- <target android:name="_R_G_L_2_G_D_1_P_0">
- <aapt:attr name="android:animation">
- <set android:ordering="together">
- <objectAnimator
- android:duration="150"
- android:propertyName="strokeAlpha"
- android:startOffset="0"
- android:valueFrom="1"
- android:valueTo="0"
- android:valueType="floatType">
- <aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.167,0.167 0.833,0.833 1.0,1.0" />
- </aapt:attr>
- </objectAnimator>
- </set>
- </aapt:attr>
- </target>
- <target android:name="_R_G_L_2_G_N_4_T_0">
- <aapt:attr name="android:animation">
- <set android:ordering="together">
- <objectAnimator
- android:duration="200"
- android:propertyName="scaleX"
- android:startOffset="0"
- android:valueFrom="1"
- android:valueTo="0.09375"
- android:valueType="floatType">
- <aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.521,0 0.942,0.896 1.0,1.0" />
- </aapt:attr>
- </objectAnimator>
- <objectAnimator
- android:duration="200"
- android:propertyName="scaleY"
- android:startOffset="0"
- android:valueFrom="1"
- android:valueTo="0.09375"
- android:valueType="floatType">
- <aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.521,0 0.942,0.896 1.0,1.0" />
- </aapt:attr>
- </objectAnimator>
- </set>
- </aapt:attr>
- </target>
- <target android:name="_R_G_L_2_G_N_4_T_0_M">
- <aapt:attr name="android:animation">
- <set android:ordering="together">
- <objectAnimator
- android:duration="0"
- android:propertyName="scaleY"
- android:startOffset="350"
- android:valueFrom="1"
- android:valueTo="0"
- android:valueType="floatType" />
- </set>
- </aapt:attr>
- </target>
- <target android:name="_R_G_L_1_G_D_0_P_0">
- <aapt:attr name="android:animation">
- <set android:ordering="together">
- <objectAnimator
- android:duration="150"
- android:propertyName="fillAlpha"
- android:startOffset="0"
- android:valueFrom="1"
- android:valueTo="0.02"
- android:valueType="floatType">
- <aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.167,0.167 0.833,0.833 1.0,1.0" />
- </aapt:attr>
- </objectAnimator>
- </set>
- </aapt:attr>
- </target>
- <target android:name="_R_G_L_1_G">
- <aapt:attr name="android:animation">
- <set android:ordering="together">
- <objectAnimator
- android:duration="200"
- android:propertyName="scaleX"
- android:startOffset="0"
- android:valueFrom="1"
- android:valueTo="0.09375"
- android:valueType="floatType">
- <aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.521,0 0.942,0.896 1.0,1.0" />
- </aapt:attr>
- </objectAnimator>
- <objectAnimator
- android:duration="200"
- android:propertyName="scaleY"
- android:startOffset="0"
- android:valueFrom="1"
- android:valueTo="0.09375"
- android:valueType="floatType">
- <aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.521,0 0.942,0.896 1.0,1.0" />
- </aapt:attr>
- </objectAnimator>
- </set>
- </aapt:attr>
- </target>
- <target android:name="_R_G_L_0_G_D_0_P_0">
- <aapt:attr name="android:animation">
- <set android:ordering="together">
- <objectAnimator
- android:duration="83"
- android:propertyName="fillAlpha"
- android:startOffset="0"
- android:valueFrom="1"
- android:valueTo="0"
- android:valueType="floatType">
- <aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.167,0.167 0.833,0.833 1.0,1.0" />
- </aapt:attr>
- </objectAnimator>
- </set>
- </aapt:attr>
- </target>
- <target android:name="_R_G_L_0_G_N_4_T_0">
- <aapt:attr name="android:animation">
- <set android:ordering="together">
- <objectAnimator
- android:duration="200"
- android:propertyName="scaleX"
- android:startOffset="0"
- android:valueFrom="1"
- android:valueTo="0.09375"
- android:valueType="floatType">
- <aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.521,0 0.942,0.896 1.0,1.0" />
- </aapt:attr>
- </objectAnimator>
- <objectAnimator
- android:duration="200"
- android:propertyName="scaleY"
- android:startOffset="0"
- android:valueFrom="1"
- android:valueTo="0.09375"
- android:valueType="floatType">
- <aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.521,0 0.942,0.896 1.0,1.0" />
- </aapt:attr>
- </objectAnimator>
- </set>
- </aapt:attr>
- </target>
- <target android:name="_R_G_L_0_G_N_4_T_0_M">
- <aapt:attr name="android:animation">
- <set android:ordering="together">
- <objectAnimator
- android:duration="0"
- android:propertyName="scaleY"
- android:startOffset="367"
- android:valueFrom="1"
- android:valueTo="0"
- android:valueType="floatType" />
- </set>
- </aapt:attr>
- </target>
- <target android:name="time_group">
- <aapt:attr name="android:animation">
- <set android:ordering="together">
- <objectAnimator
- android:duration="500"
- android:propertyName="translateX"
- android:startOffset="0"
- android:valueFrom="0"
- android:valueTo="1"
- android:valueType="floatType" />
- </set>
- </aapt:attr>
- </target>
-</animated-vector> \ No newline at end of file
diff --git a/core/res/res/anim/lock_scanning.xml b/core/res/res/anim/lock_scanning.xml
index 8ced02b947c5..db7972f542b3 100644
--- a/core/res/res/anim/lock_scanning.xml
+++ b/core/res/res/anim/lock_scanning.xml
@@ -1,5 +1,4 @@
-<!--
- Copyright (C) 2019 The Android Open Source Project
+<!-- Copyright (C) 2019 The Android Open Source Project
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
@@ -19,52 +18,36 @@
<vector android:height="42dp" android:width="32dp" android:viewportHeight="42"
android:viewportWidth="32">
<group android:name="_R_G">
- <group android:name="_R_G_L_2_G_N_5_N_1_T_0" android:translateY="5"
- android:pivotX="16" android:pivotY="16" android:scaleX="2"
- android:scaleY="2">
- <group android:name="_R_G_L_2_G_N_5_T_0" android:translateX="7.75"
- android:translateY="10.670000000000002" android:pivotX="8.25"
- android:pivotY="7.25" android:scaleX="0.64" android:scaleY="0.64">
- <group android:name="_R_G_L_2_G" android:translateX="6"
- android:translateY="5" android:pivotX="2.25" android:pivotY="2.25"
- android:scaleX="1" android:scaleY="1">
- <path android:name="_R_G_L_2_G_D_0_P_0" android:fillColor="#000"
- android:fillAlpha="1" android:fillType="nonZero"
- android:pathData=" M2.25 0.25 C3.35,0.25 4.25,1.15 4.25,2.25 C4.25,3.35 3.35,4.25 2.25,4.25 C1.15,4.25 0.25,3.35 0.25,2.25 C0.25,1.15 1.15,0.25 2.25,0.25c "/>
- </group>
- </group>
+ <group android:name="_R_G_L_2_G" android:translateX="1.6669999999999998"
+ android:translateY="11.992999999999999" android:pivotX="14.333"
+ android:pivotY="13" android:scaleX="1" android:scaleY="1">
+ <path android:name="_R_G_L_2_G_D_0_P_0" android:strokeColor="#ffffff"
+ android:strokeLineCap="round" android:strokeLineJoin="round"
+ android:strokeWidth="2" android:strokeAlpha="1"
+ android:pathData=" M22.33 21 C22.33,21 6.33,21 6.33,21 C5.6,21 5,20.4 5,19.67 C5,19.67 5,6.33 5,6.33 C5,5.6 5.6,5 6.33,5 C6.33,5 22.33,5 22.33,5 C23.07,5 23.67,5.6 23.67,6.33 C23.67,6.33 23.67,19.67 23.67,19.67 C23.67,20.4 23.07,21 22.33,21c "/>
</group>
- <group android:name="_R_G_L_1_G_N_5_N_1_T_0" android:translateY="5"
- android:pivotX="16" android:pivotY="16" android:scaleX="2"
- android:scaleY="2">
- <group android:name="_R_G_L_1_G_N_5_T_0" android:translateX="7.75"
- android:translateY="10.670000000000002" android:pivotX="8.25"
- android:pivotY="7.25" android:scaleX="0.64" android:scaleY="0.64">
- <group android:name="_R_G_L_1_G_T_1" android:translateX="8.25"
- android:translateY="1.121" android:scaleX="0.125"
- android:scaleY="0.125">
- <group android:name="_R_G_L_1_G" android:translateY="25.029">
- <path android:name="_R_G_L_1_G_D_0_P_0"
- android:strokeColor="#000" android:strokeLineCap="round"
- android:strokeLineJoin="round" android:strokeWidth="16"
- android:strokeAlpha="1"
- android:pathData=" M-28.21 -25.03 C-28.21,-25.03 -27.85,-48.38 -27.97,-55.48 C-28,-57.63 -23.5,-79.87 -0.75,-79.82 C22.77,-79.76 27.75,-59.37 27.72,-58.27 C27.55,-52.88 27.93,-26.15 27.93,-26.15 "/>
- </group>
- </group>
+ <group android:name="_R_G_L_1_G_N_7_T_0" android:translateX="1.6669999999999998"
+ android:translateY="11.992999999999999" android:pivotX="14.333"
+ android:pivotY="13" android:scaleX="1" android:scaleY="1">
+ <group android:name="_R_G_L_1_G" android:translateX="11.583"
+ android:translateY="10.257" android:pivotX="2.75" android:pivotY="2.75"
+ android:scaleX="1" android:scaleY="1">
+ <path android:name="_R_G_L_1_G_D_0_P_0" android:fillColor="#ffffff"
+ android:fillAlpha="1" android:fillType="nonZero"
+ android:pathData=" M2.75 0.25 C4.13,0.25 5.25,1.37 5.25,2.75 C5.25,4.13 4.13,5.25 2.75,5.25 C1.37,5.25 0.25,4.13 0.25,2.75 C0.25,1.37 1.37,0.25 2.75,0.25c "/>
</group>
</group>
- <group android:name="_R_G_L_0_G_N_5_N_1_T_0" android:translateY="5"
- android:pivotX="16" android:pivotY="16" android:scaleX="2"
- android:scaleY="2">
- <group android:name="_R_G_L_0_G_N_5_T_0" android:translateX="7.75"
- android:translateY="10.670000000000002" android:pivotX="8.25"
- android:pivotY="7.25" android:scaleX="0.64" android:scaleY="0.64">
- <group android:name="_R_G_L_0_G" android:translateY="0.04699999999999971"
- android:pivotX="8.25" android:pivotY="7.25" android:scaleX="1.01562"
- android:scaleY="1.01563">
- <path android:name="_R_G_L_0_G_D_0_P_0" android:fillColor="#000"
- android:fillAlpha="1" android:fillType="nonZero"
- android:pathData=" M14.25 0.25 C14.25,0.25 12.75,0.25 12.75,0.25 C12.75,0.25 10.75,0.25 10.75,0.25 C10.75,0.25 5.75,0.25 5.75,0.25 C5.75,0.25 3.75,0.25 3.75,0.25 C3.75,0.25 2.25,0.25 2.25,0.25 C1.15,0.25 0.25,1.15 0.25,2.25 C0.25,2.25 0.25,12.25 0.25,12.25 C0.25,13.35 1.15,14.25 2.25,14.25 C2.25,14.25 14.25,14.25 14.25,14.25 C15.35,14.25 16.25,13.35 16.25,12.25 C16.25,12.25 16.25,2.25 16.25,2.25 C16.25,1.15 15.35,0.25 14.25,0.25c M14.25 12.25 C14.25,12.25 2.25,12.25 2.25,12.25 C2.25,12.25 2.25,2.25 2.25,2.25 C2.25,2.25 3.75,2.25 3.75,2.25 C3.75,2.25 12.75,2.25 12.75,2.25 C12.75,2.25 14.25,2.25 14.25,2.25 C14.25,2.25 14.25,12.25 14.25,12.25c "/>
+ <group android:name="_R_G_L_0_G_N_7_T_0" android:translateX="1.6669999999999998"
+ android:translateY="11.992999999999999" android:pivotX="14.333"
+ android:pivotY="13" android:scaleX="1" android:scaleY="1">
+ <group android:name="_R_G_L_0_G_T_1" android:translateX="14.333"
+ android:translateY="0.34">
+ <group android:name="_R_G_L_0_G" android:translateX="-9.667"
+ android:translateY="-9.667">
+ <path android:name="_R_G_L_0_G_D_0_P_0" android:strokeColor="#ffffff"
+ android:strokeLineCap="round" android:strokeLineJoin="round"
+ android:strokeWidth="2" android:strokeAlpha="1"
+ android:pathData=" M14.33 14.33 C14.33,14.33 14.33,9.67 14.33,9.67 C14.33,7.09 12.24,5 9.67,5 C7.09,5 5,7.09 5,9.67 C5,9.67 5,14.33 5,14.33 "/>
</group>
</group>
</group>
@@ -75,6 +58,68 @@
<target android:name="_R_G_L_2_G">
<aapt:attr name="android:animation">
<set android:ordering="together">
+ <objectAnimator android:propertyName="scaleX" android:duration="83"
+ android:startOffset="0" android:valueFrom="1" android:valueTo="1"
+ android:valueType="floatType">
+ <aapt:attr name="android:interpolator">
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.667,1 1.0,1.0"/>
+ </aapt:attr>
+ </objectAnimator>
+ <objectAnimator android:propertyName="scaleY" android:duration="83"
+ android:startOffset="0" android:valueFrom="1" android:valueTo="1"
+ android:valueType="floatType">
+ <aapt:attr name="android:interpolator">
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.667,1 1.0,1.0"/>
+ </aapt:attr>
+ </objectAnimator>
+ <objectAnimator android:propertyName="scaleX" android:duration="83"
+ android:startOffset="83" android:valueFrom="1"
+ android:valueTo="0.96" android:valueType="floatType">
+ <aapt:attr name="android:interpolator">
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.667,1 1.0,1.0"/>
+ </aapt:attr>
+ </objectAnimator>
+ <objectAnimator android:propertyName="scaleY" android:duration="83"
+ android:startOffset="83" android:valueFrom="1"
+ android:valueTo="0.96" android:valueType="floatType">
+ <aapt:attr name="android:interpolator">
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.667,1 1.0,1.0"/>
+ </aapt:attr>
+ </objectAnimator>
+ <objectAnimator android:propertyName="scaleX" android:duration="183"
+ android:startOffset="167" android:valueFrom="0.96"
+ android:valueTo="1.28" android:valueType="floatType">
+ <aapt:attr name="android:interpolator">
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.667,1 1.0,1.0"/>
+ </aapt:attr>
+ </objectAnimator>
+ <objectAnimator android:propertyName="scaleY" android:duration="183"
+ android:startOffset="167" android:valueFrom="0.96"
+ android:valueTo="1.28" android:valueType="floatType">
+ <aapt:attr name="android:interpolator">
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.667,1 1.0,1.0"/>
+ </aapt:attr>
+ </objectAnimator>
+ <objectAnimator android:propertyName="scaleX" android:duration="250"
+ android:startOffset="350" android:valueFrom="1.28"
+ android:valueTo="1" android:valueType="floatType">
+ <aapt:attr name="android:interpolator">
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.667,1 1.0,1.0"/>
+ </aapt:attr>
+ </objectAnimator>
+ <objectAnimator android:propertyName="scaleY" android:duration="250"
+ android:startOffset="350" android:valueFrom="1.28"
+ android:valueTo="1" android:valueType="floatType">
+ <aapt:attr name="android:interpolator">
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.667,1 1.0,1.0"/>
+ </aapt:attr>
+ </objectAnimator>
+ </set>
+ </aapt:attr>
+ </target>
+ <target android:name="_R_G_L_1_G">
+ <aapt:attr name="android:animation">
+ <set android:ordering="together">
<objectAnimator android:propertyName="scaleX" android:duration="150"
android:startOffset="0" android:valueFrom="1" android:valueTo="1"
android:valueType="floatType">
@@ -120,61 +165,61 @@
</set>
</aapt:attr>
</target>
- <target android:name="_R_G_L_2_G_N_5_T_0">
+ <target android:name="_R_G_L_1_G_N_7_T_0">
<aapt:attr name="android:animation">
<set android:ordering="together">
<objectAnimator android:propertyName="scaleX" android:duration="83"
- android:startOffset="0" android:valueFrom="0.64"
- android:valueTo="0.64" android:valueType="floatType">
+ android:startOffset="0" android:valueFrom="1" android:valueTo="1"
+ android:valueType="floatType">
<aapt:attr name="android:interpolator">
<pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.667,1 1.0,1.0"/>
</aapt:attr>
</objectAnimator>
<objectAnimator android:propertyName="scaleY" android:duration="83"
- android:startOffset="0" android:valueFrom="0.64"
- android:valueTo="0.64" android:valueType="floatType">
+ android:startOffset="0" android:valueFrom="1" android:valueTo="1"
+ android:valueType="floatType">
<aapt:attr name="android:interpolator">
<pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.667,1 1.0,1.0"/>
</aapt:attr>
</objectAnimator>
<objectAnimator android:propertyName="scaleX" android:duration="83"
- android:startOffset="83" android:valueFrom="0.64"
- android:valueTo="0.62" android:valueType="floatType">
+ android:startOffset="83" android:valueFrom="1"
+ android:valueTo="0.96" android:valueType="floatType">
<aapt:attr name="android:interpolator">
<pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.667,1 1.0,1.0"/>
</aapt:attr>
</objectAnimator>
<objectAnimator android:propertyName="scaleY" android:duration="83"
- android:startOffset="83" android:valueFrom="0.64"
- android:valueTo="0.62" android:valueType="floatType">
+ android:startOffset="83" android:valueFrom="1"
+ android:valueTo="0.96" android:valueType="floatType">
<aapt:attr name="android:interpolator">
<pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.667,1 1.0,1.0"/>
</aapt:attr>
</objectAnimator>
<objectAnimator android:propertyName="scaleX" android:duration="183"
- android:startOffset="167" android:valueFrom="0.62"
- android:valueTo="0.8" android:valueType="floatType">
+ android:startOffset="167" android:valueFrom="0.96"
+ android:valueTo="1.28" android:valueType="floatType">
<aapt:attr name="android:interpolator">
<pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.667,1 1.0,1.0"/>
</aapt:attr>
</objectAnimator>
<objectAnimator android:propertyName="scaleY" android:duration="183"
- android:startOffset="167" android:valueFrom="0.62"
- android:valueTo="0.8" android:valueType="floatType">
+ android:startOffset="167" android:valueFrom="0.96"
+ android:valueTo="1.28" android:valueType="floatType">
<aapt:attr name="android:interpolator">
<pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.667,1 1.0,1.0"/>
</aapt:attr>
</objectAnimator>
<objectAnimator android:propertyName="scaleX" android:duration="250"
- android:startOffset="350" android:valueFrom="0.8"
- android:valueTo="0.64" android:valueType="floatType">
+ android:startOffset="350" android:valueFrom="1.28"
+ android:valueTo="1" android:valueType="floatType">
<aapt:attr name="android:interpolator">
<pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.667,1 1.0,1.0"/>
</aapt:attr>
</objectAnimator>
<objectAnimator android:propertyName="scaleY" android:duration="250"
- android:startOffset="350" android:valueFrom="0.8"
- android:valueTo="0.64" android:valueType="floatType">
+ android:startOffset="350" android:valueFrom="1.28"
+ android:valueTo="1" android:valueType="floatType">
<aapt:attr name="android:interpolator">
<pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.667,1 1.0,1.0"/>
</aapt:attr>
@@ -182,13 +227,13 @@
</set>
</aapt:attr>
</target>
- <target android:name="_R_G_L_1_G_D_0_P_0">
+ <target android:name="_R_G_L_0_G_D_0_P_0">
<aapt:attr name="android:animation">
<set android:ordering="together">
<objectAnimator android:propertyName="pathData" android:duration="83"
android:startOffset="0"
- android:valueFrom="M-28.21 -25.03 C-28.21,-25.03 -27.85,-48.38 -27.97,-55.48 C-28,-57.63 -23.5,-79.87 -0.75,-79.82 C22.77,-79.76 27.75,-59.37 27.72,-58.27 C27.55,-52.88 27.93,-26.15 27.93,-26.15 "
- android:valueTo="M-28.21 -25.03 C-28.21,-25.03 -27.85,-48.38 -27.97,-55.48 C-28,-57.63 -23.5,-79.87 -0.75,-79.82 C22.77,-79.76 27.75,-59.37 27.72,-58.27 C27.55,-52.88 27.93,-26.15 27.93,-26.15 "
+ android:valueFrom="M14.33 14.33 C14.33,14.33 14.33,9.67 14.33,9.67 C14.33,7.09 12.24,5 9.67,5 C7.09,5 5,7.09 5,9.67 C5,9.67 5,14.33 5,14.33 "
+ android:valueTo="M14.33 14.33 C14.33,14.33 14.33,9.67 14.33,9.67 C14.33,7.09 12.24,5 9.67,5 C7.09,5 5,7.09 5,9.67 C5,9.67 5,14.33 5,14.33 "
android:valueType="pathType">
<aapt:attr name="android:interpolator">
<pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.667,1 1.0,1.0"/>
@@ -196,8 +241,8 @@
</objectAnimator>
<objectAnimator android:propertyName="pathData" android:duration="150"
android:startOffset="83"
- android:valueFrom="M-28.21 -25.03 C-28.21,-25.03 -27.85,-48.38 -27.97,-55.48 C-28,-57.63 -23.5,-79.87 -0.75,-79.82 C22.77,-79.76 27.75,-59.37 27.72,-58.27 C27.55,-52.88 27.93,-26.15 27.93,-26.15 "
- android:valueTo="M-28.02 -43.42 C-28.02,-43.42 -27.85,-48.38 -27.97,-55.48 C-28,-57.63 -23.5,-79.87 -0.75,-79.82 C22.77,-79.76 27.75,-59.37 27.72,-58.27 C27.55,-52.88 27.76,-43.67 27.76,-43.67 "
+ android:valueFrom="M14.33 14.33 C14.33,14.33 14.33,9.67 14.33,9.67 C14.33,7.09 12.24,5 9.67,5 C7.09,5 5,7.09 5,9.67 C5,9.67 5,14.33 5,14.33 "
+ android:valueTo="M14.31 10.37 C14.31,10.37 14.33,9.67 14.33,9.67 C14.33,7.09 12.24,5 9.67,5 C7.09,5 5,7.09 5,9.67 C5,9.67 4.97,10.37 4.97,10.37 "
android:valueType="pathType">
<aapt:attr name="android:interpolator">
<pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.667,1 1.0,1.0"/>
@@ -205,8 +250,8 @@
</objectAnimator>
<objectAnimator android:propertyName="pathData" android:duration="117"
android:startOffset="233"
- android:valueFrom="M-28.02 -43.42 C-28.02,-43.42 -27.85,-48.38 -27.97,-55.48 C-28,-57.63 -23.5,-79.87 -0.75,-79.82 C22.77,-79.76 27.75,-59.37 27.72,-58.27 C27.55,-52.88 27.76,-43.67 27.76,-43.67 "
- android:valueTo="M-28.21 -25.03 C-28.21,-25.03 -27.85,-48.38 -27.97,-55.48 C-28,-57.63 -23.5,-79.87 -0.75,-79.82 C22.77,-79.76 27.75,-59.37 27.72,-58.27 C27.55,-52.88 27.93,-26.15 27.93,-26.15 "
+ android:valueFrom="M14.31 10.37 C14.31,10.37 14.33,9.67 14.33,9.67 C14.33,7.09 12.24,5 9.67,5 C7.09,5 5,7.09 5,9.67 C5,9.67 4.97,10.37 4.97,10.37 "
+ android:valueTo="M14.33 14.33 C14.33,14.33 14.33,9.67 14.33,9.67 C14.33,7.09 12.24,5 9.67,5 C7.09,5 5,7.09 5,9.67 C5,9.67 5,14.33 5,14.33 "
android:valueType="pathType">
<aapt:attr name="android:interpolator">
<pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.667,1 1.0,1.0"/>
@@ -215,150 +260,88 @@
</set>
</aapt:attr>
</target>
- <target android:name="_R_G_L_1_G_T_1">
+ <target android:name="_R_G_L_0_G_T_1">
<aapt:attr name="android:animation">
<set android:ordering="together">
<objectAnimator android:propertyName="translateY" android:duration="83"
- android:startOffset="0" android:valueFrom="1.121"
- android:valueTo="1.121" android:valueType="floatType">
+ android:startOffset="0" android:valueFrom="0.34"
+ android:valueTo="0.34" android:valueType="floatType">
<aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.667,1 1.0,1.0"/>
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.384,0 0.536,1 1.0,1.0"/>
</aapt:attr>
</objectAnimator>
<objectAnimator android:propertyName="translateY" android:duration="150"
- android:startOffset="83" android:valueFrom="1.121"
- android:valueTo="3.749" android:valueType="floatType">
+ android:startOffset="83" android:valueFrom="0.34"
+ android:valueTo="4.364" android:valueType="floatType">
<aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.667,1 1.0,1.0"/>
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.384,0 0.536,1 1.0,1.0"/>
</aapt:attr>
</objectAnimator>
<objectAnimator android:propertyName="translateY" android:duration="117"
- android:startOffset="233" android:valueFrom="3.749"
- android:valueTo="1.121" android:valueType="floatType">
+ android:startOffset="233" android:valueFrom="4.364"
+ android:valueTo="0.34" android:valueType="floatType">
<aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.667,1 1.0,1.0"/>
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.442,0 0.594,1 1.0,1.0"/>
</aapt:attr>
</objectAnimator>
</set>
</aapt:attr>
</target>
- <target android:name="_R_G_L_1_G_N_5_T_0">
+ <target android:name="_R_G_L_0_G_N_7_T_0">
<aapt:attr name="android:animation">
<set android:ordering="together">
<objectAnimator android:propertyName="scaleX" android:duration="83"
- android:startOffset="0" android:valueFrom="0.64"
- android:valueTo="0.64" android:valueType="floatType">
- <aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.667,1 1.0,1.0"/>
- </aapt:attr>
- </objectAnimator>
- <objectAnimator android:propertyName="scaleY" android:duration="83"
- android:startOffset="0" android:valueFrom="0.64"
- android:valueTo="0.64" android:valueType="floatType">
- <aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.667,1 1.0,1.0"/>
- </aapt:attr>
- </objectAnimator>
- <objectAnimator android:propertyName="scaleX" android:duration="83"
- android:startOffset="83" android:valueFrom="0.64"
- android:valueTo="0.62" android:valueType="floatType">
- <aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.667,1 1.0,1.0"/>
- </aapt:attr>
- </objectAnimator>
- <objectAnimator android:propertyName="scaleY" android:duration="83"
- android:startOffset="83" android:valueFrom="0.64"
- android:valueTo="0.62" android:valueType="floatType">
- <aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.667,1 1.0,1.0"/>
- </aapt:attr>
- </objectAnimator>
- <objectAnimator android:propertyName="scaleX" android:duration="183"
- android:startOffset="167" android:valueFrom="0.62"
- android:valueTo="0.8" android:valueType="floatType">
- <aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.667,1 1.0,1.0"/>
- </aapt:attr>
- </objectAnimator>
- <objectAnimator android:propertyName="scaleY" android:duration="183"
- android:startOffset="167" android:valueFrom="0.62"
- android:valueTo="0.8" android:valueType="floatType">
- <aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.667,1 1.0,1.0"/>
- </aapt:attr>
- </objectAnimator>
- <objectAnimator android:propertyName="scaleX" android:duration="250"
- android:startOffset="350" android:valueFrom="0.8"
- android:valueTo="0.64" android:valueType="floatType">
- <aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.667,1 1.0,1.0"/>
- </aapt:attr>
- </objectAnimator>
- <objectAnimator android:propertyName="scaleY" android:duration="250"
- android:startOffset="350" android:valueFrom="0.8"
- android:valueTo="0.64" android:valueType="floatType">
- <aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.667,1 1.0,1.0"/>
- </aapt:attr>
- </objectAnimator>
- </set>
- </aapt:attr>
- </target>
- <target android:name="_R_G_L_0_G_N_5_T_0">
- <aapt:attr name="android:animation">
- <set android:ordering="together">
- <objectAnimator android:propertyName="scaleX" android:duration="83"
- android:startOffset="0" android:valueFrom="0.64"
- android:valueTo="0.64" android:valueType="floatType">
+ android:startOffset="0" android:valueFrom="1" android:valueTo="1"
+ android:valueType="floatType">
<aapt:attr name="android:interpolator">
<pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.667,1 1.0,1.0"/>
</aapt:attr>
</objectAnimator>
<objectAnimator android:propertyName="scaleY" android:duration="83"
- android:startOffset="0" android:valueFrom="0.64"
- android:valueTo="0.64" android:valueType="floatType">
+ android:startOffset="0" android:valueFrom="1" android:valueTo="1"
+ android:valueType="floatType">
<aapt:attr name="android:interpolator">
<pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.667,1 1.0,1.0"/>
</aapt:attr>
</objectAnimator>
<objectAnimator android:propertyName="scaleX" android:duration="83"
- android:startOffset="83" android:valueFrom="0.64"
- android:valueTo="0.62" android:valueType="floatType">
+ android:startOffset="83" android:valueFrom="1"
+ android:valueTo="0.96" android:valueType="floatType">
<aapt:attr name="android:interpolator">
<pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.667,1 1.0,1.0"/>
</aapt:attr>
</objectAnimator>
<objectAnimator android:propertyName="scaleY" android:duration="83"
- android:startOffset="83" android:valueFrom="0.64"
- android:valueTo="0.62" android:valueType="floatType">
+ android:startOffset="83" android:valueFrom="1"
+ android:valueTo="0.96" android:valueType="floatType">
<aapt:attr name="android:interpolator">
<pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.667,1 1.0,1.0"/>
</aapt:attr>
</objectAnimator>
<objectAnimator android:propertyName="scaleX" android:duration="183"
- android:startOffset="167" android:valueFrom="0.62"
- android:valueTo="0.8" android:valueType="floatType">
+ android:startOffset="167" android:valueFrom="0.96"
+ android:valueTo="1.28" android:valueType="floatType">
<aapt:attr name="android:interpolator">
<pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.667,1 1.0,1.0"/>
</aapt:attr>
</objectAnimator>
<objectAnimator android:propertyName="scaleY" android:duration="183"
- android:startOffset="167" android:valueFrom="0.62"
- android:valueTo="0.8" android:valueType="floatType">
+ android:startOffset="167" android:valueFrom="0.96"
+ android:valueTo="1.28" android:valueType="floatType">
<aapt:attr name="android:interpolator">
<pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.667,1 1.0,1.0"/>
</aapt:attr>
</objectAnimator>
<objectAnimator android:propertyName="scaleX" android:duration="250"
- android:startOffset="350" android:valueFrom="0.8"
- android:valueTo="0.64" android:valueType="floatType">
+ android:startOffset="350" android:valueFrom="1.28"
+ android:valueTo="1" android:valueType="floatType">
<aapt:attr name="android:interpolator">
<pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.667,1 1.0,1.0"/>
</aapt:attr>
</objectAnimator>
<objectAnimator android:propertyName="scaleY" android:duration="250"
- android:startOffset="350" android:valueFrom="0.8"
- android:valueTo="0.64" android:valueType="floatType">
+ android:startOffset="350" android:valueFrom="1.28"
+ android:valueTo="1" android:valueType="floatType">
<aapt:attr name="android:interpolator">
<pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.667,1 1.0,1.0"/>
</aapt:attr>
@@ -369,7 +352,7 @@
<target android:name="time_group">
<aapt:attr name="android:animation">
<set android:ordering="together">
- <objectAnimator android:propertyName="translateX" android:duration="1000"
+ <objectAnimator android:propertyName="translateX" android:duration="717"
android:startOffset="0" android:valueFrom="0" android:valueTo="1"
android:valueType="floatType"/>
</set>
diff --git a/core/res/res/anim/lock_to_error.xml b/core/res/res/anim/lock_to_error.xml
index afe22909d19a..e356f26dde59 100755..100644
--- a/core/res/res/anim/lock_to_error.xml
+++ b/core/res/res/anim/lock_to_error.xml
@@ -1,5 +1,4 @@
-<!--
- Copyright (C) 2019 The Android Open Source Project
+<!-- Copyright (C) 2019 The Android Open Source Project
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
@@ -19,161 +18,157 @@
<vector android:height="32dp" android:width="32dp" android:viewportHeight="32"
android:viewportWidth="32">
<group android:name="_R_G">
- <group android:name="_R_G_L_2_G_N_2_T_0" android:translateX="7.75"
- android:translateY="12.649999999999999" android:pivotX="8.25"
- android:pivotY="7.25" android:rotation="0" android:scaleX="1.3"
- android:scaleY="1.3">
- <group android:name="_R_G_L_2_G" android:translateX="6"
- android:translateY="4.954" android:pivotX="2.25" android:pivotY="2.25"
- android:scaleX="0.98462" android:scaleY="0.98462">
- <path android:name="_R_G_L_2_G_D_0_P_0" android:fillColor="#000"
+ <group android:name="_R_G_L_2_G" android:translateX="1.6669999999999998"
+ android:translateY="6.9929999999999986" android:pivotX="14.333"
+ android:pivotY="13" android:rotation="0">
+ <path android:name="_R_G_L_2_G_D_0_P_0" android:strokeColor="#ffffff"
+ android:strokeLineCap="round" android:strokeLineJoin="round"
+ android:strokeWidth="2" android:strokeAlpha="1"
+ android:pathData=" M22.33 21 C22.33,21 6.33,21 6.33,21 C5.6,21 5,20.4 5,19.67 C5,19.67 5,6.33 5,6.33 C5,5.6 5.6,5 6.33,5 C6.33,5 22.33,5 22.33,5 C23.07,5 23.67,5.6 23.67,6.33 C23.67,6.33 23.67,19.67 23.67,19.67 C23.67,20.4 23.07,21 22.33,21c "/>
+ </group>
+ <group android:name="_R_G_L_1_G_N_4_T_0" android:translateX="1.6669999999999998"
+ android:translateY="6.9929999999999986" android:pivotX="14.333"
+ android:pivotY="13" android:rotation="0">
+ <group android:name="_R_G_L_1_G" android:translateX="11.583"
+ android:translateY="10.257">
+ <path android:name="_R_G_L_1_G_D_0_P_0" android:fillColor="#ffffff"
android:fillAlpha="1" android:fillType="nonZero"
- android:pathData=" M2.25 0.25 C3.35,0.25 4.25,1.15 4.25,2.25 C4.25,3.35 3.35,4.25 2.25,4.25 C1.15,4.25 0.25,3.35 0.25,2.25 C0.25,1.15 1.15,0.25 2.25,0.25c "/>
+ android:pathData=" M2.75 0.25 C4.13,0.25 5.25,1.37 5.25,2.75 C5.25,4.13 4.13,5.25 2.75,5.25 C1.37,5.25 0.25,4.13 0.25,2.75 C0.25,1.37 1.37,0.25 2.75,0.25c "/>
</group>
</group>
- <group android:name="_R_G_L_1_G_N_2_T_0" android:translateX="7.75"
- android:translateY="12.649999999999999" android:pivotX="8.25"
- android:pivotY="7.25" android:rotation="0" android:scaleX="1.3"
- android:scaleY="1.3">
- <group android:name="_R_G_L_1_G" android:translateX="-16.273"
- android:translateY="32.312" android:pivotX="27.965" android:pivotY="-32"
- android:scaleX="0.12308" android:scaleY="0.12308">
- <path android:name="_R_G_L_1_G_D_0_P_0" android:strokeColor="#000"
+ <group android:name="_R_G_L_0_G_N_4_T_0" android:translateX="1.6669999999999998"
+ android:translateY="6.9929999999999986" android:pivotX="14.333"
+ android:pivotY="13" android:rotation="0">
+ <group android:name="_R_G_L_0_G" android:translateX="4.666"
+ android:translateY="-9.327">
+ <path android:name="_R_G_L_0_G_D_0_P_0" android:strokeColor="#ffffff"
android:strokeLineCap="round" android:strokeLineJoin="round"
- android:strokeWidth="16" android:strokeAlpha="1"
- android:pathData=" M-28.21 -25.03 C-28.21,-25.03 -27.85,-48.38 -27.97,-55.48 C-28,-57.63 -23.5,-79.87 -0.75,-79.82 C22.77,-79.76 27.75,-59.37 27.72,-58.27 C27.55,-52.88 27.93,-26.15 27.93,-26.15 "/>
+ android:strokeWidth="2" android:strokeAlpha="1"
+ android:pathData=" M14.33 14.33 C14.33,14.33 14.33,9.67 14.33,9.67 C14.33,7.09 12.24,5 9.67,5 C7.09,5 5,7.09 5,9.67 C5,9.67 5,14.33 5,14.33 "/>
</group>
</group>
- <group android:name="_R_G_L_0_G" android:translateX="7.75"
- android:translateY="12.649999999999999" android:pivotX="8.25"
- android:pivotY="7.25" android:rotation="0" android:scaleX="1.3"
- android:scaleY="1.3">
- <path android:name="_R_G_L_0_G_D_0_P_0" android:fillColor="#000"
- android:fillAlpha="1" android:fillType="nonZero"
- android:pathData=" M14.25 0.25 C14.25,0.25 12.75,0.25 12.75,0.25 C12.75,0.25 10.75,0.25 10.75,0.25 C10.75,0.25 5.75,0.25 5.75,0.25 C5.75,0.25 3.75,0.25 3.75,0.25 C3.75,0.25 2.25,0.25 2.25,0.25 C1.15,0.25 0.25,1.15 0.25,2.25 C0.25,2.25 0.25,12.25 0.25,12.25 C0.25,13.35 1.15,14.25 2.25,14.25 C2.25,14.25 14.25,14.25 14.25,14.25 C15.35,14.25 16.25,13.35 16.25,12.25 C16.25,12.25 16.25,2.25 16.25,2.25 C16.25,1.15 15.35,0.25 14.25,0.25c M14.25 12.25 C14.25,12.25 2.25,12.25 2.25,12.25 C2.25,12.25 2.25,2.25 2.25,2.25 C2.25,2.25 3.75,2.25 3.75,2.25 C3.75,2.25 12.75,2.25 12.75,2.25 C12.75,2.25 14.25,2.25 14.25,2.25 C14.25,2.25 14.25,12.25 14.25,12.25c "/>
- </group>
</group>
<group android:name="time_group"/>
</vector>
</aapt:attr>
- <target android:name="_R_G_L_2_G_N_2_T_0">
+ <target android:name="_R_G_L_2_G">
<aapt:attr name="android:animation">
<set android:ordering="together">
<objectAnimator android:propertyName="rotation" android:duration="133"
android:startOffset="0" android:valueFrom="0" android:valueTo="0"
android:valueType="floatType">
<aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.44,0 0.601,1 1.0,1.0"/>
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.465,0 0.558,1 1.0,1.0"/>
</aapt:attr>
</objectAnimator>
- <objectAnimator android:propertyName="rotation" android:duration="120"
+ <objectAnimator android:propertyName="rotation" android:duration="117"
android:startOffset="133" android:valueFrom="0"
android:valueTo="-10" android:valueType="floatType">
<aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.44,0 0.601,1 1.0,1.0"/>
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.465,0 0.558,1 1.0,1.0"/>
</aapt:attr>
</objectAnimator>
- <objectAnimator android:propertyName="rotation" android:duration="97"
- android:startOffset="253" android:valueFrom="-10"
+ <objectAnimator android:propertyName="rotation" android:duration="100"
+ android:startOffset="250" android:valueFrom="-10"
android:valueTo="10" android:valueType="floatType">
<aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.531,0 0.389,1 1.0,1.0"/>
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.51,0 0.531,1 1.0,1.0"/>
</aapt:attr>
</objectAnimator>
<objectAnimator android:propertyName="rotation" android:duration="100"
android:startOffset="350" android:valueFrom="10"
android:valueTo="-5" android:valueType="floatType">
<aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.499,0 0.489,1 1.0,1.0"/>
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.469,0 0.599,1 1.0,1.0"/>
</aapt:attr>
</objectAnimator>
<objectAnimator android:propertyName="rotation" android:duration="167"
android:startOffset="450" android:valueFrom="-5" android:valueTo="0"
android:valueType="floatType">
<aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.293,0 0.689,1 1.0,1.0"/>
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.384,0 0.565,1 1.0,1.0"/>
</aapt:attr>
</objectAnimator>
</set>
</aapt:attr>
</target>
- <target android:name="_R_G_L_1_G_N_2_T_0">
+ <target android:name="_R_G_L_1_G_N_4_T_0">
<aapt:attr name="android:animation">
<set android:ordering="together">
<objectAnimator android:propertyName="rotation" android:duration="133"
android:startOffset="0" android:valueFrom="0" android:valueTo="0"
android:valueType="floatType">
<aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.44,0 0.601,1 1.0,1.0"/>
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.465,0 0.558,1 1.0,1.0"/>
</aapt:attr>
</objectAnimator>
- <objectAnimator android:propertyName="rotation" android:duration="120"
+ <objectAnimator android:propertyName="rotation" android:duration="117"
android:startOffset="133" android:valueFrom="0"
android:valueTo="-10" android:valueType="floatType">
<aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.44,0 0.601,1 1.0,1.0"/>
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.465,0 0.558,1 1.0,1.0"/>
</aapt:attr>
</objectAnimator>
- <objectAnimator android:propertyName="rotation" android:duration="97"
- android:startOffset="253" android:valueFrom="-10"
+ <objectAnimator android:propertyName="rotation" android:duration="100"
+ android:startOffset="250" android:valueFrom="-10"
android:valueTo="10" android:valueType="floatType">
<aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.531,0 0.389,1 1.0,1.0"/>
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.51,0 0.531,1 1.0,1.0"/>
</aapt:attr>
</objectAnimator>
<objectAnimator android:propertyName="rotation" android:duration="100"
android:startOffset="350" android:valueFrom="10"
android:valueTo="-5" android:valueType="floatType">
<aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.499,0 0.489,1 1.0,1.0"/>
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.469,0 0.599,1 1.0,1.0"/>
</aapt:attr>
</objectAnimator>
<objectAnimator android:propertyName="rotation" android:duration="167"
android:startOffset="450" android:valueFrom="-5" android:valueTo="0"
android:valueType="floatType">
<aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.293,0 0.689,1 1.0,1.0"/>
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.384,0 0.565,1 1.0,1.0"/>
</aapt:attr>
</objectAnimator>
</set>
</aapt:attr>
</target>
- <target android:name="_R_G_L_0_G">
+ <target android:name="_R_G_L_0_G_N_4_T_0">
<aapt:attr name="android:animation">
<set android:ordering="together">
<objectAnimator android:propertyName="rotation" android:duration="133"
android:startOffset="0" android:valueFrom="0" android:valueTo="0"
android:valueType="floatType">
<aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.44,0 0.601,1 1.0,1.0"/>
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.465,0 0.558,1 1.0,1.0"/>
</aapt:attr>
</objectAnimator>
- <objectAnimator android:propertyName="rotation" android:duration="120"
+ <objectAnimator android:propertyName="rotation" android:duration="117"
android:startOffset="133" android:valueFrom="0"
android:valueTo="-10" android:valueType="floatType">
<aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.44,0 0.601,1 1.0,1.0"/>
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.465,0 0.558,1 1.0,1.0"/>
</aapt:attr>
</objectAnimator>
- <objectAnimator android:propertyName="rotation" android:duration="97"
- android:startOffset="253" android:valueFrom="-10"
+ <objectAnimator android:propertyName="rotation" android:duration="100"
+ android:startOffset="250" android:valueFrom="-10"
android:valueTo="10" android:valueType="floatType">
<aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.531,0 0.389,1 1.0,1.0"/>
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.51,0 0.531,1 1.0,1.0"/>
</aapt:attr>
</objectAnimator>
<objectAnimator android:propertyName="rotation" android:duration="100"
android:startOffset="350" android:valueFrom="10"
android:valueTo="-5" android:valueType="floatType">
<aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.499,0 0.489,1 1.0,1.0"/>
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.469,0 0.599,1 1.0,1.0"/>
</aapt:attr>
</objectAnimator>
<objectAnimator android:propertyName="rotation" android:duration="167"
android:startOffset="450" android:valueFrom="-5" android:valueTo="0"
android:valueType="floatType">
<aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.293,0 0.689,1 1.0,1.0"/>
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.384,0 0.565,1 1.0,1.0"/>
</aapt:attr>
</objectAnimator>
</set>
@@ -182,7 +177,7 @@
<target android:name="time_group">
<aapt:attr name="android:animation">
<set android:ordering="together">
- <objectAnimator android:propertyName="translateX" android:duration="1000"
+ <objectAnimator android:propertyName="translateX" android:duration="717"
android:startOffset="0" android:valueFrom="0" android:valueTo="1"
android:valueType="floatType"/>
</set>
diff --git a/core/res/res/anim/lock_unlock.xml b/core/res/res/anim/lock_unlock.xml
index c8b260877c24..91d44320d8c2 100755..100644
--- a/core/res/res/anim/lock_unlock.xml
+++ b/core/res/res/anim/lock_unlock.xml
@@ -1,5 +1,4 @@
-<!--
- Copyright (C) 2019 The Android Open Source Project
+<!-- Copyright (C) 2019 The Android Open Source Project
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
@@ -14,85 +13,114 @@
limitations under the License.
-->
<animated-vector xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:aapt="http://schemas.android.com/aapt">
+ xmlns:aapt="http://schemas.android.com/aapt">
<aapt:attr name="android:drawable">
- <vector android:height="40dp" android:width="32dp" android:viewportHeight="40"
- android:viewportWidth="32">
+ <vector
+ android:width="32dp"
+ android:height="42dp"
+ android:viewportWidth="32"
+ android:viewportHeight="42">
<group android:name="_R_G">
- <group android:name="_R_G_L_2_G_N_1_T_0" android:translateX="16"
- android:translateY="20" android:scaleX="1.3" android:scaleY="1.3">
- <group android:name="_R_G_L_2_G_T_1" android:translateY="3">
- <group android:name="_R_G_L_2_G" android:translateX="-8.25"
- android:translateY="-7.25">
- <path android:name="_R_G_L_2_G_D_0_P_0" android:fillColor="#000"
- android:fillAlpha="1" android:fillType="nonZero"
- android:pathData=" M14.25 0.25 C14.25,0.25 12.75,0.25 12.75,0.25 C12.75,0.25 10.75,0.25 10.75,0.25 C10.75,0.25 5.75,0.25 5.75,0.25 C5.75,0.25 3.75,0.25 3.75,0.25 C3.75,0.25 2.25,0.25 2.25,0.25 C1.15,0.25 0.25,1.15 0.25,2.25 C0.25,2.25 0.25,12.25 0.25,12.25 C0.25,13.35 1.15,14.25 2.25,14.25 C2.25,14.25 14.25,14.25 14.25,14.25 C15.35,14.25 16.25,13.35 16.25,12.25 C16.25,12.25 16.25,2.25 16.25,2.25 C16.25,1.15 15.35,0.25 14.25,0.25c M14.25 12.25 C14.25,12.25 2.25,12.25 2.25,12.25 C2.25,12.25 2.25,2.25 2.25,2.25 C2.25,2.25 3.75,2.25 3.75,2.25 C3.75,2.25 12.75,2.25 12.75,2.25 C12.75,2.25 14.25,2.25 14.25,2.25 C14.25,2.25 14.25,12.25 14.25,12.25c "/>
- </group>
+ <group
+ android:name="_R_G_L_2_G_T_1"
+ android:translateX="16"
+ android:translateY="24.993">
+ <group
+ android:name="_R_G_L_2_G"
+ android:translateX="-14.333"
+ android:translateY="-13">
+ <path
+ android:name="_R_G_L_2_G_D_0_P_0"
+ android:pathData=" M22.33 21 C22.33,21 6.33,21 6.33,21 C5.6,21 5,20.4 5,19.67 C5,19.67 5,6.33 5,6.33 C5,5.6 5.6,5 6.33,5 C6.33,5 22.33,5 22.33,5 C23.07,5 23.67,5.6 23.67,6.33 C23.67,6.33 23.67,19.67 23.67,19.67 C23.67,20.4 23.07,21 22.33,21c "
+ android:strokeWidth="2"
+ android:strokeAlpha="1"
+ android:strokeColor="#ffffff" />
</group>
</group>
- <group android:name="_R_G_L_1_G_N_4_N_1_T_0" android:translateX="16"
- android:translateY="20" android:scaleX="1.3" android:scaleY="1.3">
- <group android:name="_R_G_L_1_G_N_4_T_1" android:translateY="3">
- <group android:name="_R_G_L_1_G_N_4_T_0" android:translateX="-8.25"
- android:translateY="-7.25">
- <group android:name="_R_G_L_1_G" android:translateX="6"
- android:translateY="5" android:pivotX="2.25"
- android:pivotY="2.25" android:scaleX="1" android:scaleY="1">
- <path android:name="_R_G_L_1_G_D_0_P_0" android:fillColor="#000"
- android:fillAlpha="1" android:fillType="nonZero"
- android:pathData=" M2.25 0.25 C3.35,0.25 4.25,1.15 4.25,2.25 C4.25,3.35 3.35,4.25 2.25,4.25 C1.15,4.25 0.25,3.35 0.25,2.25 C0.25,1.15 1.15,0.25 2.25,0.25c "/>
- </group>
+ <group
+ android:name="_R_G_L_1_G_N_4_T_1"
+ android:translateX="16"
+ android:translateY="24.993">
+ <group
+ android:name="_R_G_L_1_G_N_4_T_0"
+ android:translateX="-14.333"
+ android:translateY="-13">
+ <group
+ android:name="_R_G_L_1_G"
+ android:pivotX="2.75"
+ android:pivotY="2.75"
+ android:scaleX="1"
+ android:scaleY="1"
+ android:translateX="11.583"
+ android:translateY="10.257">
+ <path
+ android:name="_R_G_L_1_G_D_0_P_0"
+ android:fillAlpha="1"
+ android:fillColor="#ffffff"
+ android:fillType="nonZero"
+ android:pathData=" M2.75 0.25 C4.13,0.25 5.25,1.37 5.25,2.75 C5.25,4.13 4.13,5.25 2.75,5.25 C1.37,5.25 0.25,4.13 0.25,2.75 C0.25,1.37 1.37,0.25 2.75,0.25c " />
</group>
</group>
</group>
- <group android:name="_R_G_L_0_G_N_4_N_1_T_0" android:translateX="16"
- android:translateY="20" android:scaleX="1.3" android:scaleY="1.3">
- <group android:name="_R_G_L_0_G_N_4_T_1" android:translateY="3">
- <group android:name="_R_G_L_0_G_N_4_T_0" android:translateX="-8.25"
- android:translateY="-7.25">
- <group android:name="_R_G_L_0_G" android:translateX="-16.219"
- android:translateY="32.25" android:pivotX="27.965"
- android:pivotY="-32" android:scaleX="0.125"
- android:scaleY="0.125">
- <path android:name="_R_G_L_0_G_D_0_P_0" android:fillColor="#ff0000"
- android:fillAlpha="0" android:fillType="nonZero"
- android:pathData=" M-28.21 -31.92 C-28.21,-31.92 -27.85,-48.38 -27.97,-55.48 C-28,-57.63 -23.5,-79.87 -0.75,-79.82 C22.77,-79.76 27.75,-59.37 27.72,-58.27 C27.55,-52.88 27.97,-31.67 27.97,-31.67 "/>
- <path android:name="_R_G_L_0_G_D_1_P_0"
- android:strokeColor="#000" android:strokeLineCap="round"
- android:strokeLineJoin="round" android:strokeWidth="16"
- android:strokeAlpha="1"
- android:pathData=" M-28.21 -31.92 C-28.21,-31.92 -27.85,-48.38 -27.97,-55.48 C-28,-57.63 -23.5,-79.87 -0.75,-79.82 C22.77,-79.76 27.75,-59.37 27.72,-58.27 C27.55,-52.88 27.97,-31.67 27.97,-31.67 "/>
- </group>
+ <group
+ android:name="_R_G_L_0_G_N_4_T_1"
+ android:translateX="16"
+ android:translateY="24.993">
+ <group
+ android:name="_R_G_L_0_G_N_4_T_0"
+ android:translateX="-14.333"
+ android:translateY="-13">
+ <group
+ android:name="_R_G_L_0_G"
+ android:translateX="4.666"
+ android:translateY="-9.327">
+ <path
+ android:name="_R_G_L_0_G_D_0_P_0"
+ android:pathData=" M14.33 14.33 C14.33,14.33 14.33,9.67 14.33,9.67 C14.33,7.09 12.24,5 9.67,5 C7.09,5 5,7.09 5,9.67 C5,9.67 5,14.33 5,14.33 "
+ android:strokeWidth="2"
+ android:strokeAlpha="1"
+ android:strokeColor="#ffffff" />
</group>
</group>
</group>
</group>
- <group android:name="time_group"/>
+ <group android:name="time_group" />
</vector>
</aapt:attr>
<target android:name="_R_G_L_2_G_T_1">
<aapt:attr name="android:animation">
<set android:ordering="together">
- <objectAnimator android:propertyName="translateY" android:duration="133"
- android:startOffset="0" android:valueFrom="3"
- android:valueTo="1.625" android:valueType="floatType">
+ <objectAnimator
+ android:duration="133"
+ android:propertyName="translateY"
+ android:startOffset="0"
+ android:valueFrom="24.993"
+ android:valueTo="22.493"
+ android:valueType="floatType">
<aapt:attr name="android:interpolator">
- <pathInterpolator
- android:pathData="M 0.0,0.0 c0.075,0.167 0.622,1 1.0,1.0"/>
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.378,0 0.622,1 1.0,1.0" />
</aapt:attr>
</objectAnimator>
- <objectAnimator android:propertyName="translateY" android:duration="133"
- android:startOffset="133" android:valueFrom="1.625"
- android:valueTo="3.699" android:valueType="floatType">
+ <objectAnimator
+ android:duration="133"
+ android:propertyName="translateY"
+ android:startOffset="133"
+ android:valueFrom="22.493"
+ android:valueTo="25.993"
+ android:valueType="floatType">
<aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.352,0 0.717,1 1.0,1.0"/>
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.41,0 0.616,1 1.0,1.0" />
</aapt:attr>
</objectAnimator>
- <objectAnimator android:propertyName="translateY" android:duration="100"
- android:startOffset="267" android:valueFrom="3.699"
- android:valueTo="3" android:valueType="floatType">
+ <objectAnimator
+ android:duration="100"
+ android:propertyName="translateY"
+ android:startOffset="267"
+ android:valueFrom="25.993"
+ android:valueTo="24.993"
+ android:valueType="floatType">
<aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.356,0 0.527,1 1.0,1.0"/>
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.427,0 0.508,1 1.0,1.0" />
</aapt:attr>
</objectAnimator>
</set>
@@ -101,32 +129,48 @@
<target android:name="_R_G_L_1_G">
<aapt:attr name="android:animation">
<set android:ordering="together">
- <objectAnimator android:propertyName="scaleX" android:duration="100"
- android:startOffset="0" android:valueFrom="1" android:valueTo="0.85"
- android:valueType="floatType">
+ <objectAnimator
+ android:duration="100"
+ android:propertyName="scaleX"
+ android:startOffset="0"
+ android:valueFrom="1"
+ android:valueTo="0.8200000000000001"
+ android:valueType="floatType">
<aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.4,0 0.2,1 1.0,1.0"/>
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.418,0 0.565,1 1.0,1.0" />
</aapt:attr>
</objectAnimator>
- <objectAnimator android:propertyName="scaleY" android:duration="100"
- android:startOffset="0" android:valueFrom="1" android:valueTo="0.85"
- android:valueType="floatType">
+ <objectAnimator
+ android:duration="100"
+ android:propertyName="scaleY"
+ android:startOffset="0"
+ android:valueFrom="1"
+ android:valueTo="0.8200000000000001"
+ android:valueType="floatType">
<aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.4,0 0.2,1 1.0,1.0"/>
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.418,0 0.565,1 1.0,1.0" />
</aapt:attr>
</objectAnimator>
- <objectAnimator android:propertyName="scaleX" android:duration="283"
- android:startOffset="100" android:valueFrom="0.85"
- android:valueTo="1" android:valueType="floatType">
+ <objectAnimator
+ android:duration="283"
+ android:propertyName="scaleX"
+ android:startOffset="100"
+ android:valueFrom="0.8200000000000001"
+ android:valueTo="1"
+ android:valueType="floatType">
<aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.4,0 0.2,1 1.0,1.0"/>
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.535,1 1.0,1.0" />
</aapt:attr>
</objectAnimator>
- <objectAnimator android:propertyName="scaleY" android:duration="283"
- android:startOffset="100" android:valueFrom="0.85"
- android:valueTo="1" android:valueType="floatType">
+ <objectAnimator
+ android:duration="283"
+ android:propertyName="scaleY"
+ android:startOffset="100"
+ android:valueFrom="0.8200000000000001"
+ android:valueTo="1"
+ android:valueType="floatType">
<aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.4,0 0.2,1 1.0,1.0"/>
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.333,0 0.535,1 1.0,1.0" />
</aapt:attr>
</objectAnimator>
</set>
@@ -135,26 +179,37 @@
<target android:name="_R_G_L_1_G_N_4_T_1">
<aapt:attr name="android:animation">
<set android:ordering="together">
- <objectAnimator android:propertyName="translateY" android:duration="133"
- android:startOffset="0" android:valueFrom="3"
- android:valueTo="1.625" android:valueType="floatType">
+ <objectAnimator
+ android:duration="133"
+ android:propertyName="translateY"
+ android:startOffset="0"
+ android:valueFrom="24.993"
+ android:valueTo="22.493"
+ android:valueType="floatType">
<aapt:attr name="android:interpolator">
- <pathInterpolator
- android:pathData="M 0.0,0.0 c0.075,0.167 0.622,1 1.0,1.0"/>
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.378,0 0.622,1 1.0,1.0" />
</aapt:attr>
</objectAnimator>
- <objectAnimator android:propertyName="translateY" android:duration="133"
- android:startOffset="133" android:valueFrom="1.625"
- android:valueTo="3.699" android:valueType="floatType">
+ <objectAnimator
+ android:duration="133"
+ android:propertyName="translateY"
+ android:startOffset="133"
+ android:valueFrom="22.493"
+ android:valueTo="25.993"
+ android:valueType="floatType">
<aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.352,0 0.717,1 1.0,1.0"/>
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.41,0 0.616,1 1.0,1.0" />
</aapt:attr>
</objectAnimator>
- <objectAnimator android:propertyName="translateY" android:duration="100"
- android:startOffset="267" android:valueFrom="3.699"
- android:valueTo="3" android:valueType="floatType">
+ <objectAnimator
+ android:duration="100"
+ android:propertyName="translateY"
+ android:startOffset="267"
+ android:valueFrom="25.993"
+ android:valueTo="24.993"
+ android:valueType="floatType">
<aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.356,0 0.527,1 1.0,1.0"/>
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.427,0 0.508,1 1.0,1.0" />
</aapt:attr>
</objectAnimator>
</set>
@@ -163,46 +218,26 @@
<target android:name="_R_G_L_0_G_D_0_P_0">
<aapt:attr name="android:animation">
<set android:ordering="together">
- <objectAnimator android:propertyName="pathData" android:duration="67"
- android:startOffset="0"
- android:valueFrom="M-28.21 -31.92 C-28.21,-31.92 -27.85,-48.38 -27.97,-55.48 C-28,-57.63 -23.5,-79.87 -0.75,-79.82 C22.77,-79.76 27.75,-59.37 27.72,-58.27 C27.55,-52.88 27.97,-31.67 27.97,-31.67 "
- android:valueTo="M-27.97 -59.3 C-27.97,-59.3 -28,-64.5 -27.97,-66.23 C-27.92,-68.37 -23.5,-90.63 -0.75,-90.57 C22.77,-90.51 27.75,-70.12 27.72,-69.02 C27.55,-63.63 27.97,-25.67 27.97,-25.67 "
- android:valueType="pathType">
- <aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.353,0 0.2,1 1.0,1.0"/>
- </aapt:attr>
- </objectAnimator>
- <objectAnimator android:propertyName="pathData" android:duration="333"
- android:startOffset="67"
- android:valueFrom="M-27.97 -59.3 C-27.97,-59.3 -28,-64.5 -27.97,-66.23 C-27.92,-68.37 -23.5,-90.63 -0.75,-90.57 C22.77,-90.51 27.75,-70.12 27.72,-69.02 C27.55,-63.63 27.97,-25.67 27.97,-25.67 "
- android:valueTo="M79.79 -48.55 C79.79,-48.55 79.75,-53.75 79.78,-55.48 C79.83,-57.62 79.08,-78.36 53.07,-78.83 C29.5,-79.25 25.2,-59.38 25.22,-58.27 C25.25,-56.25 24.97,-31.17 24.97,-31.17 "
- android:valueType="pathType">
- <aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.542,0 0.026,1 1.0,1.0"/>
- </aapt:attr>
- </objectAnimator>
- </set>
- </aapt:attr>
- </target>
- <target android:name="_R_G_L_0_G_D_1_P_0">
- <aapt:attr name="android:animation">
- <set android:ordering="together">
- <objectAnimator android:propertyName="pathData" android:duration="67"
- android:startOffset="0"
- android:valueFrom="M-28.21 -31.92 C-28.21,-31.92 -27.85,-48.38 -27.97,-55.48 C-28,-57.63 -23.5,-79.87 -0.75,-79.82 C22.77,-79.76 27.75,-59.37 27.72,-58.27 C27.55,-52.88 27.97,-31.67 27.97,-31.67 "
- android:valueTo="M-27.97 -59.3 C-27.97,-59.3 -28,-64.5 -27.97,-66.23 C-27.92,-68.37 -23.5,-90.63 -0.75,-90.57 C22.77,-90.51 27.75,-70.12 27.72,-69.02 C27.55,-63.63 27.97,-25.67 27.97,-25.67 "
- android:valueType="pathType">
+ <objectAnimator
+ android:duration="67"
+ android:propertyName="pathData"
+ android:startOffset="0"
+ android:valueFrom="M14.33 14.33 C14.33,14.33 14.33,9.67 14.33,9.67 C14.33,7.09 12.24,5 9.67,5 C7.09,5 5,7.09 5,9.67 C5,9.67 5,14.33 5,14.33 "
+ android:valueTo="M14.33 14.33 C14.33,14.33 14.29,6.17 14.29,6.17 C14.29,3.59 12.2,1.5 9.63,1.5 C7.05,1.5 4.96,3.59 4.96,6.17 C4.96,6.17 4.96,7.33 4.96,7.33 "
+ android:valueType="pathType">
<aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.353,0 0.2,1 1.0,1.0"/>
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.56,0 0.439,1 1.0,1.0" />
</aapt:attr>
</objectAnimator>
- <objectAnimator android:propertyName="pathData" android:duration="333"
- android:startOffset="67"
- android:valueFrom="M-27.97 -59.3 C-27.97,-59.3 -28,-64.5 -27.97,-66.23 C-27.92,-68.37 -23.5,-90.63 -0.75,-90.57 C22.77,-90.51 27.75,-70.12 27.72,-69.02 C27.55,-63.63 27.97,-25.67 27.97,-25.67 "
- android:valueTo="M79.79 -48.55 C79.79,-48.55 79.75,-53.75 79.78,-55.48 C79.83,-57.62 79.08,-78.36 53.07,-78.83 C29.5,-79.25 25.2,-59.38 25.22,-58.27 C25.25,-56.25 24.97,-31.17 24.97,-31.17 "
- android:valueType="pathType">
+ <objectAnimator
+ android:duration="333"
+ android:propertyName="pathData"
+ android:startOffset="67"
+ android:valueFrom="M14.33 14.33 C14.33,14.33 14.29,6.17 14.29,6.17 C14.29,3.59 12.2,1.5 9.63,1.5 C7.05,1.5 4.96,3.59 4.96,6.17 C4.96,6.17 4.96,7.33 4.96,7.33 "
+ android:valueTo="M14.33 14.33 C14.33,14.33 14.32,9.42 14.32,9.42 C14.32,7.4 15.67,5.01 18.65,5 C21.76,4.99 23.07,7.37 23.05,9.47 C23.05,9.47 23.06,9.77 23.06,9.77 "
+ android:valueType="pathType">
<aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.542,0 0.026,1 1.0,1.0"/>
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.702,0 0.308,1 1.0,1.0" />
</aapt:attr>
</objectAnimator>
</set>
@@ -211,26 +246,37 @@
<target android:name="_R_G_L_0_G_N_4_T_1">
<aapt:attr name="android:animation">
<set android:ordering="together">
- <objectAnimator android:propertyName="translateY" android:duration="133"
- android:startOffset="0" android:valueFrom="3"
- android:valueTo="1.625" android:valueType="floatType">
+ <objectAnimator
+ android:duration="133"
+ android:propertyName="translateY"
+ android:startOffset="0"
+ android:valueFrom="24.993"
+ android:valueTo="22.493"
+ android:valueType="floatType">
<aapt:attr name="android:interpolator">
- <pathInterpolator
- android:pathData="M 0.0,0.0 c0.075,0.167 0.622,1 1.0,1.0"/>
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.378,0 0.622,1 1.0,1.0" />
</aapt:attr>
</objectAnimator>
- <objectAnimator android:propertyName="translateY" android:duration="133"
- android:startOffset="133" android:valueFrom="1.625"
- android:valueTo="3.699" android:valueType="floatType">
+ <objectAnimator
+ android:duration="133"
+ android:propertyName="translateY"
+ android:startOffset="133"
+ android:valueFrom="22.493"
+ android:valueTo="25.993"
+ android:valueType="floatType">
<aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.352,0 0.717,1 1.0,1.0"/>
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.41,0 0.616,1 1.0,1.0" />
</aapt:attr>
</objectAnimator>
- <objectAnimator android:propertyName="translateY" android:duration="100"
- android:startOffset="267" android:valueFrom="3.699"
- android:valueTo="3" android:valueType="floatType">
+ <objectAnimator
+ android:duration="100"
+ android:propertyName="translateY"
+ android:startOffset="267"
+ android:valueFrom="25.993"
+ android:valueTo="24.993"
+ android:valueType="floatType">
<aapt:attr name="android:interpolator">
- <pathInterpolator android:pathData="M 0.0,0.0 c0.356,0 0.527,1 1.0,1.0"/>
+ <pathInterpolator android:pathData="M 0.0,0.0 c0.427,0 0.508,1 1.0,1.0" />
</aapt:attr>
</objectAnimator>
</set>
@@ -239,9 +285,13 @@
<target android:name="time_group">
<aapt:attr name="android:animation">
<set android:ordering="together">
- <objectAnimator android:propertyName="translateX" android:duration="717"
- android:startOffset="0" android:valueFrom="0" android:valueTo="1"
- android:valueType="floatType"/>
+ <objectAnimator
+ android:duration="717"
+ android:propertyName="translateX"
+ android:startOffset="0"
+ android:valueFrom="0"
+ android:valueTo="1"
+ android:valueType="floatType" />
</set>
</aapt:attr>
</target>
diff --git a/core/res/res/drawable/ic_lock.xml b/core/res/res/drawable/ic_lock.xml
index fed0e0d71287..7582d5f82c1d 100644
--- a/core/res/res/drawable/ic_lock.xml
+++ b/core/res/res/drawable/ic_lock.xml
@@ -16,12 +16,12 @@ Copyright (C) 2019 The Android Open Source Project
<vector xmlns:android="http://schemas.android.com/apk/res/android"
android:width="32dp"
android:height="32dp"
- android:viewportWidth="32"
- android:viewportHeight="32">
+ android:viewportWidth="32.0"
+ android:viewportHeight="32.0">
<path
- android:fillColor="#000"
- android:pathData="M16,20m-2.7,0a2.7,2.7 0,1 1,5.4 0a2.7,2.7 0,1 1,-5.4 0"/>
+ android:fillColor="#FF000000"
+ android:pathData="M16,20m-2.5,0a2.5,2.5 0,1 1,5 0a2.5,2.5 0,1 1,-5 0"/>
<path
- android:fillColor="#000"
- android:pathData="M24,10.7h-2V7.3c0,-3.3 -2.7,-6 -6,-6s-6,2.7 -6,6v3.3H8c-1.5,0 -2.7,1.2 -2.7,2.7v13.3c0,1.5 1.2,2.7 2.7,2.7h16c1.5,0 2.7,-1.2 2.7,-2.7V13.3C26.7,11.9 25.5,10.7 24,10.7zM12.7,7.3C12.7,5.5 14.2,4 16,4s3.3,1.5 3.3,3.3v3.3h-6.7V7.3zM24,26.7H8V13.3h2h12h2V26.7z"/>
-</vector>
+ android:fillColor="#FF000000"
+ android:pathData="M24,11h-2.3V7.3c0,-3.1 -2.5,-5.7 -5.7,-5.7c-3.1,0 -5.7,2.5 -5.7,5.7V11H8c-1.3,0 -2.3,1 -2.3,2.3v13.3c0,1.3 1,2.3 2.3,2.3h16c1.3,0 2.3,-1 2.3,-2.3V13.3C26.3,12 25.3,11 24,11zM12.3,7.3c0,-2 1.6,-3.7 3.7,-3.7c2,0 3.7,1.6 3.7,3.7V11h-7.3V7.3zM24.3,26.7c0,0.2 -0.1,0.3 -0.3,0.3H8c-0.2,0 -0.3,-0.1 -0.3,-0.3V13.3C7.7,13.1 7.8,13 8,13h16c0.2,0 0.3,0.1 0.3,0.3V26.7z"/>
+</vector> \ No newline at end of file
diff --git a/core/res/res/drawable/ic_lock_open.xml b/core/res/res/drawable/ic_lock_open.xml
index 494fd6ae9a76..e0deb598b1b1 100644
--- a/core/res/res/drawable/ic_lock_open.xml
+++ b/core/res/res/drawable/ic_lock_open.xml
@@ -16,12 +16,12 @@ Copyright (C) 2019 The Android Open Source Project
<vector xmlns:android="http://schemas.android.com/apk/res/android"
android:width="32dp"
android:height="32dp"
- android:viewportWidth="32"
- android:viewportHeight="32">
+ android:viewportWidth="32.0"
+ android:viewportHeight="32.0">
<path
- android:fillColor="#000"
- android:pathData="M16,20m-2.67,0a2.67,2.67 0,1 1,5.34 0a2.67,2.67 0,1 1,-5.34 0"/>
+ android:fillColor="#FF000000"
+ android:pathData="M16,20m-2.5,0a2.5,2.5 0,1 1,5 0a2.5,2.5 0,1 1,-5 0"/>
<path
- android:fillColor="#000"
- android:pathData="M24.67,1.33a6,6 0,0 0,-6 6v3.34L8,10.67a2.67,2.67 0,0 0,-2.67 2.66L5.33,26.67A2.67,2.67 0,0 0,8 29.33L24,29.33a2.67,2.67 0,0 0,2.67 -2.66L26.67,13.33A2.67,2.67 0,0 0,24 10.67L21.33,10.67L21.33,7.33a3.34,3.34 0,0 1,6.67 0L28,8h2.67L30.67,7.33A6,6 0,0 0,24.67 1.33ZM24,13.33L24,26.67L8,26.67L8,13.33Z"/>
+ android:fillColor="#FF000000"
+ android:pathData="M25.3,1.7c-3.1,0 -5.7,2.5 -5.7,5.7V11H8c-1.3,0 -2.3,1 -2.3,2.3v13.3c0,1.3 1,2.3 2.3,2.3h16c1.3,0 2.3,-1 2.3,-2.3V13.3c0,-1.3 -1,-2.3 -2.3,-2.3h-2.3V7.3c0,-2 1.6,-3.7 3.7,-3.7c2,0 3.7,1.6 3.7,3.7V8h2V7.3C31,4.2 28.5,1.7 25.3,1.7zM24.3,13.3v13.3c0,0.2 -0.1,0.3 -0.3,0.3H8c-0.2,0 -0.3,-0.1 -0.3,-0.3V13.3C7.7,13.1 7.8,13 8,13h16C24.2,13 24.3,13.1 24.3,13.3z"/>
</vector> \ No newline at end of file
diff --git a/core/res/res/layout-car/car_preference.xml b/core/res/res/layout-car/car_preference.xml
index ae3d63bd2d6a..b138f4d7cf50 100644
--- a/core/res/res/layout-car/car_preference.xml
+++ b/core/res/res/layout-car/car_preference.xml
@@ -27,20 +27,20 @@
<com.android.internal.widget.PreferenceImageView
android:id="@id/icon"
- android:layout_width="@*android:dimen/car_primary_icon_size"
- android:layout_height="@*android:dimen/car_primary_icon_size"
+ android:layout_width="@dimen/car_preference_icon_size"
+ android:layout_height="@dimen/car_preference_icon_size"
android:layout_alignParentStart="true"
android:layout_centerVertical="true"
- android:layout_marginBottom="@*android:dimen/car_padding_2"
+ android:layout_marginBottom="@dimen/car_preference_row_vertical_margin"
android:layout_marginEnd="?android:attr/listPreferredItemPaddingEnd"
- android:layout_marginTop="@android:dimen/car_padding_2"/>
+ android:layout_marginTop="@dimen/car_preference_row_vertical_margin"/>
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_centerVertical="true"
- android:layout_marginBottom="@*android:dimen/car_padding_2"
- android:layout_marginTop="@*android:dimen/car_padding_2"
+ android:layout_marginBottom="@dimen/car_preference_row_vertical_margin"
+ android:layout_marginTop="@dimen/car_preference_row_vertical_margin"
android:layout_toEndOf="@id/icon"
android:layout_toStartOf="@id/widget_frame"
android:orientation="vertical">
diff --git a/core/res/res/layout-car/car_preference_category.xml b/core/res/res/layout-car/car_preference_category.xml
index d1f73421e185..b674487cffa7 100644
--- a/core/res/res/layout-car/car_preference_category.xml
+++ b/core/res/res/layout-car/car_preference_category.xml
@@ -22,25 +22,25 @@
android:background="?android:attr/selectableItemBackground"
android:focusable="true"
android:gravity="center_vertical"
- android:minHeight="@*android:dimen/car_card_header_height"
+ android:minHeight="@dimen/car_card_header_height"
android:orientation="horizontal"
android:paddingEnd="?android:attr/listPreferredItemPaddingEnd"
android:paddingStart="?android:attr/listPreferredItemPaddingStart">
<com.android.internal.widget.PreferenceImageView
android:id="@id/icon"
- android:layout_width="@*android:dimen/car_primary_icon_size"
- android:layout_height="@*android:dimen/car_primary_icon_size"
+ android:layout_width="@dimen/car_preference_category_icon_size"
+ android:layout_height="@dimen/car_preference_category_icon_size"
android:layout_gravity="center_vertical"
- android:layout_marginBottom="@dimen/car_padding_2"
+ android:layout_marginBottom="@dimen/car_preference_row_vertical_margin"
android:layout_marginEnd="?android:attr/listPreferredItemPaddingEnd"
- android:layout_marginTop="@*android:dimen/car_padding_2"/>
+ android:layout_marginTop="@dimen/car_preference_row_vertical_margin"/>
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
- android:layout_marginBottom="@*android:dimen/car_padding_2"
- android:layout_marginTop="@*android:dimen/car_padding_2"
+ android:layout_marginBottom="@dimen/car_preference_row_vertical_margin"
+ android:layout_marginTop="@dimen/car_preference_row_vertical_margin"
android:orientation="vertical">
<TextView
diff --git a/core/res/res/values-af/strings.xml b/core/res/res/values-af/strings.xml
index f2028b9d0d91..221215a729a2 100644
--- a/core/res/res/values-af/strings.xml
+++ b/core/res/res/values-af/strings.xml
@@ -571,13 +571,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"Skryf jou gesig asseblief weer in."</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"Kan nie meer gesig herken nie. Probeer weer."</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"Te eenders. Verander asseblief jou pose."</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"Draai jou kop \'n bietjie minder."</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"Draai jou kop \'n bietjie minder."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"Hou asseblief jou kop regop."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"Hou die spasie tussen jou kop en foon oop."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"Maak asseblief die kamera skoon."</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"Kan nie gesig verifieer nie. Hardeware nie beskikbaar nie."</string>
diff --git a/core/res/res/values-am/strings.xml b/core/res/res/values-am/strings.xml
index 7c59d4a88f14..dbb115ddb485 100644
--- a/core/res/res/values-am/strings.xml
+++ b/core/res/res/values-am/strings.xml
@@ -571,13 +571,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"እባክዎ ፊትዎን እንደገና ያስመዝግቡ"</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"ከእንግዲህ ፊትን ለይቶ ማወቅ አይችልም። እንደገና ይሞክሩ።"</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"በጣም ይመሳሰላል፣ እባክዎ የእርስዎን ፎቶ አነሳስ ይለውጡ"</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"ጭንቅላትዎን ትንሽ ብቻ ያዙሩት።"</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"ጭንቅላትዎን ትንሽ ብቻ ያዙሩት።"</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"እባክዎ ጭንቅላትዎን ቀጥ ያድርጉ።"</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"በእርስዎ ጭንቅላት እና በስልኩ መካከል ያለውን ክፍተት ያጽዱ።"</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"እባክዎ ካሜራውን ያፅዱት።"</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"መልክን ማረጋገጥ አይቻልም። ሃርድዌር የለም።"</string>
diff --git a/core/res/res/values-ar/strings.xml b/core/res/res/values-ar/strings.xml
index aab5224f2757..7fbf223eb9e7 100644
--- a/core/res/res/values-ar/strings.xml
+++ b/core/res/res/values-ar/strings.xml
@@ -583,13 +583,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"يُرجى إعادة تسجيل وجهك."</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"لم يعُد يمكن التعرّف على الوجه. حاول مرة أخرى."</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"الوجه مشابه جدًا، يُرجى تغيير وضعيتك."</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"اخفض وجهك قليلاً."</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"اخفض وجهك قليلاً."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"يُرجى تثبيت الرأس في وضع عمودي."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"يُرجى إخلاء المنطقة بين رأسك والهاتف."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"يُرجى تنظيف الكاميرا."</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"يتعذّر التحقُّق من الوجه. الجهاز غير مُتاح."</string>
diff --git a/core/res/res/values-as/strings.xml b/core/res/res/values-as/strings.xml
index d511f805f664..cf3745f66710 100644
--- a/core/res/res/values-as/strings.xml
+++ b/core/res/res/values-as/strings.xml
@@ -571,13 +571,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"আপোনাৰ মুখমণ্ডল পুনৰ পঞ্জীয়ন কৰক।"</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"মুখমণ্ডল আৰু চিনাক্ত কৰিব নোৱাৰি। আকৌ চেষ্টা কৰক।"</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"একে ধৰণৰ হৈছে, অনুগ্ৰহ কৰি আপোনাৰ প’জটো সলনি কৰক।"</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"আপোনাৰ মূৰটো সামান্য কমকৈ ঘূৰাওক।"</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"আপোনাৰ মূৰটো সামান্য কমকৈ ঘূৰাওক।"</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"অনুগ্ৰহ কৰি আপোনাৰ মূৰটো উলম্বভাৱে চিধা কৰক।"</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"আপোনাৰ মূৰ আৰু ফ’নৰ মাজত যদি কিবা আছে আঁতৰাওক।"</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"কেমেৰা পৰিস্কাৰ কৰক।"</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"মুখমণ্ডল সত্যাপন কৰিব পৰা নগ’ল। হাৰ্ডৱেৰ নাই।"</string>
diff --git a/core/res/res/values-az/strings.xml b/core/res/res/values-az/strings.xml
index 3e666e0e6b4f..200a2d033231 100644
--- a/core/res/res/values-az/strings.xml
+++ b/core/res/res/values-az/strings.xml
@@ -571,13 +571,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"Üzünüzü yenidən qeydiyyatdan keçirin."</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"Üzü artıq tanımaq olmur. Yenidən cəhd edin."</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"Digəri ilə oxşardır, pozanızı dəyişin."</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"Başınızı bir az döndərin."</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"Başınızı bir az döndərin."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"Başınızı şaquli istiqamətdə qaldırın."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"Başınız və telefon arasında məsafə olmamalıdır."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"Kameranı təmizləyin."</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"Üz doğrulanmadı. Avadanlıq əlçatan deyil."</string>
diff --git a/core/res/res/values-b+sr+Latn/strings.xml b/core/res/res/values-b+sr+Latn/strings.xml
index 936ab3cd6de2..79db13cfca07 100644
--- a/core/res/res/values-b+sr+Latn/strings.xml
+++ b/core/res/res/values-b+sr+Latn/strings.xml
@@ -574,13 +574,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"Ponovo registrujte lice."</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"Više ne može da se prepozna lice. Probajte ponovo."</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"Previše je slično, promenite pozu."</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"Malo manje pomerite glavu."</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"Malo manje pomerite glavu."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"Ispravite glavu."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"Oslobodite prostor između glave i telefona."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"Očistite kameru."</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"Provera lica nije uspela. Hardver nije dostupan."</string>
diff --git a/core/res/res/values-be/strings.xml b/core/res/res/values-be/strings.xml
index a6548208c861..e3f5310a56d3 100644
--- a/core/res/res/values-be/strings.xml
+++ b/core/res/res/values-be/strings.xml
@@ -577,13 +577,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"Паўтарыце рэгістрацыю твару."</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"Не ўдаецца распазнаць твар. Паўтарыце спробу."</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"Не бачна розніцы. Памяняйце позу."</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"Вы занадта моцна павярнулі галаву."</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"Галава не ў цэнтры."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"Выраўнуйце галаву."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"Прыбярыце ўсё лішняе паміж тварам і тэлефонам."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"Пачысціце камеру."</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"Твар не спраўджаны. Абсталяванне недаступнае."</string>
diff --git a/core/res/res/values-bg/strings.xml b/core/res/res/values-bg/strings.xml
index 0f872f84b5aa..31d9e0534f97 100644
--- a/core/res/res/values-bg/strings.xml
+++ b/core/res/res/values-bg/strings.xml
@@ -571,13 +571,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"Моля, регистрирайте лицето си отново."</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"Лицето не бе разпознато. Опитайте отново."</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"Позата ви е сходна с предишна. Моля, променете я."</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"Не завъртайте главата си толкова много."</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"Не завъртайте главата си толкова много."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"Моля, изправете главата си."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"Между лицето ви и телефона не трябва да има нищо."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"Моля, почистете камерата."</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"Лицето не може да се потвърди. Хардуерът не е налице."</string>
diff --git a/core/res/res/values-bn/strings.xml b/core/res/res/values-bn/strings.xml
index 39a1603cb8ee..dee997fbe6ea 100644
--- a/core/res/res/values-bn/strings.xml
+++ b/core/res/res/values-bn/strings.xml
@@ -571,13 +571,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"আপনার মুখের ছবি আবার নথিভুক্ত করুন।"</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"আর মুখ চিনতে পারবেন না। আবার চেষ্টা করুন।"</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"একই ধরনের দেখতে, একটু অন্যদিকে ঘুরে দাঁড়ান।"</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"আপনার মাথাটি নিচের দিকে সামান্য নামান।"</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"আপনার মাথাটি নিচের দিকে সামান্য নামান।"</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"মাথা সোজা করে রাখুন।"</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"আপনার মুখের উপর কোনও আবরণ থাকলে সেটি সরিয়ে দিন।"</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"ক্যামেরাটি পরিষ্কার করুন।"</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"ফেস যাচাই করা যায়নি। হার্ডওয়্যার উপলভ্য নেই।"</string>
@@ -1122,7 +1123,7 @@
<string name="dialog_alert_title" msgid="2049658708609043103">"খেয়াল করুন"</string>
<string name="loading" msgid="7933681260296021180">"লোড হচ্ছে..."</string>
<string name="capital_on" msgid="1544682755514494298">"চালু"</string>
- <string name="capital_off" msgid="6815870386972805832">"বন্ধ করুন"</string>
+ <string name="capital_off" msgid="6815870386972805832">"বন্ধ আছে"</string>
<string name="whichApplication" msgid="4533185947064773386">"এটি ব্যবহার করে ক্রিয়াকলাপ সম্পূর্ণ করুন"</string>
<string name="whichApplicationNamed" msgid="8260158865936942783">"%1$s ব্যবহার করে ক্রিয়াকলাপ সম্পূর্ণ করুন"</string>
<string name="whichApplicationLabel" msgid="7425855495383818784">"ক্রিয়াকলাপ সম্পূর্ণ করুন"</string>
@@ -1598,7 +1599,7 @@
<string name="wireless_display_route_description" msgid="9070346425023979651">"ওয়্যারলেস প্রদর্শন"</string>
<string name="media_route_button_content_description" msgid="591703006349356016">"কাস্ট করুন"</string>
<string name="media_route_chooser_title" msgid="1751618554539087622">"ডিভাইসে সংযোগ করুন"</string>
- <string name="media_route_chooser_title_for_remote_display" msgid="3395541745872017583">"ডিভাইসে স্ক্রীণ কাস্ট করুন"</string>
+ <string name="media_route_chooser_title_for_remote_display" msgid="3395541745872017583">"ডিভাইসে স্ক্রিন কাস্ট করুন"</string>
<string name="media_route_chooser_searching" msgid="4776236202610828706">"ডিভাইসগুলি সার্চ করা হচ্ছে…"</string>
<string name="media_route_chooser_extended_settings" msgid="87015534236701604">"সেটিংস"</string>
<string name="media_route_controller_disconnect" msgid="8966120286374158649">"সংযোগ বিচ্ছিন্ন করুন"</string>
@@ -1842,7 +1843,7 @@
<string name="zen_mode_until" msgid="7336308492289875088">"<xliff:g id="FORMATTEDTIME">%1$s</xliff:g> পর্যন্ত"</string>
<string name="zen_mode_alarm" msgid="9128205721301330797">"<xliff:g id="FORMATTEDTIME">%1$s</xliff:g> পর্যন্ত (পরবর্তী অ্যালার্ম)"</string>
<string name="zen_mode_forever" msgid="931849471004038757">"যতক্ষণ না আপনি বন্ধ করছেন"</string>
- <string name="zen_mode_forever_dnd" msgid="3792132696572189081">"যতক্ষণ না পর্যন্ত আপনি বিরক্ত করবেন না বন্ধ করছেন"</string>
+ <string name="zen_mode_forever_dnd" msgid="3792132696572189081">"যতক্ষণ পর্যন্ত না আপনি বিরক্ত করবেন না বন্ধ করছেন"</string>
<string name="zen_mode_rule_name_combination" msgid="191109939968076477">"<xliff:g id="FIRST">%1$s</xliff:g> / <xliff:g id="REST">%2$s</xliff:g>"</string>
<string name="toolbar_collapse_description" msgid="2821479483960330739">"সঙ্কুচিত করুন"</string>
<string name="zen_mode_feature_name" msgid="5254089399895895004">"বিরক্ত করবেন না"</string>
diff --git a/core/res/res/values-bs/strings.xml b/core/res/res/values-bs/strings.xml
index dcd391bd5733..ac541a6bc327 100644
--- a/core/res/res/values-bs/strings.xml
+++ b/core/res/res/values-bs/strings.xml
@@ -574,13 +574,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"Ponovo registrirajte lice."</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"Nije više moguće prepoznati lice. Pokušajte opet."</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"Previše slično, promijenite položaj."</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"Malo manje zakrenite glavu."</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"Malo manje zakrenite glavu."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"Poravnajte položaj glave vertikalno."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"Sklonite prepreke između vaše glave i telefona."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"Očistite kameru."</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"Nije moguće potvrditi lice. Hardver nije dostupan."</string>
diff --git a/core/res/res/values-ca/strings.xml b/core/res/res/values-ca/strings.xml
index ad98ff3012ff..31930894bf0c 100644
--- a/core/res/res/values-ca/strings.xml
+++ b/core/res/res/values-ca/strings.xml
@@ -571,13 +571,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"Torna a registrar la teva cara."</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"Ja no es reconeix la teva cara. Torna-ho a provar."</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"És massa semblant; canvia de postura."</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"Inclina el cap una mica menys."</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"Inclina el cap una mica menys."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"Mantén el cap recte, sense inclinar-lo."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"Procura que no hi hagi res entre tu i el telèfon."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"Neteja la càmera."</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"No es pot verificar la cara. Maquinari no disponible."</string>
@@ -817,10 +818,10 @@
<string name="lockscreen_password_wrong" msgid="5737815393253165301">"Torna-ho a provar"</string>
<string name="lockscreen_storage_locked" msgid="9167551160010625200">"Desbl. per accedir a totes les funcions i dades"</string>
<string name="faceunlock_multiple_failures" msgid="754137583022792429">"S\'ha superat el nombre màxim d\'intents de desbloqueig facial"</string>
- <string name="lockscreen_missing_sim_message_short" msgid="5099439277819215399">"No hi ha cap targeta SIM."</string>
- <string name="lockscreen_missing_sim_message" product="tablet" msgid="151659196095791474">"No hi ha cap targeta SIM a la tauleta."</string>
- <string name="lockscreen_missing_sim_message" product="tv" msgid="1943633865476989599">"No hi ha cap targeta SIM al televisor."</string>
- <string name="lockscreen_missing_sim_message" product="default" msgid="2186920585695169078">"No hi ha cap targeta SIM al telèfon."</string>
+ <string name="lockscreen_missing_sim_message_short" msgid="5099439277819215399">"No hi ha cap SIM"</string>
+ <string name="lockscreen_missing_sim_message" product="tablet" msgid="151659196095791474">"No hi ha cap SIM a la tauleta."</string>
+ <string name="lockscreen_missing_sim_message" product="tv" msgid="1943633865476989599">"No hi ha cap SIM al televisor."</string>
+ <string name="lockscreen_missing_sim_message" product="default" msgid="2186920585695169078">"No hi ha cap SIM al telèfon."</string>
<string name="lockscreen_missing_sim_instructions" msgid="5372787138023272615">"Insereix una targeta SIM."</string>
<string name="lockscreen_missing_sim_instructions_long" msgid="3526573099019319472">"Falta la targeta SIM o no es pot llegir. Insereix-ne una."</string>
<string name="lockscreen_permanent_disabled_sim_message_short" msgid="5096149665138916184">"Targeta SIM no utilitzable."</string>
@@ -1597,7 +1598,7 @@
<string name="wireless_display_route_description" msgid="9070346425023979651">"Pantalla sense fil"</string>
<string name="media_route_button_content_description" msgid="591703006349356016">"Emet"</string>
<string name="media_route_chooser_title" msgid="1751618554539087622">"Connexió al dispositiu"</string>
- <string name="media_route_chooser_title_for_remote_display" msgid="3395541745872017583">"Emissió de pantalla al dispositiu"</string>
+ <string name="media_route_chooser_title_for_remote_display" msgid="3395541745872017583">"Emet pantalla al dispositiu"</string>
<string name="media_route_chooser_searching" msgid="4776236202610828706">"S\'estan cercant dispositius…"</string>
<string name="media_route_chooser_extended_settings" msgid="87015534236701604">"Configuració"</string>
<string name="media_route_controller_disconnect" msgid="8966120286374158649">"Desconnecta"</string>
diff --git a/core/res/res/values-cs/strings.xml b/core/res/res/values-cs/strings.xml
index b328f5733553..6d76c5bc58ef 100644
--- a/core/res/res/values-cs/strings.xml
+++ b/core/res/res/values-cs/strings.xml
@@ -577,13 +577,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"Zaznamenejte obličej znovu."</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"Obličej už nelze rozpoznat. Zkuste to znovu."</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"Příliš podobné, změňte výraz."</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"Natočte hlavu o něco méně."</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"Natočte hlavu o něco méně."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"Narovnejte hlavu."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"Mezi vaší hlavou a telefonem nesmí nic překážet."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"Očistěte fotoaparát."</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"Obličej nelze ověřit. Hardware není dostupný."</string>
@@ -987,7 +988,7 @@
</plurals>
<string name="last_month" msgid="3959346739979055432">"Poslední měsíc"</string>
<string name="older" msgid="5211975022815554840">"Starší"</string>
- <string name="preposition_for_date" msgid="9093949757757445117">"dne <xliff:g id="DATE">%s</xliff:g>"</string>
+ <string name="preposition_for_date" msgid="9093949757757445117">"<xliff:g id="DATE">%s</xliff:g>"</string>
<string name="preposition_for_time" msgid="5506831244263083793">"v <xliff:g id="TIME">%s</xliff:g>"</string>
<string name="preposition_for_year" msgid="5040395640711867177">"roku <xliff:g id="YEAR">%s</xliff:g>"</string>
<string name="day" msgid="8144195776058119424">"den"</string>
diff --git a/core/res/res/values-da/strings.xml b/core/res/res/values-da/strings.xml
index 5eb51ee95235..a6b7af842a57 100644
--- a/core/res/res/values-da/strings.xml
+++ b/core/res/res/values-da/strings.xml
@@ -571,13 +571,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"Registrer dit ansigt igen."</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"Ansigtet kan ikke længere genkendes. Prøv igen."</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"Det minder for meget om et andet. Skift stilling."</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"Sørg for, at hovedet ikke er drejet for meget."</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"Sørg for, at hovedet ikke er bøjet for meget."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"Hold hovedet helt lodret."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"Sørg for, at der ikke er noget foran dit ansigt."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"Rengør kameraet."</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"Ansigt ikke bekræftet. Hardware ikke tilgængelig."</string>
@@ -1597,7 +1598,7 @@
<string name="wireless_display_route_description" msgid="9070346425023979651">"Trådløs skærm"</string>
<string name="media_route_button_content_description" msgid="591703006349356016">"Cast"</string>
<string name="media_route_chooser_title" msgid="1751618554539087622">"Opret forbindelse til enheden"</string>
- <string name="media_route_chooser_title_for_remote_display" msgid="3395541745872017583">"Send skærm til enhed"</string>
+ <string name="media_route_chooser_title_for_remote_display" msgid="3395541745872017583">"Cast skærm til enhed"</string>
<string name="media_route_chooser_searching" msgid="4776236202610828706">"Søger efter enheder…"</string>
<string name="media_route_chooser_extended_settings" msgid="87015534236701604">"Indstillinger"</string>
<string name="media_route_controller_disconnect" msgid="8966120286374158649">"Afbryd forbindelsen"</string>
diff --git a/core/res/res/values-de/strings.xml b/core/res/res/values-de/strings.xml
index b8fad3a3fe34..ed0f3b5e1ce8 100644
--- a/core/res/res/values-de/strings.xml
+++ b/core/res/res/values-de/strings.xml
@@ -571,13 +571,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"Bitte registriere dein Gesicht noch einmal."</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"Gesicht wird nicht mehr erkannt. Erneut versuchen."</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"Zu ähnlich. Bitte dreh deinen Kopf etwas."</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"Dreh den Kopf etwas weniger zur Seite."</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"Neig den Kopf etwas weniger stark."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"Bitte halte deinen Kopf gerade."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"Halte den Platz zwischen Kopf und Smartphone frei."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"Bitte reinige die Kamera."</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"Gesicht nicht erkannt. Hardware nicht verfügbar."</string>
diff --git a/core/res/res/values-el/strings.xml b/core/res/res/values-el/strings.xml
index 374866b98ca7..c06e1c59e3a8 100644
--- a/core/res/res/values-el/strings.xml
+++ b/core/res/res/values-el/strings.xml
@@ -571,13 +571,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"Καταχωρίστε ξανά το πρόσωπό σας."</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"Αδύνατη η αναγνώριση του προσώπου. Επανάληψη."</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"Πολύ παρόμοιο, αλλάξτε την πόζα σας."</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"Στρέψτε λιγότερο το κεφάλι σας."</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"Στρέψτε λιγότερο το κεφάλι σας."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"Ευθυγραμμίστε το κεφάλι σας στον κατακόρυφο άξονα."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"Αδειάστε τον χώρο ανάμεσα σε εσάς και το τηλέφωνο."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"Καθαρίστε την κάμερα."</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"Αδύν. επαλήθ. προσώπου. Μη διαθέσιμος εξοπλισμός."</string>
diff --git a/core/res/res/values-en-rAU/strings.xml b/core/res/res/values-en-rAU/strings.xml
index 39538a59c245..e1e618c868b1 100644
--- a/core/res/res/values-en-rAU/strings.xml
+++ b/core/res/res/values-en-rAU/strings.xml
@@ -272,7 +272,7 @@
<string name="foreground_service_tap_for_details" msgid="372046743534354644">"Tap for details on battery and data usage"</string>
<string name="foreground_service_multiple_separator" msgid="4021901567939866542">"<xliff:g id="LEFT_SIDE">%1$s</xliff:g>, <xliff:g id="RIGHT_SIDE">%2$s</xliff:g>"</string>
<string name="safeMode" msgid="2788228061547930246">"Safe mode"</string>
- <string name="android_system_label" msgid="6577375335728551336">"Android system"</string>
+ <string name="android_system_label" msgid="6577375335728551336">"Android System"</string>
<string name="user_owner_label" msgid="8836124313744349203">"Switch to personal profile"</string>
<string name="managed_profile_label" msgid="8947929265267690522">"Switch to work profile"</string>
<string name="permgrouplab_contacts" msgid="3657758145679177612">"Contacts"</string>
@@ -303,7 +303,7 @@
<string name="permgroupdesc_camera" msgid="3250611594678347720">"take pictures and record video"</string>
<string name="permgrouprequest_camera" msgid="1299833592069671756">"Allow &lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; to take pictures and record video?"</string>
<string name="permgrouplab_calllog" msgid="8798646184930388160">"Call logs"</string>
- <string name="permgroupdesc_calllog" msgid="3006237336748283775">"read and write phone call log"</string>
+ <string name="permgroupdesc_calllog" msgid="3006237336748283775">"read and write phone call logs"</string>
<string name="permgrouprequest_calllog" msgid="8487355309583773267">"Allow &lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; to access your phone call logs?"</string>
<string name="permgrouplab_phone" msgid="5229115638567440675">"Telephone"</string>
<string name="permgroupdesc_phone" msgid="6234224354060641055">"make and manage phone calls"</string>
@@ -571,13 +571,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"Please re-enroll your face."</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"No longer able to recognise face. Try again."</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"Too similar, please change your pose."</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"Turn your head a little less."</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"Turn your head a little less."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"Please straighten your head vertically."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"Clear the space between your head and the phone."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"Please clean the camera."</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"Can’t verify face. Hardware not available."</string>
diff --git a/core/res/res/values-en-rCA/strings.xml b/core/res/res/values-en-rCA/strings.xml
index 09ccce62bf55..4585a256184c 100644
--- a/core/res/res/values-en-rCA/strings.xml
+++ b/core/res/res/values-en-rCA/strings.xml
@@ -272,7 +272,7 @@
<string name="foreground_service_tap_for_details" msgid="372046743534354644">"Tap for details on battery and data usage"</string>
<string name="foreground_service_multiple_separator" msgid="4021901567939866542">"<xliff:g id="LEFT_SIDE">%1$s</xliff:g>, <xliff:g id="RIGHT_SIDE">%2$s</xliff:g>"</string>
<string name="safeMode" msgid="2788228061547930246">"Safe mode"</string>
- <string name="android_system_label" msgid="6577375335728551336">"Android system"</string>
+ <string name="android_system_label" msgid="6577375335728551336">"Android System"</string>
<string name="user_owner_label" msgid="8836124313744349203">"Switch to personal profile"</string>
<string name="managed_profile_label" msgid="8947929265267690522">"Switch to work profile"</string>
<string name="permgrouplab_contacts" msgid="3657758145679177612">"Contacts"</string>
@@ -303,7 +303,7 @@
<string name="permgroupdesc_camera" msgid="3250611594678347720">"take pictures and record video"</string>
<string name="permgrouprequest_camera" msgid="1299833592069671756">"Allow &lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; to take pictures and record video?"</string>
<string name="permgrouplab_calllog" msgid="8798646184930388160">"Call logs"</string>
- <string name="permgroupdesc_calllog" msgid="3006237336748283775">"read and write phone call log"</string>
+ <string name="permgroupdesc_calllog" msgid="3006237336748283775">"read and write phone call logs"</string>
<string name="permgrouprequest_calllog" msgid="8487355309583773267">"Allow &lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; to access your phone call logs?"</string>
<string name="permgrouplab_phone" msgid="5229115638567440675">"Telephone"</string>
<string name="permgroupdesc_phone" msgid="6234224354060641055">"make and manage phone calls"</string>
@@ -571,13 +571,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"Please re-enroll your face."</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"No longer able to recognise face. Try again."</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"Too similar, please change your pose."</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"Turn your head a little less."</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"Turn your head a little less."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"Please straighten your head vertically."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"Clear the space between your head and the phone."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"Please clean the camera."</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"Can’t verify face. Hardware not available."</string>
diff --git a/core/res/res/values-en-rGB/strings.xml b/core/res/res/values-en-rGB/strings.xml
index 39538a59c245..e1e618c868b1 100644
--- a/core/res/res/values-en-rGB/strings.xml
+++ b/core/res/res/values-en-rGB/strings.xml
@@ -272,7 +272,7 @@
<string name="foreground_service_tap_for_details" msgid="372046743534354644">"Tap for details on battery and data usage"</string>
<string name="foreground_service_multiple_separator" msgid="4021901567939866542">"<xliff:g id="LEFT_SIDE">%1$s</xliff:g>, <xliff:g id="RIGHT_SIDE">%2$s</xliff:g>"</string>
<string name="safeMode" msgid="2788228061547930246">"Safe mode"</string>
- <string name="android_system_label" msgid="6577375335728551336">"Android system"</string>
+ <string name="android_system_label" msgid="6577375335728551336">"Android System"</string>
<string name="user_owner_label" msgid="8836124313744349203">"Switch to personal profile"</string>
<string name="managed_profile_label" msgid="8947929265267690522">"Switch to work profile"</string>
<string name="permgrouplab_contacts" msgid="3657758145679177612">"Contacts"</string>
@@ -303,7 +303,7 @@
<string name="permgroupdesc_camera" msgid="3250611594678347720">"take pictures and record video"</string>
<string name="permgrouprequest_camera" msgid="1299833592069671756">"Allow &lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; to take pictures and record video?"</string>
<string name="permgrouplab_calllog" msgid="8798646184930388160">"Call logs"</string>
- <string name="permgroupdesc_calllog" msgid="3006237336748283775">"read and write phone call log"</string>
+ <string name="permgroupdesc_calllog" msgid="3006237336748283775">"read and write phone call logs"</string>
<string name="permgrouprequest_calllog" msgid="8487355309583773267">"Allow &lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; to access your phone call logs?"</string>
<string name="permgrouplab_phone" msgid="5229115638567440675">"Telephone"</string>
<string name="permgroupdesc_phone" msgid="6234224354060641055">"make and manage phone calls"</string>
@@ -571,13 +571,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"Please re-enroll your face."</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"No longer able to recognise face. Try again."</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"Too similar, please change your pose."</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"Turn your head a little less."</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"Turn your head a little less."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"Please straighten your head vertically."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"Clear the space between your head and the phone."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"Please clean the camera."</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"Can’t verify face. Hardware not available."</string>
diff --git a/core/res/res/values-en-rIN/strings.xml b/core/res/res/values-en-rIN/strings.xml
index 39538a59c245..e1e618c868b1 100644
--- a/core/res/res/values-en-rIN/strings.xml
+++ b/core/res/res/values-en-rIN/strings.xml
@@ -272,7 +272,7 @@
<string name="foreground_service_tap_for_details" msgid="372046743534354644">"Tap for details on battery and data usage"</string>
<string name="foreground_service_multiple_separator" msgid="4021901567939866542">"<xliff:g id="LEFT_SIDE">%1$s</xliff:g>, <xliff:g id="RIGHT_SIDE">%2$s</xliff:g>"</string>
<string name="safeMode" msgid="2788228061547930246">"Safe mode"</string>
- <string name="android_system_label" msgid="6577375335728551336">"Android system"</string>
+ <string name="android_system_label" msgid="6577375335728551336">"Android System"</string>
<string name="user_owner_label" msgid="8836124313744349203">"Switch to personal profile"</string>
<string name="managed_profile_label" msgid="8947929265267690522">"Switch to work profile"</string>
<string name="permgrouplab_contacts" msgid="3657758145679177612">"Contacts"</string>
@@ -303,7 +303,7 @@
<string name="permgroupdesc_camera" msgid="3250611594678347720">"take pictures and record video"</string>
<string name="permgrouprequest_camera" msgid="1299833592069671756">"Allow &lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; to take pictures and record video?"</string>
<string name="permgrouplab_calllog" msgid="8798646184930388160">"Call logs"</string>
- <string name="permgroupdesc_calllog" msgid="3006237336748283775">"read and write phone call log"</string>
+ <string name="permgroupdesc_calllog" msgid="3006237336748283775">"read and write phone call logs"</string>
<string name="permgrouprequest_calllog" msgid="8487355309583773267">"Allow &lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; to access your phone call logs?"</string>
<string name="permgrouplab_phone" msgid="5229115638567440675">"Telephone"</string>
<string name="permgroupdesc_phone" msgid="6234224354060641055">"make and manage phone calls"</string>
@@ -571,13 +571,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"Please re-enroll your face."</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"No longer able to recognise face. Try again."</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"Too similar, please change your pose."</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"Turn your head a little less."</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"Turn your head a little less."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"Please straighten your head vertically."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"Clear the space between your head and the phone."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"Please clean the camera."</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"Can’t verify face. Hardware not available."</string>
diff --git a/core/res/res/values-en-rXC/strings.xml b/core/res/res/values-en-rXC/strings.xml
index d760b193e1f2..9fffe2f29a4d 100644
--- a/core/res/res/values-en-rXC/strings.xml
+++ b/core/res/res/values-en-rXC/strings.xml
@@ -571,13 +571,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"‎‏‎‎‎‎‎‏‎‏‏‏‎‎‎‎‎‎‏‎‎‏‎‎‎‎‏‏‏‏‏‏‏‏‏‏‎‎‎‎‎‎‎‏‏‎‏‎‏‎‏‎‎‏‎‎‎‏‎‎‎‏‏‎‎‎‏‎‏‎‎‏‏‎‎‎‎‏‎‏‏‏‎‏‎‎‎‏‎‎‎‏‎‎‏‏‎Please re-enroll your face.‎‏‎‎‏‎"</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"‎‏‎‎‎‎‎‏‎‏‏‏‎‎‎‎‎‎‏‎‎‏‎‎‎‎‏‏‏‏‏‏‏‏‏‎‏‎‏‎‎‏‎‏‏‎‏‏‏‏‏‏‎‎‎‎‏‎‏‎‎‎‏‎‎‎‏‎‎‏‏‎‏‎‎‏‎‏‏‎‎‏‏‎‎‏‎‏‎‏‏‏‏‏‏‎‎No longer able to recognize face. Try again.‎‏‎‎‏‎"</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"‎‏‎‎‎‎‎‏‎‏‏‏‎‎‎‎‎‎‏‎‎‏‎‎‎‎‏‏‏‏‏‎‏‏‎‏‎‎‏‏‏‏‎‎‎‎‎‏‎‎‎‎‎‎‏‎‎‎‏‏‏‏‎‎‎‏‎‎‏‎‏‎‏‏‎‏‏‏‏‎‏‏‎‏‎‎‏‏‏‏‏‏‎‎‎Too similar, please change your pose.‎‏‎‎‏‎"</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"‎‏‎‎‎‎‎‏‎‏‏‏‎‎‎‎‎‎‏‎‎‏‎‎‎‎‏‏‏‏‏‏‎‏‏‏‏‏‏‏‎‎‏‎‏‎‏‎‎‏‏‎‏‏‏‏‎‎‏‏‏‎‎‏‏‏‎‏‏‏‎‏‎‏‎‎‎‎‎‏‏‎‎‏‎‎‎‏‏‏‏‎‎‏‎‎Turn your head a little less.‎‏‎‎‏‎"</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"‎‏‎‎‎‎‎‏‎‏‏‏‎‎‎‎‎‎‏‎‎‏‎‎‎‎‏‏‏‏‏‏‎‏‏‎‏‏‏‏‏‎‎‏‎‎‏‏‎‏‏‏‏‏‏‎‎‎‏‏‎‏‎‏‎‎‎‎‏‎‎‎‎‏‎‏‏‎‏‎‏‎‏‎‏‎‎‎‏‎‏‎‏‎‎‎Turn your head a little less.‎‏‎‎‏‎"</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"‎‏‎‎‎‎‎‏‎‏‏‏‎‎‎‎‎‎‏‎‎‏‎‎‎‎‏‏‏‏‏‎‏‏‎‏‎‎‎‎‎‎‏‏‎‏‎‎‎‏‎‎‎‎‏‎‎‎‏‎‎‏‎‏‏‎‎‏‎‎‏‏‏‏‎‎‎‏‎‏‎‏‎‏‎‎‎‏‏‏‏‎‏‏‎Please straighten your head vertically.‎‏‎‎‏‎"</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"‎‏‎‎‎‎‎‏‎‏‏‏‎‎‎‎‎‎‏‎‎‏‎‎‎‎‏‏‏‏‏‏‏‏‎‎‏‏‏‏‏‏‎‎‎‎‏‏‎‏‎‎‏‎‏‏‏‏‏‎‏‏‎‏‎‎‏‏‎‏‏‎‎‏‏‏‎‎‏‏‎‏‎‏‎‎‏‎‎‎‏‎‏‎‎‏‎Clear the space between your head and the phone.‎‏‎‎‏‎"</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"‎‏‎‎‎‎‎‏‎‏‏‏‎‎‎‎‎‎‏‎‎‏‎‎‎‎‏‏‏‏‎‏‏‏‎‏‎‎‎‎‏‏‏‎‏‏‏‏‎‎‎‏‎‎‏‏‏‏‏‎‎‎‎‎‏‎‏‎‏‎‎‎‏‏‎‏‎‏‎‏‏‎‏‏‎‎‏‎‎‏‎‎‎Please clean the camera.‎‏‎‎‏‎"</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"‎‏‎‎‎‎‎‏‎‏‏‏‎‎‎‎‎‎‏‎‎‏‎‎‎‎‏‏‏‏‎‏‏‏‎‏‏‎‎‎‎‎‏‎‎‎‎‎‎‎‏‏‏‎‎‎‎‏‎‎‏‎‏‏‎‎‏‏‎‎‎‏‎‎‏‏‎‎‎‏‎‏‏‎‎‏‎‎‎‏‎‎‎Can’t verify face. Hardware not available.‎‏‎‎‏‎"</string>
diff --git a/core/res/res/values-es-rUS/strings.xml b/core/res/res/values-es-rUS/strings.xml
index e2e9e32726d8..5c580ea6c038 100644
--- a/core/res/res/values-es-rUS/strings.xml
+++ b/core/res/res/values-es-rUS/strings.xml
@@ -302,7 +302,7 @@
<string name="permgrouplab_camera" msgid="4820372495894586615">"Cámara"</string>
<string name="permgroupdesc_camera" msgid="3250611594678347720">"tomar fotografías y grabar videos"</string>
<string name="permgrouprequest_camera" msgid="1299833592069671756">"¿Permitir que &lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; tome fotos y grabe videos?"</string>
- <string name="permgrouplab_calllog" msgid="8798646184930388160">"Registro de llamadas"</string>
+ <string name="permgrouplab_calllog" msgid="8798646184930388160">"Llamadas"</string>
<string name="permgroupdesc_calllog" msgid="3006237336748283775">"leer y escribir el registro de llamadas telefónicas"</string>
<string name="permgrouprequest_calllog" msgid="8487355309583773267">"¿Permitir que &lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; acceda al registro de las llamadas telefónicas?"</string>
<string name="permgrouplab_phone" msgid="5229115638567440675">"Teléfono"</string>
@@ -571,13 +571,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"Vuelve a registrar tu cara."</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"Ya no se reconoce la cara. Vuelve a intentarlo."</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"Es muy similar a la anterior. Haz otra pose."</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"Gira la cabeza un poco menos."</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"Gira la cabeza un poco menos."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"Mantén la cabeza en posición vertical."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"Ilumina el espacio entre tu cabeza y el teléfono."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"Limpia la cámara."</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"No se verificó el rostro. Hardware no disponible."</string>
diff --git a/core/res/res/values-es/strings.xml b/core/res/res/values-es/strings.xml
index 44e05a5ad79e..e54af4e8f5bc 100644
--- a/core/res/res/values-es/strings.xml
+++ b/core/res/res/values-es/strings.xml
@@ -571,13 +571,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"Vuelve a registrar tu cara."</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"No puede reconocer tu cara. Vuelve a intentarlo."</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"Se parece mucha a la anterior. Pon otra cara."</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"Gira la cabeza un poco menos."</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"Gira la cabeza un poco menos."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"Mantén la cabeza en posición vertical."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"No dejes espacio entre tu cabeza y el teléfono."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"Limpia la cámara."</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"No se puede verificar. Hardware no disponible."</string>
diff --git a/core/res/res/values-et/strings.xml b/core/res/res/values-et/strings.xml
index 99d1c9b378d3..01bd8a4893ef 100644
--- a/core/res/res/values-et/strings.xml
+++ b/core/res/res/values-et/strings.xml
@@ -571,13 +571,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"Registreerige oma nägu uuesti."</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"Nägu ei õnnestu enam tuvastada. Proovige uuesti."</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"Liiga sarnane, palun muutke oma asendit."</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"Pöörake oma pead veidi vähem."</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"Pöörake oma pead veidi vähem."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"Pange pea vertikaalselt otseks."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"Eemaldage pea ja telefoni vahelt takistused."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"Puhastage kaamerat."</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"Nägu ei saa kinnitada. Riistvara pole saadaval."</string>
diff --git a/core/res/res/values-eu/strings.xml b/core/res/res/values-eu/strings.xml
index 87ef0306707d..1cca09e32e75 100644
--- a/core/res/res/values-eu/strings.xml
+++ b/core/res/res/values-eu/strings.xml
@@ -571,13 +571,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"Erregistratu berriro aurpegia."</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"Ez dugu ezagutzen aurpegi hori. Saiatu berriro."</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"Jarrera berdintsuegia da. Alda ezazu."</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"Biratu burua pixka bat gutxiago."</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"Biratu burua pixka bat gutxiago."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"Jarri burua zuzen."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"Kendu buruaren eta telefonoaren arteko oztopoak."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"Garbitu kamera"</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"Ezin da egiaztatu aurpegia. Hardwarea ez dago erabilgarri."</string>
diff --git a/core/res/res/values-fa/strings.xml b/core/res/res/values-fa/strings.xml
index a2388eff526c..f6b2ab717326 100644
--- a/core/res/res/values-fa/strings.xml
+++ b/core/res/res/values-fa/strings.xml
@@ -571,13 +571,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"لطفاً چهره‌تان را مجدداً ثبت کنید."</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"دیگر چهره را تشخیص نمی‌دهد. دوباره امتحان کنید."</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"بسیار شبیه قبلی است، لطفاً قیافه دیگری بگیرید."</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"سرتان را کمی پایین آورید."</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"سرتان را کمی پایین آورید."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"لطفاً سرتان را به‌صورت عمود نگه دارید."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"هرگونه مانعی را بین سرتان و تلفن بردارید."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"لطفاً دوربین را تمیز کنید."</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"چهره تأیید نشد. سخت‌افزار در دسترس نیست."</string>
diff --git a/core/res/res/values-fi/strings.xml b/core/res/res/values-fi/strings.xml
index a66efe9fda02..1fa7efa69c15 100644
--- a/core/res/res/values-fi/strings.xml
+++ b/core/res/res/values-fi/strings.xml
@@ -275,7 +275,7 @@
<string name="android_system_label" msgid="6577375335728551336">"Android-järjestelmä"</string>
<string name="user_owner_label" msgid="8836124313744349203">"Vaihda henkilökohtaiseen profiiliin"</string>
<string name="managed_profile_label" msgid="8947929265267690522">"Vaihda työprofiiliin"</string>
- <string name="permgrouplab_contacts" msgid="3657758145679177612">"Kontaktit"</string>
+ <string name="permgrouplab_contacts" msgid="3657758145679177612">"Yhteystiedot"</string>
<string name="permgroupdesc_contacts" msgid="6951499528303668046">"käyttää yhteystietoja"</string>
<string name="permgrouprequest_contacts" msgid="6032805601881764300">"Saako &lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; yhteystietojesi käyttöoikeuden?"</string>
<string name="permgrouplab_location" msgid="7275582855722310164">"Sijainti"</string>
@@ -571,13 +571,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"Rekisteröi kasvot uudelleen."</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"Ei enää tunnista kasvoja. Yritä uudelleen."</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"Liian samanlainen, vaihda asentoa."</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"Käännä päätä vähän vähemmän."</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"Käännä päätä vähän vähemmän."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"Suorista pää pystysuunnassa."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"Poista esteet pääsi ja puhelimen väliltä."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"Puhdista kamera."</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"Kasvoja ei voi vahvistaa. Laitteisto ei käytettäv."</string>
diff --git a/core/res/res/values-fr-rCA/strings.xml b/core/res/res/values-fr-rCA/strings.xml
index 15453bd57637..bea10c3fd57c 100644
--- a/core/res/res/values-fr-rCA/strings.xml
+++ b/core/res/res/values-fr-rCA/strings.xml
@@ -571,13 +571,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"Veuillez inscrire votre visage à nouveau."</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"Ce visage ne sera plus reconnu. Réessayez."</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"Trop similaire. Changez de pose."</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"Tournez un peu moins votre tête."</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"Tournez un peu moins votre tête."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"Veuillez redresse votre tête verticalement."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"L\'espace entre le tél. et votre tête doit être libre."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"Veuillez nettoyer l\'objectif de l\'appareil photo."</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"Imposs. de vérif. visage. Matériel non accessible."</string>
diff --git a/core/res/res/values-fr/strings.xml b/core/res/res/values-fr/strings.xml
index 262a33283f2a..d26cacc256cf 100644
--- a/core/res/res/values-fr/strings.xml
+++ b/core/res/res/values-fr/strings.xml
@@ -227,7 +227,7 @@
<string name="global_action_emergency" msgid="7112311161137421166">"Urgences"</string>
<string name="global_action_bug_report" msgid="7934010578922304799">"Rapport de bug"</string>
<string name="global_action_logout" msgid="935179188218826050">"Fermer la session"</string>
- <string name="global_action_screenshot" msgid="8329831278085426283">"Capture d\'écran"</string>
+ <string name="global_action_screenshot" msgid="8329831278085426283">"Capture"</string>
<string name="bugreport_title" msgid="5981047024855257269">"Rapport de bug"</string>
<string name="bugreport_message" msgid="398447048750350456">"Cela permet de recueillir des informations concernant l\'état actuel de votre appareil. Ces informations sont ensuite envoyées sous forme d\'e-mail. Merci de patienter pendant la préparation du rapport de bug. Cette opération peut prendre quelques instants."</string>
<string name="bugreport_option_interactive_title" msgid="8635056131768862479">"Rapport interactif"</string>
@@ -571,13 +571,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"Veuillez enregistrer à nouveau votre visage."</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"Impossible de reconnaître le visage. Réessayez."</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"Ressemble à un visage existant, changez de pose."</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"Tournez un peu moins la tête."</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"Tournez un peu moins la tête."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"Veuillez tenir votre tête droite."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"Assurez-vous que rien ne cache votre visage."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"Veuillez nettoyer l\'objectif de l\'appareil photo."</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"Imposs. valider visage. Matériel non disponible."</string>
diff --git a/core/res/res/values-gl/strings.xml b/core/res/res/values-gl/strings.xml
index ec56875ceff1..102beb9bc3b0 100644
--- a/core/res/res/values-gl/strings.xml
+++ b/core/res/res/values-gl/strings.xml
@@ -227,7 +227,7 @@
<string name="global_action_emergency" msgid="7112311161137421166">"Emerxencia"</string>
<string name="global_action_bug_report" msgid="7934010578922304799">"Informe de erros"</string>
<string name="global_action_logout" msgid="935179188218826050">"Finalizar a sesión"</string>
- <string name="global_action_screenshot" msgid="8329831278085426283">"Captura de pantalla"</string>
+ <string name="global_action_screenshot" msgid="8329831278085426283">"Capt. pantalla"</string>
<string name="bugreport_title" msgid="5981047024855257269">"Informe de erros"</string>
<string name="bugreport_message" msgid="398447048750350456">"Este informe recompilará información acerca do estado actual do teu dispositivo para enviala en forma de mensaxe de correo electrónico. O informe de erros tardará un pouco en completarse desde o seu inicio ata que estea preparado para enviarse, polo que che recomendamos que teñas paciencia."</string>
<string name="bugreport_option_interactive_title" msgid="8635056131768862479">"Informe interactivo"</string>
@@ -266,7 +266,7 @@
<string name="notification_channel_retail_mode" msgid="6088920674914038779">"Demostración comercial"</string>
<string name="notification_channel_usb" msgid="9006850475328924681">"conexión USB"</string>
<string name="notification_channel_heavy_weight_app" msgid="6218742927792852607">"Estase executando a aplicación"</string>
- <string name="notification_channel_foreground_service" msgid="3931987440602669158">"Aplicacións que consumen batería"</string>
+ <string name="notification_channel_foreground_service" msgid="3931987440602669158">"Aplicacións que consomen batería"</string>
<string name="foreground_service_app_in_background" msgid="1060198778219731292">"A aplicación <xliff:g id="APP_NAME">%1$s</xliff:g> está consumindo batería"</string>
<string name="foreground_service_apps_in_background" msgid="7175032677643332242">"<xliff:g id="NUMBER">%1$d</xliff:g> aplicacións están consumindo batería"</string>
<string name="foreground_service_tap_for_details" msgid="372046743534354644">"Toca para obter información sobre o uso de datos e a batería"</string>
@@ -275,40 +275,40 @@
<string name="android_system_label" msgid="6577375335728551336">"Sistema Android"</string>
<string name="user_owner_label" msgid="8836124313744349203">"Cambiar ao perfil persoal"</string>
<string name="managed_profile_label" msgid="8947929265267690522">"Cambiar ao perfil de traballo"</string>
- <string name="permgrouplab_contacts" msgid="3657758145679177612">"contactos"</string>
+ <string name="permgrouplab_contacts" msgid="3657758145679177612">"Contactos"</string>
<string name="permgroupdesc_contacts" msgid="6951499528303668046">"acceder aos teus contactos"</string>
<string name="permgrouprequest_contacts" msgid="6032805601881764300">"Queres permitir que a aplicación &lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; acceda aos teus contactos?"</string>
- <string name="permgrouplab_location" msgid="7275582855722310164">"localización"</string>
+ <string name="permgrouplab_location" msgid="7275582855722310164">"Localización"</string>
<string name="permgroupdesc_location" msgid="1346617465127855033">"acceder á localización deste dispositivo"</string>
- <string name="permgrouprequest_location" msgid="3788275734953323491">"Queres permitir que a aplicación &lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; acceda á localización deste dispositivo?"</string>
+ <string name="permgrouprequest_location" msgid="3788275734953323491">"Permitir que a aplicación &lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; acceda á localización deste dispositivo?"</string>
<string name="permgrouprequestdetail_location" msgid="1347189607421252902">"A aplicación só terá acceso á localización mentres a esteas utilizando"</string>
<string name="permgroupbackgroundrequest_location" msgid="5039063878675613235">"Queres permitir que &lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; acceda á localización deste dispositivo &lt;b&gt;sempre&lt;/b&gt;?"</string>
<string name="permgroupbackgroundrequestdetail_location" msgid="4597006851453417387">"Actualmente, a aplicación pode acceder á localización só mentres a utilices"</string>
- <string name="permgrouplab_calendar" msgid="5863508437783683902">"calendario"</string>
+ <string name="permgrouplab_calendar" msgid="5863508437783683902">"Calendario"</string>
<string name="permgroupdesc_calendar" msgid="3889615280211184106">"acceder ao teu calendario"</string>
<string name="permgrouprequest_calendar" msgid="289900767793189421">"Queres permitir que a aplicación &lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; acceda ao teu calendario?"</string>
<string name="permgrouplab_sms" msgid="228308803364967808">"SMS"</string>
<string name="permgroupdesc_sms" msgid="4656988620100940350">"enviar e consultar mensaxes de SMS"</string>
<string name="permgrouprequest_sms" msgid="7168124215838204719">"Queres permitir que a aplicación &lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; envíe e vexa mensaxes SMS?"</string>
- <string name="permgrouplab_storage" msgid="1971118770546336966">"almacenamento"</string>
+ <string name="permgrouplab_storage" msgid="1971118770546336966">"Almacenamento"</string>
<string name="permgroupdesc_storage" msgid="637758554581589203">"acceder a fotos, contido multimedia e ficheiros no teu dispositivo"</string>
<string name="permgrouprequest_storage" msgid="7885942926944299560">"Queres permitir que a aplicación &lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; acceda a fotos, contido multimedia e ficheiros no teu dispositivo?"</string>
<string name="permgrouplab_microphone" msgid="171539900250043464">"Micrófono"</string>
<string name="permgroupdesc_microphone" msgid="4988812113943554584">"gravar audio"</string>
<string name="permgrouprequest_microphone" msgid="9167492350681916038">"Queres permitir que a aplicación &lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; grave audio?"</string>
- <string name="permgrouplab_activityRecognition" msgid="1565108047054378642">"actividade física"</string>
+ <string name="permgrouplab_activityRecognition" msgid="1565108047054378642">"Actividade física"</string>
<string name="permgroupdesc_activityRecognition" msgid="6949472038320473478">"acceder á túa actividade física"</string>
<string name="permgrouprequest_activityRecognition" msgid="7626438016904799383">"Queres permitir que &lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; acceda á túa actividade física?"</string>
- <string name="permgrouplab_camera" msgid="4820372495894586615">"cámara"</string>
+ <string name="permgrouplab_camera" msgid="4820372495894586615">"Cámara"</string>
<string name="permgroupdesc_camera" msgid="3250611594678347720">"tirar fotos e gravar vídeos"</string>
<string name="permgrouprequest_camera" msgid="1299833592069671756">"Queres permitir que a aplicación &lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; realice fotos e grave vídeos?"</string>
- <string name="permgrouplab_calllog" msgid="8798646184930388160">"rexistros de chamadas"</string>
+ <string name="permgrouplab_calllog" msgid="8798646184930388160">"Rexistros de chamadas"</string>
<string name="permgroupdesc_calllog" msgid="3006237336748283775">"ler e editar o rexistro de chamadas do teléfono"</string>
<string name="permgrouprequest_calllog" msgid="8487355309583773267">"Queres permitir que &lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; acceda aos rexistros de chamadas do teléfono?"</string>
- <string name="permgrouplab_phone" msgid="5229115638567440675">"teléfono"</string>
+ <string name="permgrouplab_phone" msgid="5229115638567440675">"Teléfono"</string>
<string name="permgroupdesc_phone" msgid="6234224354060641055">"facer e xestionar chamadas telefónicas"</string>
<string name="permgrouprequest_phone" msgid="9166979577750581037">"Queres permitir que a aplicación &lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; realice e xestione chamadas telefónicas?"</string>
- <string name="permgrouplab_sensors" msgid="4838614103153567532">"sensores corporais"</string>
+ <string name="permgrouplab_sensors" msgid="4838614103153567532">"Sensores corporais"</string>
<string name="permgroupdesc_sensors" msgid="7147968539346634043">"acceder aos datos dos sensores sobre as túas constantes vitais"</string>
<string name="permgrouprequest_sensors" msgid="6349806962814556786">"Queres permitir que a aplicación &lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; acceda aos datos dos sensores sobre as túas constantes vitais?"</string>
<string name="capability_title_canRetrieveWindowContent" msgid="3901717936930170320">"Recuperar contido da ventá"</string>
@@ -571,13 +571,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"Volve rexistrar a túa cara."</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"Xa non se pode recoñecer a cara. Téntao de novo."</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"É moi similar. Cambia a pose."</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"Xira a cabeza un pouco menos."</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"Xira a cabeza un pouco menos."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"Endereita a cabeza."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"Quita o que haxa entre a túa cabeza e o teléfono."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"Limpa a cámara."</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"Sen verificar a cara. Hardware non dispoñible."</string>
@@ -1796,14 +1797,14 @@
<string name="managed_profile_label_badge_2" msgid="5048136430082124036">"2.º <xliff:g id="LABEL">%1$s</xliff:g> do traballo"</string>
<string name="managed_profile_label_badge_3" msgid="2808305070321719040">"3.º <xliff:g id="LABEL">%1$s</xliff:g> do traballo"</string>
<string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"Solicitar PIN para soltar fixación"</string>
- <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"Solicitar un padrón de desbloqueo antes de soltar a pantalla"</string>
- <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"Solicitar un contrasinal antes de soltar a pantalla"</string>
+ <string name="lock_to_app_unlock_pattern" msgid="4182192144797225137">"Solicitar un padrón de desbloqueo antes de deixar de fixar a pantalla"</string>
+ <string name="lock_to_app_unlock_password" msgid="6380979775916974414">"Solicitar un contrasinal para deixar de fixar a pantalla"</string>
<string name="package_installed_device_owner" msgid="6875717669960212648">"Instalado polo teu administrador"</string>
<string name="package_updated_device_owner" msgid="1847154566357862089">"Actualizado polo teu administrador"</string>
<string name="package_deleted_device_owner" msgid="2307122077550236438">"Eliminado polo teu administrador"</string>
<string name="confirm_battery_saver" msgid="639106420541753635">"Aceptar"</string>
- <string name="battery_saver_description_with_learn_more" msgid="2108984221113106294">"A función Aforro de batería desactiva ou restrinxe a actividade en segundo plano, algúns efectos visuais e outras funcións que consumen moita batería para que esta dure máis. "<annotation id="url">"Máis información"</annotation></string>
- <string name="battery_saver_description" msgid="6413346684861241431">"A función Aforro de batería desactiva ou restrinxe a actividade en segundo plano, algúns efectos visuais e outras funcións que consumen moita batería para que esta dure máis."</string>
+ <string name="battery_saver_description_with_learn_more" msgid="2108984221113106294">"A función Aforro de batería desactiva ou restrinxe a actividade en segundo plano, algúns efectos visuais e outras funcións que consomen moita batería para que esta dure máis. "<annotation id="url">"Máis información"</annotation></string>
+ <string name="battery_saver_description" msgid="6413346684861241431">"A función Aforro de batería desactiva ou restrinxe a actividade en segundo plano, algúns efectos visuais e outras funcións que consomen moita batería para que esta dure máis."</string>
<string name="data_saver_description" msgid="6015391409098303235">"Para contribuír a reducir o uso de datos, o Economizador de datos impide que algunhas aplicacións envíen ou reciban datos en segundo plano. Cando esteas utilizando unha aplicación, esta poderá acceder aos datos, pero é posible que o faga con menos frecuencia. Por exemplo, é posible que as imaxes non se mostren ata que as toques."</string>
<string name="data_saver_enable_title" msgid="4674073932722787417">"Queres activar o economizador de datos?"</string>
<string name="data_saver_enable_button" msgid="7147735965247211818">"Activar"</string>
diff --git a/core/res/res/values-gu/strings.xml b/core/res/res/values-gu/strings.xml
index 43ffac0c5ede..e0107e97c04e 100644
--- a/core/res/res/values-gu/strings.xml
+++ b/core/res/res/values-gu/strings.xml
@@ -575,9 +575,12 @@
<skip />
<!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"કૃપા કરીને તમારું માથું સીધું ઊભું રાખો."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"તમારા મસ્તક અને ફોન વચ્ચેની જગ્યા સાફ કરો."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"કૃપા કરીને કૅમેરા સાફ કરો."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
+ <skip />
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
+ <skip />
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"ચહેરો ચકાસી શકાતો નથી. હાર્ડવેર ઉપલબ્ધ નથી."</string>
diff --git a/core/res/res/values-hi/strings.xml b/core/res/res/values-hi/strings.xml
index 8564a0a81a38..d47d0425d15d 100644
--- a/core/res/res/values-hi/strings.xml
+++ b/core/res/res/values-hi/strings.xml
@@ -42,8 +42,8 @@
<string name="serviceErased" msgid="1288584695297200972">"मिटाना सफल था."</string>
<string name="passwordIncorrect" msgid="7612208839450128715">"गलत पासवर्ड"</string>
<string name="mmiComplete" msgid="8232527495411698359">"MMI पूर्ण."</string>
- <string name="badPin" msgid="9015277645546710014">"आपके द्वारा लिखा गया पुराना पिन सही नहीं है."</string>
- <string name="badPuk" msgid="5487257647081132201">"आपके द्वारा लिखा गया PUK सही नहीं है."</string>
+ <string name="badPin" msgid="9015277645546710014">" लिखा गया पुराना पिन सही नहीं है."</string>
+ <string name="badPuk" msgid="5487257647081132201">" लिखा गया PUK सही नहीं है."</string>
<string name="mismatchPin" msgid="609379054496863419">"आपने जो पिन लिखे हैं उसका मिलान नहीं होता."</string>
<string name="invalidPin" msgid="3850018445187475377">"कोई ऐसा पिन लिखें, जिसमें 4 से 8 अंक हों."</string>
<string name="invalidPuk" msgid="8761456210898036513">"ऐसा PUK लिखें जो 8 अंकों या ज़्यादा का हो."</string>
@@ -180,11 +180,11 @@
<item quantity="other">प्रमाणपत्र अनुमतियों को इंस्टॉल किया गया</item>
</plurals>
<string name="ssl_ca_cert_noti_by_unknown" msgid="4475437862189850602">"किसी अज्ञात तृतीय पक्ष के द्वारा"</string>
- <string name="ssl_ca_cert_noti_by_administrator" msgid="3541729986326153557">"आपकी कार्य प्रोफ़ाइल का व्यवस्थापक करता है"</string>
+ <string name="ssl_ca_cert_noti_by_administrator" msgid="3541729986326153557">"आपकी वर्क प्रोफ़ाइल का व्यवस्थापक करता है"</string>
<string name="ssl_ca_cert_noti_managed" msgid="4030263497686867141">"<xliff:g id="MANAGING_DOMAIN">%s</xliff:g> के द्वारा"</string>
- <string name="work_profile_deleted" msgid="5005572078641980632">"कार्य प्रोफ़ाइल हटाई गई"</string>
- <string name="work_profile_deleted_details" msgid="6307630639269092360">"कार्य प्रोफ़ाइल व्यवस्थापक ऐप्लिकेशन या तो मौजूद नहीं है या वह खराब हो गया है. परिणामस्वरूप, आपकी कार्य प्रोफ़ाइल और उससे जुड़े डेटा को हटा दिया गया है. सहायता के लिए अपने व्यवस्थापक से संपर्क करें."</string>
- <string name="work_profile_deleted_description_dpm_wipe" msgid="8823792115612348820">"आपकी कार्य प्रोफ़ाइल अब इस डिवाइस पर उपलब्‍ध नहीं है"</string>
+ <string name="work_profile_deleted" msgid="5005572078641980632">"वर्क प्रोफ़ाइल हटाई गई"</string>
+ <string name="work_profile_deleted_details" msgid="6307630639269092360">"वर्क प्रोफ़ाइल व्यवस्थापक ऐप्लिकेशन या तो मौजूद नहीं है या वह खराब हो गया है. परिणामस्वरूप, आपकी वर्क प्रोफ़ाइल और उससे जुड़े डेटा को हटा दिया गया है. सहायता के लिए अपने व्यवस्थापक से संपर्क करें."</string>
+ <string name="work_profile_deleted_description_dpm_wipe" msgid="8823792115612348820">"आपकी वर्क प्रोफ़ाइल अब इस डिवाइस पर उपलब्‍ध नहीं है"</string>
<string name="work_profile_deleted_reason_maximum_password_failure" msgid="8986903510053359694">"कई बार गलत पासवर्ड डाला गया"</string>
<string name="network_logging_notification_title" msgid="6399790108123704477">"डिवाइस प्रबंधित है"</string>
<string name="network_logging_notification_text" msgid="7930089249949354026">"आपका संगठन इस डिवाइस का प्रबंधन करता है और वह नेटवर्क ट्रैफ़िक की निगरानी भी कर सकता है. विवरण के लिए टैप करें."</string>
@@ -274,7 +274,7 @@
<string name="safeMode" msgid="2788228061547930246">"सुरक्षित मोड"</string>
<string name="android_system_label" msgid="6577375335728551336">"Android सिस्‍टम"</string>
<string name="user_owner_label" msgid="8836124313744349203">"प्रोफ़ाइल बदलकर निजी प्रोफ़ाइल पर जाएं"</string>
- <string name="managed_profile_label" msgid="8947929265267690522">"प्रोफ़ाइल बदलकर कार्य प्रोफ़ाइल पर जाएं"</string>
+ <string name="managed_profile_label" msgid="8947929265267690522">"प्रोफ़ाइल बदलकर वर्क प्रोफ़ाइल पर जाएं"</string>
<string name="permgrouplab_contacts" msgid="3657758145679177612">"संपर्क"</string>
<string name="permgroupdesc_contacts" msgid="6951499528303668046">"अपने संपर्कों को ऐक्सेस करने की"</string>
<string name="permgrouprequest_contacts" msgid="6032805601881764300">"&lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; को अपने संपर्क देखने की अनुमति देना चाहते हैं?"</string>
@@ -392,9 +392,9 @@
<string name="permdesc_readContacts" product="tv" msgid="1839238344654834087">"ऐप को आपके टीवी पर मौजूद आपके संपर्कों का डेटा पढ़ने देती है, जिसमें ये भी शामिल है कि आपने कुछ ख़ास लोगों से कितनी बार कॉल, ईमेल, या कुछ और तरीकों से बातचीत की. यह अनुमति ऐप को आपका संपर्क डेटा सेव करने देती है और धोखा देने वाले ऐप संपर्क डेटा को आपकी जानकारी के बिना शेयर कर सकते हैं."</string>
<string name="permdesc_readContacts" product="default" msgid="8440654152457300662">"ऐप को आपके फ़ोन पर मौजूद आपके संपर्कों का डेटा पढ़ने देती है, जिसमें ये भी शामिल है कि आपने कुछ ख़ास लोगों से कितनी बार कॉल, ईमेल, या कुछ और तरीकों से बातचीत की. यह अनुमति ऐप को आपका संपर्क डेटा सेव करने देती है और धोखा देने वाले ऐप, संपर्क डेटा को आपकी जानकारी के बिना शेयर कर सकते हैं."</string>
<string name="permlab_writeContacts" msgid="5107492086416793544">"अपने संपर्क बदलें"</string>
- <string name="permdesc_writeContacts" product="tablet" msgid="897243932521953602">"ऐप्स को आपके टैबलेट में संग्रहित संपर्कों के डेटा को, साथ ही आपके द्वारा विशिष्ट व्यक्तियों को कॉल करने, ईमेल करने, या अन्‍य तरीके से डॉयलॉग करने की आवृत्ति को संशोधित करने देता है. यह अनुमति ऐप्स को आपके संपर्क डेटा को हटाने देती है."</string>
- <string name="permdesc_writeContacts" product="tv" msgid="5438230957000018959">"ऐप को आपके टीवी पर संग्रहित आपके संपर्कों के बारे में संग्रहित डेटा में बदलाव करने देती है, जिसमें आपके द्वारा विशिष्‍ट व्‍यक्‍तियों को कॉल करने, ईमेल भेजने या अन्‍य तरीकों से संचार किए जाने की आवृत्‍ति भी शामिल है. यह अनुमति ऐप्‍स को संपर्क डेटा हटाने देती है."</string>
- <string name="permdesc_writeContacts" product="default" msgid="589869224625163558">"ऐप्स को आपके फ़ोन में संग्रहित संपर्कों के डेटा को, साथ ही आपके द्वारा विशिष्ट व्यक्तियों को कॉल करने, ईमेल करने, या अन्‍य तरीके से डॉयलॉग करने की आवृत्ति को संशोधित करने देता है. यह अनुमति ऐप्स को आपके संपर्क डेटा को हटाने देती है."</string>
+ <string name="permdesc_writeContacts" product="tablet" msgid="897243932521953602">"ऐप्स को आपके टैबलेट में संग्रहित संपर्कों के डेटा को, साथ ही विशिष्ट व्यक्तियों को कॉल करने, ईमेल करने, या अन्‍य तरीके से डॉयलॉग करने की आवृत्ति को संशोधित करने देता है. यह अनुमति ऐप्स को आपके संपर्क डेटा को हटाने देती है."</string>
+ <string name="permdesc_writeContacts" product="tv" msgid="5438230957000018959">"ऐप को आपके टीवी पर संग्रहित आपके संपर्कों के बारे में संग्रहित डेटा में बदलाव करने देती है, जिसमें विशिष्‍ट व्‍यक्‍तियों को कॉल करने, ईमेल भेजने या अन्‍य तरीकों से संचार किए जाने की आवृत्‍ति भी शामिल है. यह अनुमति ऐप्‍स को संपर्क डेटा हटाने देती है."</string>
+ <string name="permdesc_writeContacts" product="default" msgid="589869224625163558">"ऐप्स को आपके फ़ोन में संग्रहित संपर्कों के डेटा को, साथ ही विशिष्ट व्यक्तियों को कॉल करने, ईमेल करने, या अन्‍य तरीके से डॉयलॉग करने की आवृत्ति को संशोधित करने देता है. यह अनुमति ऐप्स को आपके संपर्क डेटा को हटाने देती है."</string>
<string name="permlab_readCallLog" msgid="3478133184624102739">"कॉल लॉग पढ़ें"</string>
<string name="permdesc_readCallLog" msgid="3204122446463552146">"यह ऐप्लिकेशन आपका कॉल इतिहास पढ़ सकता है."</string>
<string name="permlab_writeCallLog" msgid="8552045664743499354">"कॉल लॉग लिखें"</string>
@@ -466,9 +466,9 @@
<string name="permdesc_setTimeZone" product="tv" msgid="888864653946175955">"ऐप को टीवी का समय क्षेत्र बदलने देती है."</string>
<string name="permdesc_setTimeZone" product="default" msgid="4499943488436633398">"ऐप्स को टैबलेट का समय क्षेत्र बदलने देता है."</string>
<string name="permlab_getAccounts" msgid="1086795467760122114">"डिवाइस पर खाते ढूंढें"</string>
- <string name="permdesc_getAccounts" product="tablet" msgid="2741496534769660027">"ऐप्स को टैबलेट द्वारा ज्ञात खातों की सूची प्राप्‍त करने देता है. इसमें वे खाते शामिल हो सकते हैं जिन्‍हें आपके द्वारा इंस्‍टॉल किए गए ऐप्स ने बनाया है."</string>
- <string name="permdesc_getAccounts" product="tv" msgid="4190633395633907543">"ऐप को टीवी द्वारा ज्ञात खातों की सूची प्राप्‍त करने देती है. इसमें आपके द्वारा इंस्‍टॉल किए गए ऐप्‍लिकेशन के द्वारा बनाए गए खाते शामिल हो सकते हैं."</string>
- <string name="permdesc_getAccounts" product="default" msgid="3448316822451807382">"ऐप्स को फ़ोन द्वारा ज्ञात खातों की सूची प्राप्‍त करने देता है. इसमें वे खाते शामिल हो सकते हैं जिन्‍हें आपके द्वारा इंस्‍टॉल किए गए ऐप्स ने बनाया है."</string>
+ <string name="permdesc_getAccounts" product="tablet" msgid="2741496534769660027">"ऐप्स को टैबलेट द्वारा ज्ञात खातों की सूची प्राप्‍त करने देता है. इसमें वे खाते शामिल हो सकते हैं जिन्‍हें इंस्‍टॉल किए गए ऐप्स ने बनाया है."</string>
+ <string name="permdesc_getAccounts" product="tv" msgid="4190633395633907543">"ऐप को टीवी द्वारा ज्ञात खातों की सूची प्राप्‍त करने देती है. इसमें इंस्‍टॉल किए गए ऐप्‍लिकेशन के द्वारा बनाए गए खाते शामिल हो सकते हैं."</string>
+ <string name="permdesc_getAccounts" product="default" msgid="3448316822451807382">"ऐप्स को फ़ोन द्वारा ज्ञात खातों की सूची प्राप्‍त करने देता है. इसमें वे खाते शामिल हो सकते हैं जिन्‍हें इंस्‍टॉल किए गए ऐप्स ने बनाया है."</string>
<string name="permlab_accessNetworkState" msgid="4951027964348974773">"नेटवर्क कनेक्‍शन देखें"</string>
<string name="permdesc_accessNetworkState" msgid="8318964424675960975">"ऐप को नेटवर्क कनेक्‍शन के बारे में जानकारी देखने देता है, जैसे कौन से नेटवर्क मौजूद हैं और कनेक्‍ट हैं."</string>
<string name="permlab_createNetworkSockets" msgid="7934516631384168107">"नेटवर्क को पूरी तरह इस्तेमाल करें"</string>
@@ -575,9 +575,12 @@
<skip />
<!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"कृपया अपना सिर सीधा करें, दाएं-बाएं न झुकाएं"</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"अपने सिर और फ़ोन के बीच की दूरी हटाएं."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"कृपया कैमरा साफ़ करें."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
+ <skip />
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
+ <skip />
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"चेहरा नहीं पहचान पा रहे. हार्डवेयर उपलब्ध नहीं है."</string>
@@ -1111,7 +1114,7 @@
<string name="define" msgid="7394820043869954211">"परिभाषित करें"</string>
<string name="define_desc" msgid="7910883642444919726">"चुना गया टेक्स्ट परिभाषित करें"</string>
<string name="low_internal_storage_view_title" msgid="5576272496365684834">"मेमोरी में जगह नहीं बची है"</string>
- <string name="low_internal_storage_view_text" msgid="6640505817617414371">"हो सकता है कुछ सिस्टम फ़ंक्शन कार्य न करें"</string>
+ <string name="low_internal_storage_view_text" msgid="6640505817617414371">"हो सकता है कुछ सिस्टम फ़ंक्शन काम नहीं करें"</string>
<string name="low_internal_storage_view_text_no_boot" msgid="6935190099204693424">"सिस्टम के लिए ज़रूरी मेमोरी नहीं है. पक्का करें कि आपके पास 250एमबी की खाली जगह है और फिर से शुरू करें."</string>
<string name="app_running_notification_title" msgid="8718335121060787914">"<xliff:g id="APP_NAME">%1$s</xliff:g> चल रहा है"</string>
<string name="app_running_notification_text" msgid="1197581823314971177">"ज़्यादा जानकारी के लिए या ऐप्लिकेशन को रोकने के लिए छूएं."</string>
@@ -1446,8 +1449,8 @@
<string name="deny" msgid="2081879885755434506">"अस्वीकारें"</string>
<string name="permission_request_notification_title" msgid="6486759795926237907">"अनुमति अनुरोधित"</string>
<string name="permission_request_notification_with_subtitle" msgid="8530393139639560189">"<xliff:g id="ACCOUNT">%s</xliff:g> खाते के लिए अनुमति\nका अनुरोध किया गया."</string>
- <string name="forward_intent_to_owner" msgid="1207197447013960896">"आप इस ऐप्स का उपयोग अपनी कार्य प्रोफ़ाइल से बाहर कर रहे हैं"</string>
- <string name="forward_intent_to_work" msgid="621480743856004612">"आप इस ऐप्स का उपयोग अपनी कार्य प्रोफ़ाइल में कर रहे हैं"</string>
+ <string name="forward_intent_to_owner" msgid="1207197447013960896">"आप इस ऐप्स का उपयोग अपनी वर्क प्रोफ़ाइल से बाहर कर रहे हैं"</string>
+ <string name="forward_intent_to_work" msgid="621480743856004612">"आप इस ऐप्स का उपयोग अपनी वर्क प्रोफ़ाइल में कर रहे हैं"</string>
<string name="input_method_binding_label" msgid="1283557179944992649">"इनपुट विधि"</string>
<string name="sync_binding_label" msgid="3687969138375092423">"समन्वयन"</string>
<string name="accessibility_binding_label" msgid="4148120742096474641">"सुलभता"</string>
@@ -1584,7 +1587,7 @@
<string name="activity_resolver_use_always" msgid="8017770747801494933">"हमेशा"</string>
<string name="activity_resolver_use_once" msgid="2404644797149173758">"केवल एक बार"</string>
<string name="activity_resolver_app_settings" msgid="8965806928986509855">"सेटिंग"</string>
- <string name="activity_resolver_work_profiles_support" msgid="185598180676883455">"%1$s कार्य प्रोफ़ाइल का समर्थन नहीं करता"</string>
+ <string name="activity_resolver_work_profiles_support" msgid="185598180676883455">"%1$s वर्क प्रोफ़ाइल का समर्थन नहीं करता"</string>
<string name="default_audio_route_name" product="tablet" msgid="4617053898167127471">"टैबलेट"</string>
<string name="default_audio_route_name" product="tv" msgid="9158088547603019321">"टीवी"</string>
<string name="default_audio_route_name" product="default" msgid="4239291273420140123">"फ़ोन"</string>
@@ -1791,7 +1794,7 @@
<string name="select_day" msgid="7774759604701773332">"माह और दिन चुनें"</string>
<string name="select_year" msgid="7952052866994196170">"वर्ष चुनें"</string>
<string name="deleted_key" msgid="7659477886625566590">"<xliff:g id="KEY">%1$s</xliff:g> को हटा दिया गया"</string>
- <string name="managed_profile_label_badge" msgid="2355652472854327647">"कार्यस्थल का <xliff:g id="LABEL">%1$s</xliff:g>"</string>
+ <string name="managed_profile_label_badge" msgid="2355652472854327647">"दफ़्तर का <xliff:g id="LABEL">%1$s</xliff:g>"</string>
<string name="managed_profile_label_badge_2" msgid="5048136430082124036">"दूसरा कार्य <xliff:g id="LABEL">%1$s</xliff:g>"</string>
<string name="managed_profile_label_badge_3" msgid="2808305070321719040">"तीसरा कार्य <xliff:g id="LABEL">%1$s</xliff:g>"</string>
<string name="lock_to_app_unlock_pin" msgid="2552556656504331634">"अनपिन करने से पहले पिन के लिए पूछें"</string>
@@ -1861,7 +1864,7 @@
<string name="stk_cc_ss_to_dial_video" msgid="6577956662913194947">"एसएस कोड चलाने के अनुरोध को वीडियो कॉल में बदला गया"</string>
<string name="stk_cc_ss_to_ussd" msgid="5614626512855868785">"एसएस कोड चलाने के अनुरोध को यूएसएसडी कोड चलाने के अनुरोध में बदला गया"</string>
<string name="stk_cc_ss_to_ss" msgid="7716729801537709054">"एसएस कोड चलाने के नए अनुरोध में बदला गया"</string>
- <string name="notification_work_profile_content_description" msgid="4600554564103770764">"कार्य प्रोफ़ाइल"</string>
+ <string name="notification_work_profile_content_description" msgid="4600554564103770764">"वर्क प्रोफ़ाइल"</string>
<string name="notification_alerted_content_description" msgid="1296617716556420585">"अलर्ट किया गया"</string>
<string name="expand_button_content_description_collapsed" msgid="3609784019345534652">"विस्तार करें"</string>
<string name="expand_button_content_description_expanded" msgid="8520652707158554895">"छोटा करें"</string>
@@ -1893,8 +1896,8 @@
<string name="app_suspended_title" msgid="2075071241147969611">"यह ऐप्लिकेशन उपलब्ध नहीं है"</string>
<string name="app_suspended_default_message" msgid="123166680425711887">"फ़िलहाल <xliff:g id="APP_NAME_0">%1$s</xliff:g> उपलब्ध नहीं है. इसे <xliff:g id="APP_NAME_1">%2$s</xliff:g> के ज़रिए प्रबंधित किया जाता है."</string>
<string name="app_suspended_more_details" msgid="1131804827776778187">"ज़्यादा जानें"</string>
- <string name="work_mode_off_title" msgid="1118691887588435530">"कार्य प्रोफ़ाइल चालू करें?"</string>
- <string name="work_mode_off_message" msgid="5130856710614337649">"आपके काम से जुड़े ऐप्लिकेशन, सूचनाएं, डेटा और कार्य प्रोफ़ाइल से जुड़ी दूसरी सुविधाएं चालू हो जाएंगी"</string>
+ <string name="work_mode_off_title" msgid="1118691887588435530">"वर्क प्रोफ़ाइल चालू करें?"</string>
+ <string name="work_mode_off_message" msgid="5130856710614337649">"आपके काम से जुड़े ऐप्लिकेशन, सूचनाएं, डेटा और वर्क प्रोफ़ाइल से जुड़ी दूसरी सुविधाएं चालू हो जाएंगी"</string>
<string name="work_mode_turn_on" msgid="2062544985670564875">"चालू करें"</string>
<string name="deprecated_target_sdk_message" msgid="1449696506742572767">"यह ऐप्लिकेशन Android के पुराने वर्शन के लिए बनाया गया था, इसलिए हो सकता है कि यह सही से काम न करे. देखें कि अपडेट मौजूद हैं या नहीं, या फिर डेवलपर से संपर्क करें."</string>
<string name="deprecated_target_sdk_app_store" msgid="5032340500368495077">"देखें कि अपडेट मौजूद है या नहीं"</string>
@@ -1903,7 +1906,7 @@
<string name="user_encrypted_title" msgid="9054897468831672082">"कुछ कार्य क्षमताएं सीमित हो सकती हैं"</string>
<string name="user_encrypted_message" msgid="4923292604515744267">"अनलॉक करने के लिए टैप करें"</string>
<string name="user_encrypted_detail" msgid="5708447464349420392">"उपयोगकर्ता डेटा लॉक किया गया"</string>
- <string name="profile_encrypted_detail" msgid="3700965619978314974">"कार्य प्रोफ़ाइल लॉक है"</string>
+ <string name="profile_encrypted_detail" msgid="3700965619978314974">"वर्क प्रोफ़ाइल लॉक है"</string>
<string name="profile_encrypted_message" msgid="6964994232310195874">"कार्य प्रोफाइल अनलॉक करने के लिए टैप करें"</string>
<string name="usb_mtp_launch_notification_title" msgid="8359219638312208932">"<xliff:g id="PRODUCT_NAME">%1$s</xliff:g> से कनेक्ट किया गया"</string>
<string name="usb_mtp_launch_notification_description" msgid="8541876176425411358">"फ़ाइलें देखने के लिए टैप करें"</string>
@@ -2029,5 +2032,5 @@
<item quantity="other"><xliff:g id="FILE_NAME_2">%s</xliff:g> + <xliff:g id="COUNT_3">%d</xliff:g> फ़ाइलें</item>
</plurals>
<string name="chooser_no_direct_share_targets" msgid="997970693708458895">"सीधे शेयर नहीं किया जा सकता"</string>
- <string name="chooser_all_apps_button_label" msgid="3631524352936289457">"ऐप्लिकेशन सूची"</string>
+ <string name="chooser_all_apps_button_label" msgid="3631524352936289457">"ऐप्लिकेशन की सूची"</string>
</resources>
diff --git a/core/res/res/values-hr/strings.xml b/core/res/res/values-hr/strings.xml
index 8c5bc4138a7a..fd7fcce6acca 100644
--- a/core/res/res/values-hr/strings.xml
+++ b/core/res/res/values-hr/strings.xml
@@ -574,13 +574,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"Ponovo registrirajte svoje lice."</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"Lice nije prepoznato. Pokušajte ponovo."</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"Previše slično, promijenite pozu."</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"Nagnite glavu malo manje."</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"Nagnite glavu malo manje."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"Izravnajte glavu okomito."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"Uklonite sve između svojeg lica i telefona."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"Očistite fotoaparat."</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"Lice nije potvrđeno. Hardver nije dostupan."</string>
@@ -1324,7 +1325,7 @@
<string name="wifi_p2p_enter_pin_message" msgid="5920929550367828970">"Upišite potreban PIN:"</string>
<string name="wifi_p2p_show_pin_message" msgid="8530563323880921094">"PIN:"</string>
<string name="wifi_p2p_frequency_conflict_message" product="tablet" msgid="8012981257742232475">"Tablet će se privremeno isključiti s Wi-Fija dok je povezan s uređajem <xliff:g id="DEVICE_NAME">%1$s</xliff:g>"</string>
- <string name="wifi_p2p_frequency_conflict_message" product="tv" msgid="3087858235069421128">"Televizor će privremeno prekinuti vezu s Wi-Fi-jem dok je povezan s uređajem <xliff:g id="DEVICE_NAME">%1$s</xliff:g>"</string>
+ <string name="wifi_p2p_frequency_conflict_message" product="tv" msgid="3087858235069421128">"Televizor će privremeno prekinuti vezu s Wi-Fijem dok je povezan s uređajem <xliff:g id="DEVICE_NAME">%1$s</xliff:g>"</string>
<string name="wifi_p2p_frequency_conflict_message" product="default" msgid="7363907213787469151">"Telefon će se privremeno isključiti s Wi-Fija dok je povezan s uređajem <xliff:g id="DEVICE_NAME">%1$s</xliff:g>"</string>
<string name="select_character" msgid="3365550120617701745">"Umetni znak"</string>
<string name="sms_control_title" msgid="7296612781128917719">"Slanje SMS poruka"</string>
diff --git a/core/res/res/values-hu/strings.xml b/core/res/res/values-hu/strings.xml
index 2dff9031ef47..8571ebbc39eb 100644
--- a/core/res/res/values-hu/strings.xml
+++ b/core/res/res/values-hu/strings.xml
@@ -571,13 +571,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"Rögzítsen újra képet az arcáról."</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"Már nem lehet felismerni az arcát. Próbálja újra."</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"Túlságosan hasonló, változtasson a pózon."</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"Kicsit kevésbé fordítsa el a fejét."</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"Kicsit kevésbé fordítsa el a fejét."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"Fejét tartsa egyenesen, függőleges irányban."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"Távolítson el mindent az arca és a telefon közül."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"Tisztítsa meg a kamerát."</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"Sikertelen arcellenőrzés. A hardver nem érhető el."</string>
@@ -1028,20 +1029,20 @@
<item quantity="one"><xliff:g id="COUNT_0">%d</xliff:g>é múlva</item>
</plurals>
<plurals name="duration_minutes_relative" formatted="false" msgid="3178131706192980192">
- <item quantity="other"><xliff:g id="COUNT_1">%d</xliff:g> perccel ezelőtt</item>
- <item quantity="one"><xliff:g id="COUNT_0">%d</xliff:g> perccel ezelőtt</item>
+ <item quantity="other"><xliff:g id="COUNT_1">%d</xliff:g> perce</item>
+ <item quantity="one"><xliff:g id="COUNT_0">%d</xliff:g> perce</item>
</plurals>
<plurals name="duration_hours_relative" formatted="false" msgid="676894109982008411">
- <item quantity="other"><xliff:g id="COUNT_1">%d</xliff:g> órával ezelőtt</item>
- <item quantity="one"><xliff:g id="COUNT_0">%d</xliff:g> órával ezelőtt</item>
+ <item quantity="other"><xliff:g id="COUNT_1">%d</xliff:g> órája</item>
+ <item quantity="one"><xliff:g id="COUNT_0">%d</xliff:g> órája</item>
</plurals>
<plurals name="duration_days_relative" formatted="false" msgid="2203515825765397130">
- <item quantity="other"><xliff:g id="COUNT_1">%d</xliff:g> nappal ezelőtt</item>
- <item quantity="one"><xliff:g id="COUNT_0">%d</xliff:g> nappal ezelőtt</item>
+ <item quantity="other"><xliff:g id="COUNT_1">%d</xliff:g> napja</item>
+ <item quantity="one"><xliff:g id="COUNT_0">%d</xliff:g> napja</item>
</plurals>
<plurals name="duration_years_relative" formatted="false" msgid="4820062134188885734">
- <item quantity="other"><xliff:g id="COUNT_1">%d</xliff:g> évvel ezelőtt</item>
- <item quantity="one"><xliff:g id="COUNT_0">%d</xliff:g> évvel ezelőtt</item>
+ <item quantity="other"><xliff:g id="COUNT_1">%d</xliff:g> éve</item>
+ <item quantity="one"><xliff:g id="COUNT_0">%d</xliff:g> éve</item>
</plurals>
<plurals name="duration_minutes_relative_future" formatted="false" msgid="4655043589817680966">
<item quantity="other"><xliff:g id="COUNT_1">%d</xliff:g> percen belül</item>
diff --git a/core/res/res/values-hy/strings.xml b/core/res/res/values-hy/strings.xml
index 2afcbee089f5..20aaf6c35a15 100644
--- a/core/res/res/values-hy/strings.xml
+++ b/core/res/res/values-hy/strings.xml
@@ -218,7 +218,7 @@
<string name="reboot_safemode_title" msgid="7054509914500140361">"Վերաբեռնել անվտանգ ռեժիմի"</string>
<string name="reboot_safemode_confirm" msgid="55293944502784668">"Ցանկանու՞մ եք վերաբեռնել անվտանգ ռեժիմի: Սա կկասեցնի ձեր տեղադրած բոլոր կողմնակի ծրագրերը: Դրանք կվերականգնվեն, երբ դուք կրկին վերաբեռնեք:"</string>
<string name="recent_tasks_title" msgid="3691764623638127888">"Վերջին"</string>
- <string name="no_recent_tasks" msgid="8794906658732193473">"Նոր հավելվածեր չկան:"</string>
+ <string name="no_recent_tasks" msgid="8794906658732193473">"Նոր հավելվածներ չկան:"</string>
<string name="global_actions" product="tablet" msgid="408477140088053665">"Պլանշետի ընտրանքները"</string>
<string name="global_actions" product="tv" msgid="7240386462508182976">"Հեռուստացույցի ընտրանքներ"</string>
<string name="global_actions" product="default" msgid="2406416831541615258">"Հեռախոսի ընտրանքներ"</string>
@@ -280,7 +280,7 @@
<string name="permgrouprequest_contacts" msgid="6032805601881764300">"Թույլատրե՞լ &lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; հավելվածին օգտագործել ձեր կոնտակտները"</string>
<string name="permgrouplab_location" msgid="7275582855722310164">"Տեղորոշում"</string>
<string name="permgroupdesc_location" msgid="1346617465127855033">"տեղորոշել այս սարքը"</string>
- <string name="permgrouprequest_location" msgid="3788275734953323491">"Թույլատրե՞լ, որ &lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt;-ն օգտագործի այս սարքի տեղադրության տվյալները"</string>
+ <string name="permgrouprequest_location" msgid="3788275734953323491">"Թույլատրե՞լ &lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt;-ին օգտագործել այս սարքի տեղադրության տվյալները"</string>
<string name="permgrouprequestdetail_location" msgid="1347189607421252902">"Տեղադրության տվյալները հասանելի կլինեն հավելվածին, միայն երբ այն օգտագործելիս լինեք"</string>
<string name="permgroupbackgroundrequest_location" msgid="5039063878675613235">"&lt;b&gt;Միշտ&lt;/b&gt; հասանելի դարձնե՞լ &lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; հավելվածին ձեր սարքի տեղադրությունը"</string>
<string name="permgroupbackgroundrequestdetail_location" msgid="4597006851453417387">"Տեղադրության տվյալները հասանելի կլինեն հավելվածին, միայն երբ այն օգտագործելիս լինեք"</string>
@@ -571,13 +571,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"Նորից փորձեք։"</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"Չհաջողվեց ճանաչել դեմքը։ Նորից փորձեք:"</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"Շատ նման է նախորդին։ Փոխեք ձեր դիրքը։"</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"Գլուխն ուղիղ պահեք։"</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"Գլուխն ուղիղ պահեք։"</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"Ուղղեք գլուխը հորիզոնական գծով։"</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"Գլխի և հեռախոսի միջև տարածությունը պետք է բաց լինի"</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"Մաքրեք տեսախցիկը։"</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"Չհաջողվեց հաստատել դեմքը։ Սարքն անհասանելի է:"</string>
diff --git a/core/res/res/values-in/strings.xml b/core/res/res/values-in/strings.xml
index 49b228ce910e..00cc38f7d98d 100644
--- a/core/res/res/values-in/strings.xml
+++ b/core/res/res/values-in/strings.xml
@@ -571,13 +571,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"Daftarkan ulang wajah Anda."</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"Tidak lagi dapat mengenali wajah. Coba lagi."</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"Terlalu mirip, ubah pose Anda."</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"Putar sedikit kepala Anda."</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"Putar sedikit kepala Anda."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"Luruskan kepala secara vertikal."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"Pastikan wajah Anda tidak terhalang."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"Harap bersihkan kamera."</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"Tidak dapat memverifikasi wajah. Hardware tidak tersedia."</string>
diff --git a/core/res/res/values-is/strings.xml b/core/res/res/values-is/strings.xml
index d45498d3b39f..57df45c658a7 100644
--- a/core/res/res/values-is/strings.xml
+++ b/core/res/res/values-is/strings.xml
@@ -571,13 +571,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"Skráðu nafnið þitt aftur."</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"Andlit þekkist ekki lengur. Reyndu aftur."</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"Of svipað. Stilltu þér öðruvísi upp."</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"Snúðu höfðinu aðeins minna."</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"Hallaðu höfðinu aðeins minna."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"Vinsamlega réttu úr höfðinu."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"Ekki hafa neitt milli höfuðsins og símans."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"Hreinsaðu myndavélina."</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"Andlit ekki staðfest. Vélbúnaður er ekki tiltækur."</string>
diff --git a/core/res/res/values-it/strings.xml b/core/res/res/values-it/strings.xml
index 28d1a7f97743..67a36d11cf6d 100644
--- a/core/res/res/values-it/strings.xml
+++ b/core/res/res/values-it/strings.xml
@@ -278,7 +278,7 @@
<string name="permgrouplab_contacts" msgid="3657758145679177612">"Contatti"</string>
<string name="permgroupdesc_contacts" msgid="6951499528303668046">"accedere ai contatti"</string>
<string name="permgrouprequest_contacts" msgid="6032805601881764300">"Consentire all\'app &lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; di accedere ai tuoi contatti?"</string>
- <string name="permgrouplab_location" msgid="7275582855722310164">"Geolocalizzazione"</string>
+ <string name="permgrouplab_location" msgid="7275582855722310164">"Geolocalizz."</string>
<string name="permgroupdesc_location" msgid="1346617465127855033">"accedere alla posizione di questo dispositivo"</string>
<string name="permgrouprequest_location" msgid="3788275734953323491">"Consentire all\'app &lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; di accedere alla posizione di questo dispositivo?"</string>
<string name="permgrouprequestdetail_location" msgid="1347189607421252902">"L\'app avrà accesso alla posizione soltanto quando la usi"</string>
@@ -302,8 +302,8 @@
<string name="permgrouplab_camera" msgid="4820372495894586615">"Fotocamera"</string>
<string name="permgroupdesc_camera" msgid="3250611594678347720">"scattare foto e registrare video"</string>
<string name="permgrouprequest_camera" msgid="1299833592069671756">"Consentire all\'app &lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; di scattare foto e registrare video?"</string>
- <string name="permgrouplab_calllog" msgid="8798646184930388160">"Registri chiamate"</string>
- <string name="permgroupdesc_calllog" msgid="3006237336748283775">"leggere e scrivere il registro chiamate del telefono"</string>
+ <string name="permgrouplab_calllog" msgid="8798646184930388160">"Log chiamate"</string>
+ <string name="permgroupdesc_calllog" msgid="3006237336748283775">"leggere e modificare il registro chiamate del telefono"</string>
<string name="permgrouprequest_calllog" msgid="8487355309583773267">"Consentire all\'app &lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; di accedere ai registri chiamate del tuo telefono?"</string>
<string name="permgrouplab_phone" msgid="5229115638567440675">"Telefono"</string>
<string name="permgroupdesc_phone" msgid="6234224354060641055">"eseguire e gestire le telefonate"</string>
@@ -571,13 +571,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"Ripeti l\'acquisizione del volto."</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"Non è più possibile riconoscere il volto. Riprova."</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"Troppo simile; cambia posa."</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"Gira un po\' meno la testa."</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"Gira un po\' meno la testa."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"Raddrizza la testa in verticale."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"Libera lo spazio tra la tua testa e il telefono."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"Pulisci la fotocamera."</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"Imposs. verificare volto. Hardware non disponibile."</string>
diff --git a/core/res/res/values-iw/strings.xml b/core/res/res/values-iw/strings.xml
index 473bcd5b4193..fe481a47cea2 100644
--- a/core/res/res/values-iw/strings.xml
+++ b/core/res/res/values-iw/strings.xml
@@ -577,13 +577,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"יש לרשום מחדש את הפנים."</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"כבר לא ניתן לזהות פנים. יש לנסות שוב."</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"דומה מדי, יש לשנות תנוחה."</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"עליך ליישר קצת את הראש."</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"עליך ליישר קצת את הראש."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"יש ליישר את הראש במאונך."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"הפנים שלך צריכים להיות גלויים לגמרי."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"צריך לנקות את המצלמה."</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"לא ניתן לאמת את הפנים. החומרה לא זמינה."</string>
diff --git a/core/res/res/values-ja/strings.xml b/core/res/res/values-ja/strings.xml
index b01f1148810d..9660a3748938 100644
--- a/core/res/res/values-ja/strings.xml
+++ b/core/res/res/values-ja/strings.xml
@@ -227,7 +227,7 @@
<string name="global_action_emergency" msgid="7112311161137421166">"緊急通報"</string>
<string name="global_action_bug_report" msgid="7934010578922304799">"バグレポート"</string>
<string name="global_action_logout" msgid="935179188218826050">"セッションを終了"</string>
- <string name="global_action_screenshot" msgid="8329831278085426283">"スクリーンショット"</string>
+ <string name="global_action_screenshot" msgid="8329831278085426283">"画面の保存"</string>
<string name="bugreport_title" msgid="5981047024855257269">"バグレポート"</string>
<string name="bugreport_message" msgid="398447048750350456">"現在のデバイスの状態に関する情報が収集され、その内容がメールで送信されます。バグレポートが開始してから送信可能な状態となるまでには多少の時間がかかりますのでご了承ください。"</string>
<string name="bugreport_option_interactive_title" msgid="8635056131768862479">"対話型レポート"</string>
@@ -571,13 +571,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"顔を登録し直してください。"</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"顔を認識できなくなりました。もう一度お試しください。"</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"似すぎています。ポーズを変えてください。"</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"顔の向きを少し戻してください。"</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"顔の向きを少し戻してください。"</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"頭を左右に傾けず、まっすぐにしてください。"</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"顔とスマートフォンの間に何も置かないでください。"</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"カメラの汚れを拭き取ってください。"</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"顔を確認できません。ハードウェアを利用できません。"</string>
diff --git a/core/res/res/values-ka/strings.xml b/core/res/res/values-ka/strings.xml
index 8de2c007f644..1e4eba005088 100644
--- a/core/res/res/values-ka/strings.xml
+++ b/core/res/res/values-ka/strings.xml
@@ -571,13 +571,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"გთხოვთ, ხელახლა დაარეგისტრიროთ თქვენი სახე."</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"სახის ამოცნობა ვეღარ ხერხდება. ცადეთ ხელახლა."</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"მეტისმეტად მსგავსია. გთხოვთ, შეცვალოთ პოზა."</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"თავი ცოტა ნაკლებად მიაბრუნეთ."</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"თავი ცოტა ნაკლებად მიაბრუნეთ."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"გთხოვთ, ვერტიკალურად გაასწოროთ თავი."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"გაათავისუფლეთ სივრცე თავსა და ტელეფონს შორის."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"გაწმინდეთ კამერა."</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"სახე ვერ დასტურდება. აპარატი მიუწვდომელია."</string>
diff --git a/core/res/res/values-kk/strings.xml b/core/res/res/values-kk/strings.xml
index 035dc3fd7e76..17b92da51826 100644
--- a/core/res/res/values-kk/strings.xml
+++ b/core/res/res/values-kk/strings.xml
@@ -304,7 +304,7 @@
<string name="permgrouprequest_camera" msgid="1299833592069671756">"&lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; қолданбасына суретке түсіруге және бейне жазуға рұқсат берілсін бе?"</string>
<string name="permgrouplab_calllog" msgid="8798646184930388160">"Қоңырау журналдары"</string>
<string name="permgroupdesc_calllog" msgid="3006237336748283775">"телефонның қоңыраулар журналын оқу және жазу"</string>
- <string name="permgrouprequest_calllog" msgid="8487355309583773267">"&lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; қолданбасына телефонның қоңыраулар журналына кіруге рұқсат етілсін бе?"</string>
+ <string name="permgrouprequest_calllog" msgid="8487355309583773267">"&lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; қолданбасына телефонның қоңыраулар журналына кіруге рұқсат берілсін бе?"</string>
<string name="permgrouplab_phone" msgid="5229115638567440675">"Телефон"</string>
<string name="permgroupdesc_phone" msgid="6234224354060641055">"қоңырау шалу және телефон қоңырауларын басқару"</string>
<string name="permgrouprequest_phone" msgid="9166979577750581037">"&lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; қолданбасына қоңыраулар шалуға және басқаруға рұқсат берілсін бе?"</string>
@@ -575,9 +575,12 @@
<skip />
<!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"Басыңызды тік ұстаңыз."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"Бетіңіз бен телефон арасында ештеңе тұрмауы керек."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"Камераны тазалаңыз."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
+ <skip />
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
+ <skip />
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"Бетті тану мүмкін емес. Жабдық қолжетімді емес."</string>
@@ -1598,7 +1601,7 @@
<string name="wireless_display_route_description" msgid="9070346425023979651">"Сымсыз дисплей"</string>
<string name="media_route_button_content_description" msgid="591703006349356016">"Трансляциялау"</string>
<string name="media_route_chooser_title" msgid="1751618554539087622">"Құрылғыға жалғау"</string>
- <string name="media_route_chooser_title_for_remote_display" msgid="3395541745872017583">"Экранды құрылғымен байланыстыру"</string>
+ <string name="media_route_chooser_title_for_remote_display" msgid="3395541745872017583">"Экран трансляциясы"</string>
<string name="media_route_chooser_searching" msgid="4776236202610828706">"Құрылғыларды іздеуде…"</string>
<string name="media_route_chooser_extended_settings" msgid="87015534236701604">"Параметрлер"</string>
<string name="media_route_controller_disconnect" msgid="8966120286374158649">"Ажырату"</string>
diff --git a/core/res/res/values-km/strings.xml b/core/res/res/values-km/strings.xml
index fb66cb0cfeea..67c7c27ec40d 100644
--- a/core/res/res/values-km/strings.xml
+++ b/core/res/res/values-km/strings.xml
@@ -571,13 +571,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"សូម​​ស្កេន​បញ្ចូល​មុខរបស់អ្នក​ម្ដងទៀត។"</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"មិន​អាច​សម្គាល់មុខ​បាន​ទៀតទេ។ សូមព្យាយាមម្ដងទៀត។"</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"ស្រដៀងគ្នា​ពេក សូមផ្លាស់ប្ដូរ​កាយវិការ​របស់អ្នក។"</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"ងាកក្បាល​របស់អ្នក​បន្តិចទៀត។"</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"ងាកក្បាល​របស់អ្នក​បន្តិចទៀត។"</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"សូម​ងើយ​ក្បាល​របស់អ្នកឱ្យត្រង់។"</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"កុំឱ្យមានអ្វីបាំងនៅចន្លោះក្បាល និងទូរសព្ទរបស់អ្នក។"</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"សូមសម្អាតកាមេរ៉ា។"</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"មិនអាច​ផ្ទៀងផ្ទាត់​មុខបានទេ។ មិនមាន​ហាតវែរទេ។"</string>
@@ -1599,7 +1600,7 @@
<string name="wireless_display_route_description" msgid="9070346425023979651">"បង្ហាញ​បណ្ដាញ​ឥត​ខ្សែ"</string>
<string name="media_route_button_content_description" msgid="591703006349356016">"បញ្ជូន"</string>
<string name="media_route_chooser_title" msgid="1751618554539087622">"ភ្ជាប់​ឧបករណ៍"</string>
- <string name="media_route_chooser_title_for_remote_display" msgid="3395541745872017583">"ខាស​អេក្រង់​ទៅ​ឧបករណ៍"</string>
+ <string name="media_route_chooser_title_for_remote_display" msgid="3395541745872017583">"ភ្ជាប់អេក្រង់​ទៅ​ឧបករណ៍"</string>
<string name="media_route_chooser_searching" msgid="4776236202610828706">"កំពុង​ស្វែងរក​ឧបករណ៍..."</string>
<string name="media_route_chooser_extended_settings" msgid="87015534236701604">"ការ​កំណត់"</string>
<string name="media_route_controller_disconnect" msgid="8966120286374158649">"ផ្ដាច់"</string>
diff --git a/core/res/res/values-kn/strings.xml b/core/res/res/values-kn/strings.xml
index 98cc303eff9d..ffb02d8ac3d4 100644
--- a/core/res/res/values-kn/strings.xml
+++ b/core/res/res/values-kn/strings.xml
@@ -571,13 +571,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"ನಿಮ್ಮ ಮುಖವನ್ನು ಮರುನೋಂದಣಿ ಮಾಡಿ."</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"ಮುಖ ಗುರುತಿಸಲು ಸಾಧ್ಯವಾಗುವುದಿಲ್ಲ. ಪುನಃ ಪ್ರಯತ್ನಿಸಿ."</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"ತುಂಬಾ ಸಮಾನ, ನಿಮ್ಮ ಪೋಸ್ ಬದಲಾಯಿಸಿ."</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"ನಿಮ್ಮ ತಲೆಯನ್ನು ಹೆಚ್ಚು ತಿರುಗಿಸಬೇಡಿ."</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"ನಿಮ್ಮ ತಲೆಯನ್ನು ಹೆಚ್ಚು ತಿರುಗಿಸಬೇಡಿ."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"ನಿಮ್ಮ ತಲೆಯನ್ನು ವರ್ಟಿಕಲ್‌ ಆಗಿ ನೇರವಾಗಿಸಿ."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"ನಿಮ್ಮ ತಲೆ ಮತ್ತು ಫೋನ್ ನಡುವಿನ ಅಡಚಣೆಯನ್ನು ತೆರವುಗೊಳಿಸಿ"</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"ಕ್ಯಾಮರಾವನ್ನು ಸ್ವಚ್ಛಗೊಳಿಸಿ."</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"ಮುಖ ದೃಢೀಕರಿಸಲು ಸಾಧ್ಯವಿಲ್ಲ. ಹಾರ್ಡ್‌ವೇರ್ ಲಭ್ಯವಿಲ್ಲ."</string>
@@ -1598,7 +1599,7 @@
<string name="wireless_display_route_description" msgid="9070346425023979651">"ವಯರ್‌ಲೆಸ್ ಪ್ರದರ್ಶನ"</string>
<string name="media_route_button_content_description" msgid="591703006349356016">"ಪಾತ್ರ"</string>
<string name="media_route_chooser_title" msgid="1751618554539087622">"ಸಾಧನಕ್ಕೆ ಸಂಪರ್ಕಿಸಿ"</string>
- <string name="media_route_chooser_title_for_remote_display" msgid="3395541745872017583">"ಸಾಧನಕ್ಕೆ ಬಿತ್ತರಿಸುವ ಪರದೆ"</string>
+ <string name="media_route_chooser_title_for_remote_display" msgid="3395541745872017583">"ಪರದೆಯನ್ನು ಸಾಧನದಲ್ಲಿ ಬಿತ್ತರಿಸಿ"</string>
<string name="media_route_chooser_searching" msgid="4776236202610828706">"ಸಾಧನಗಳನ್ನು ಹುಡುಕಲಾಗುತ್ತಿದೆ…"</string>
<string name="media_route_chooser_extended_settings" msgid="87015534236701604">"ಸೆಟ್ಟಿಂಗ್‌ಗಳು"</string>
<string name="media_route_controller_disconnect" msgid="8966120286374158649">"ಸಂಪರ್ಕ ಕಡಿತಗೊಳಿಸು"</string>
diff --git a/core/res/res/values-ko/strings.xml b/core/res/res/values-ko/strings.xml
index 20a26d33c0a0..072a365438cf 100644
--- a/core/res/res/values-ko/strings.xml
+++ b/core/res/res/values-ko/strings.xml
@@ -304,7 +304,7 @@
<string name="permgrouprequest_camera" msgid="1299833592069671756">"&lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt;에서 사진을 촬영하고 동영상을 녹화하도록 허용하시겠습니까?"</string>
<string name="permgrouplab_calllog" msgid="8798646184930388160">"통화 기록"</string>
<string name="permgroupdesc_calllog" msgid="3006237336748283775">"통화 기록 읽고 쓰기"</string>
- <string name="permgrouprequest_calllog" msgid="8487355309583773267">"&lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt;이(가) 통화 기록에 액세스하도록 허용하시겠습니까?"</string>
+ <string name="permgrouprequest_calllog" msgid="8487355309583773267">"&lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt;에서 통화 기록에 액세스하도록 허용하시겠습니까?"</string>
<string name="permgrouplab_phone" msgid="5229115638567440675">"전화"</string>
<string name="permgroupdesc_phone" msgid="6234224354060641055">"전화 걸기 및 관리"</string>
<string name="permgrouprequest_phone" msgid="9166979577750581037">"&lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt;에서 전화를 걸고 관리하도록 허용하시겠습니까?"</string>
@@ -571,13 +571,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"얼굴을 다시 등록해 주세요."</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"더 이상 얼굴을 인식할 수 없습니다. 다시 시도하세요."</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"너무 비슷합니다. 다른 포즈를 취해 보세요."</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"고개를 조금 덜 돌려 보세요."</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"고개를 조금 덜 돌려 보세요."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"고개를 똑바로 세워 주세요."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"얼굴과 휴대전화 사이의 공간을 비워두세요."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"카메라의 이물질을 제거하세요."</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"얼굴을 확인할 수 없습니다. 하드웨어를 사용할 수 없습니다."</string>
diff --git a/core/res/res/values-ky/strings.xml b/core/res/res/values-ky/strings.xml
index 9c4366da8761..ad03d79f6016 100644
--- a/core/res/res/values-ky/strings.xml
+++ b/core/res/res/values-ky/strings.xml
@@ -87,7 +87,7 @@
<string name="NetworkPreferenceSwitchSummary" msgid="509327194863482733">"Тандалган тармакты өзгөртүп көрүңүз. Өзгөртүү үчүн таптаңыз."</string>
<string name="EmergencyCallWarningTitle" msgid="813380189532491336">"Шашылыш чалуу жеткиликсиз"</string>
<string name="EmergencyCallWarningSummary" msgid="1899692069750260619">"Wi-Fi аркылуу шашылыш чалуулар иштетилген жок"</string>
- <string name="notification_channel_network_alert" msgid="4427736684338074967">"Эскертүүлөр"</string>
+ <string name="notification_channel_network_alert" msgid="4427736684338074967">"Шашылыш билдирүүлөр"</string>
<string name="notification_channel_call_forward" msgid="2419697808481833249">"Чалууну башка номерге багыттоо"</string>
<string name="notification_channel_emergency_callback" msgid="6686166232265733921">"Шашылыш кайра чалуу режими"</string>
<string name="notification_channel_mobile_data_status" msgid="4575131690860945836">"Мобилдик Интернеттин абалы"</string>
@@ -262,7 +262,7 @@
<string name="notification_channel_network_available" msgid="4531717914138179517">"Жеткиликтүү тармактар"</string>
<string name="notification_channel_vpn" msgid="8330103431055860618">"VPN абалы"</string>
<string name="notification_channel_device_admin" msgid="1568154104368069249">"Түзмөктү администрациялоо"</string>
- <string name="notification_channel_alerts" msgid="4496839309318519037">"Эскертүүлөр"</string>
+ <string name="notification_channel_alerts" msgid="4496839309318519037">"Шашылыш билдирүүлөр"</string>
<string name="notification_channel_retail_mode" msgid="6088920674914038779">"Чекене соода дүкөнү үчүн демо режим"</string>
<string name="notification_channel_usb" msgid="9006850475328924681">"USB аркылуу туташуу"</string>
<string name="notification_channel_heavy_weight_app" msgid="6218742927792852607">"Колдонмо иштеп жатат"</string>
@@ -295,19 +295,19 @@
<string name="permgrouprequest_storage" msgid="7885942926944299560">"&lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; колдонмосуна түзмөгүңүздөгү сүрөттөрдү жана башка мультимедиа файлдарын пайдаланууга уруксат бересизби?"</string>
<string name="permgrouplab_microphone" msgid="171539900250043464">"Микрофон"</string>
<string name="permgroupdesc_microphone" msgid="4988812113943554584">"аудио жаздыруу"</string>
- <string name="permgrouprequest_microphone" msgid="9167492350681916038">"&lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; колдонмосуна аудио файлдарды жаздырууга уруксат берилсинби?"</string>
+ <string name="permgrouprequest_microphone" msgid="9167492350681916038">"&lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; колдонмосуна аудио файлдарды жазганга уруксат бересизби?"</string>
<string name="permgrouplab_activityRecognition" msgid="1565108047054378642">"Кыймыл-аракет"</string>
<string name="permgroupdesc_activityRecognition" msgid="6949472038320473478">"кыймыл-аракетиңизге мүмкүнчүлүк алат"</string>
<string name="permgrouprequest_activityRecognition" msgid="7626438016904799383">"&lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; колдонмосуна кыймыл-аракетиңизге мүмкүнчүлүк бересизби?"</string>
<string name="permgrouplab_camera" msgid="4820372495894586615">"Камера"</string>
<string name="permgroupdesc_camera" msgid="3250611594678347720">"сүрөт жана видео тартууга"</string>
- <string name="permgrouprequest_camera" msgid="1299833592069671756">"&lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; колдонмосуна сүрөттөрдү тартып, видеолорду жаздырууга уруксат берилсинби?"</string>
+ <string name="permgrouprequest_camera" msgid="1299833592069671756">"&lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; колдонмосуна сүрөттөр менен видеолорду тартканга уруксат бересизби?"</string>
<string name="permgrouplab_calllog" msgid="8798646184930388160">"Чалуулар тизмелери"</string>
<string name="permgroupdesc_calllog" msgid="3006237336748283775">"телефондогу чалуулар тизмесин окуу жана жазуу"</string>
<string name="permgrouprequest_calllog" msgid="8487355309583773267">"&lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; колдонмосуна телефондогу чалуулар тизмесин пайдаланууга уруксат берилсинби?"</string>
<string name="permgrouplab_phone" msgid="5229115638567440675">"Телефон"</string>
<string name="permgroupdesc_phone" msgid="6234224354060641055">"телефон чалуу жана аларды башкаруу"</string>
- <string name="permgrouprequest_phone" msgid="9166979577750581037">"&lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; колдонмосуна телефон чалууга жана чалууларды башкарууга уруксат берилсинби?"</string>
+ <string name="permgrouprequest_phone" msgid="9166979577750581037">"&lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; колдонмосуна телефон чалууга жана чалууларды башкарууга уруксат бересизби?"</string>
<string name="permgrouplab_sensors" msgid="4838614103153567532">"Дене сенсорлору"</string>
<string name="permgroupdesc_sensors" msgid="7147968539346634043">"организмдин абалына көз салган сенсордун дайындарына мүмкүнчүлүк алуу"</string>
<string name="permgrouprequest_sensors" msgid="6349806962814556786">"&lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; колдонмосуна организмдин абалына көз салган сенсордун көрсөткүчтөрүн көрүүгө уруксат бересизби?"</string>
@@ -548,7 +548,7 @@
<string name="fingerprint_name_template" msgid="5870957565512716938">"<xliff:g id="FINGERID">%d</xliff:g>-манжа"</string>
<string-array name="fingerprint_error_vendor">
</string-array>
- <string name="fingerprint_icon_content_description" msgid="2340202869968465936">"Манжа изинин сөлөкөтү"</string>
+ <string name="fingerprint_icon_content_description" msgid="2340202869968465936">"Манжа изинин сүрөтчөсү"</string>
<string name="permlab_manageFace" msgid="2137540986007309781">"жүздүн аныктыгын текшерүүчү аппараттык камсыздоону башкаруу"</string>
<string name="permdesc_manageFace" msgid="8919637120670185330">"Колдонмого пайдалануу үчүн жүздүн үлгүлөрүн кошуу жана жок кылуу мүмкүндүгүн берет."</string>
<string name="permlab_useFaceAuthentication" msgid="8996134460546804535">"жүздүн аныктыгын текшерүүчү аппараттык камсыздоону колдонуу"</string>
@@ -575,9 +575,12 @@
<skip />
<!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"Башыңызды түз кармаңыз."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"Башыңыз менен телефондун ортосу бош болушу керек."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"Камераны тазалаңыз."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
+ <skip />
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
+ <skip />
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"Жүз ырасталбай жатат. Аппараттык камсыздоо жеткиликсиз."</string>
@@ -1599,7 +1602,7 @@
<string name="wireless_display_route_description" msgid="9070346425023979651">"Зымсыз дисплей"</string>
<string name="media_route_button_content_description" msgid="591703006349356016">"Тышкы экранга чыгаруу"</string>
<string name="media_route_chooser_title" msgid="1751618554539087622">"Түзмөккө туташуу"</string>
- <string name="media_route_chooser_title_for_remote_display" msgid="3395541745872017583">"Сырткы экранга чыгаруу"</string>
+ <string name="media_route_chooser_title_for_remote_display" msgid="3395541745872017583">"Тышкы экранга чыгаруу"</string>
<string name="media_route_chooser_searching" msgid="4776236202610828706">"Түзмөктөр изделүүдө..."</string>
<string name="media_route_chooser_extended_settings" msgid="87015534236701604">"Жөндөөлөр"</string>
<string name="media_route_controller_disconnect" msgid="8966120286374158649">"Ажыратуу"</string>
diff --git a/core/res/res/values-lo/strings.xml b/core/res/res/values-lo/strings.xml
index ae5d9705845f..d30159906d99 100644
--- a/core/res/res/values-lo/strings.xml
+++ b/core/res/res/values-lo/strings.xml
@@ -575,9 +575,12 @@
<skip />
<!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"ກະລຸນາຍັບຫົວຂອງທ່ານໃຫ້ຊື່ຕາມລວງຕັ້ງ."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"ເຄລຍພື້ນທີ່ລະຫວ່າງຫົວ ແລະ ໂທລະສັບຂອງທ່ານ."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"ກະລຸນາທຳຄວາມສະອາດກ້ອງ."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
+ <skip />
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
+ <skip />
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"ບໍ່ສາມາດຢັ້ງຢືນໃບໜ້າໄດ້. ບໍ່ມີຮາດແວໃຫ້ໃຊ້."</string>
diff --git a/core/res/res/values-lt/strings.xml b/core/res/res/values-lt/strings.xml
index 277d824e820c..28ce6edacd72 100644
--- a/core/res/res/values-lt/strings.xml
+++ b/core/res/res/values-lt/strings.xml
@@ -577,13 +577,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"Užregistruokite veidą iš naujo."</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"Nebegalima atpažinti veido. Bandykite dar kartą."</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"Per daug panašu, pakeiskite veido išraišką."</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"Nesukite tiek galvos."</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"Nesukite tiek galvos."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"Laikykite galvą vertikaliai."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"Nieko negali būti tarp galvos ir telefono."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"Nuvalykite fotoaparatą."</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"Nepavyko patv. veido. Aparatinė įranga negalima."</string>
diff --git a/core/res/res/values-lv/strings.xml b/core/res/res/values-lv/strings.xml
index 2be11ca3278f..888e637e062d 100644
--- a/core/res/res/values-lv/strings.xml
+++ b/core/res/res/values-lv/strings.xml
@@ -574,13 +574,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"Lūdzu, atkārtoti reģistrējiet savu seju."</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"Seju vairs nevar atpazīt. Mēģiniet vēlreiz."</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"Pārāk līdzīgi. Lūdzu, mainiet pozu."</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"Pagrieziet galvu nedaudz mazāk."</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"Pagrieziet galvu nedaudz mazāk."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"Lūdzu, vertikāli iztaisnojiet galvu."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"Atbrīvojiet vietu starp savu galvu un tālruni."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"Lūdzu, notīriet kameru."</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"Nevar verificēt seju. Aparatūra nav pieejama."</string>
diff --git a/core/res/res/values-mk/strings.xml b/core/res/res/values-mk/strings.xml
index 8e64959df547..8db6305eec43 100644
--- a/core/res/res/values-mk/strings.xml
+++ b/core/res/res/values-mk/strings.xml
@@ -571,13 +571,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"Повторно регистрирајте го лицето."</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"Ликот не се препознава. Обидете се повторно."</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"Премногу слично, сменете ја позата."</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"Не вртете ја главата толку многу."</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"Не вртете ја главата толку многу."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"Исправете ја главата вертикално."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"Исчистете го просторот меѓу главата и телефонот"</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"Исчистете ја камерата."</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"Ликот не може да се потврди. Хардвер - недостапен."</string>
@@ -1601,7 +1602,7 @@
<string name="media_route_button_content_description" msgid="591703006349356016">"Емитувај"</string>
<string name="media_route_chooser_title" msgid="1751618554539087622">"Поврзи се со уред"</string>
<string name="media_route_chooser_title_for_remote_display" msgid="3395541745872017583">"Префрли екран на уред"</string>
- <string name="media_route_chooser_searching" msgid="4776236202610828706">"Пребарување за уреди..."</string>
+ <string name="media_route_chooser_searching" msgid="4776236202610828706">"Се бараат уреди..."</string>
<string name="media_route_chooser_extended_settings" msgid="87015534236701604">"Поставки"</string>
<string name="media_route_controller_disconnect" msgid="8966120286374158649">"Исклучи"</string>
<string name="media_route_status_scanning" msgid="7279908761758293783">"Скенирање..."</string>
diff --git a/core/res/res/values-ml/strings.xml b/core/res/res/values-ml/strings.xml
index 79ab0fbb7422..c09330b0b87e 100644
--- a/core/res/res/values-ml/strings.xml
+++ b/core/res/res/values-ml/strings.xml
@@ -571,13 +571,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"നിങ്ങളുടെ മുഖം വീണ്ടും എൻറോൾ ചെയ്യുക."</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"ഇനി മുഖം തിരിച്ചറിയാനാവില്ല. വീണ്ടും ശ്രമിക്കൂ."</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"വളരെയധികം സമാനത, നിങ്ങളുടെ പോസ് മാറ്റുക."</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"നിങ്ങളുടെ തല ഇത്ര തിരിക്കേണ്ട."</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"നിങ്ങളുടെ തല ഇത്ര തിരിക്കേണ്ട."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"നിങ്ങളുടെ തല ലംബമായി നേരെയാക്കുക"</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"തലയ്ക്കും ഫോണിനുമിടയിലുള്ള തടസ്സം നീക്കുക."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"ക്യാമറ വൃത്തിയാക്കുക."</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"മുഖം പരിശോധിക്കാൻ കഴിയില്ല. ഹാർഡ്‌വെയർ ലഭ്യമല്ല."</string>
diff --git a/core/res/res/values-mn/strings.xml b/core/res/res/values-mn/strings.xml
index 5fc96ce01acd..11dbc522803b 100644
--- a/core/res/res/values-mn/strings.xml
+++ b/core/res/res/values-mn/strings.xml
@@ -571,13 +571,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"Нүүрээ дахин бүртгүүлнэ үү."</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"Царайг таних боломжгүй боллоо. Дахин оролдоно уу."</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"Хэт адилхан байгаа тул байрлалаа өөрчилнө үү."</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"Толгойгоо арай багаар эргүүлнэ үү."</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"Толгойгоо арай багаар эргүүлнэ үү."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"Толгойгоо босоо чиглэлд тэгшилнэ үү."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"Толгой болон утасныхаа хоорондох зайг тохируулна уу."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"Камераа цэвэрлэнэ үү."</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"Царайг бататгаж чадсангүй. Техник хангамж боломжгүй байна."</string>
diff --git a/core/res/res/values-mr/strings.xml b/core/res/res/values-mr/strings.xml
index 3c1323ac9338..73c42f184de1 100644
--- a/core/res/res/values-mr/strings.xml
+++ b/core/res/res/values-mr/strings.xml
@@ -571,13 +571,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"कृपया तुमच्या चेहऱ्याची पुन्हा नोंदणी करा."</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"चेहरा ओळखू शकत नाही. पुन्हा प्रयत्न करा."</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"एकाच प्रकारची पोझ देत आहात कृपया तुमची पोझ बदला."</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"तुमचे डोके थोडे कमी फिरवा."</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"तुमचे डोके थोडे कमी फिरवा."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"कृपया तुमची मान वर करा."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"तुमचे डोके आणि फोन यांमधली जागा मोकळी करा."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"कृपया कॅमेरा साफ करा."</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"चेहरा पडताळू शकत नाही. हार्डवेअर उपलब्ध नाही."</string>
@@ -1121,7 +1122,7 @@
<string name="no" msgid="5141531044935541497">"रद्द करा"</string>
<string name="dialog_alert_title" msgid="2049658708609043103">"लक्ष द्या"</string>
<string name="loading" msgid="7933681260296021180">"लोड करत आहे..."</string>
- <string name="capital_on" msgid="1544682755514494298">"चालू"</string>
+ <string name="capital_on" msgid="1544682755514494298">"सुरू"</string>
<string name="capital_off" msgid="6815870386972805832">"बंद"</string>
<string name="whichApplication" msgid="4533185947064773386">"याचा वापर करून क्रिया पूर्ण करा"</string>
<string name="whichApplicationNamed" msgid="8260158865936942783">"%1$s वापरून क्रिया पूर्ण करा"</string>
@@ -1599,7 +1600,7 @@
<string name="media_route_button_content_description" msgid="591703006349356016">"कास्‍ट करा"</string>
<string name="media_route_chooser_title" msgid="1751618554539087622">"डिव्हाइसला कनेक्ट करा"</string>
<string name="media_route_chooser_title_for_remote_display" msgid="3395541745872017583">"डिव्‍हाइसवर स्क्रीन कास्‍ट करा"</string>
- <string name="media_route_chooser_searching" msgid="4776236202610828706">"डिव्‍हाइसेस शोधत आहे…"</string>
+ <string name="media_route_chooser_searching" msgid="4776236202610828706">"डिव्‍हाइस शोधत आहे…"</string>
<string name="media_route_chooser_extended_settings" msgid="87015534236701604">"सेटिंग्ज"</string>
<string name="media_route_controller_disconnect" msgid="8966120286374158649">"‍डिस्कनेक्ट करा"</string>
<string name="media_route_status_scanning" msgid="7279908761758293783">"स्कॅन करत आहे..."</string>
@@ -1805,7 +1806,7 @@
<string name="battery_saver_description_with_learn_more" msgid="2108984221113106294">"बॅटरी लाइफ वाढवण्यासाठी बॅटरी सेव्हर बॅकग्राउंड अ‍ॅक्टिव्हिटी, काही व्हिज्युअल इफेक्ट आणि इतर हाय-पॉवर वैशिष्ट्ये बंद किंवा मर्यादित करतो. "<annotation id="url">"अधिक जाणून घ्या"</annotation></string>
<string name="battery_saver_description" msgid="6413346684861241431">"बॅटरी लाइफ वाढवण्यासाठी बॅटरी सेव्हर बॅकग्राउंड अ‍ॅक्टिव्हिटी, काही व्हिज्युअल इफेक्ट आणि इतर हाय-पॉवर वैशिष्ट्ये बंद किंवा मर्यादित करतो."</string>
<string name="data_saver_description" msgid="6015391409098303235">"डेटा वापर कमी करण्यात मदत करण्यासाठी, डेटा सर्व्हर काही अ‍ॅप्सना पार्श्वभूमीमध्ये डेटा पाठविण्यास किंवा मिळवण्यास प्रतिबंध करतो. तुम्ही सध्या वापरत असलेला अ‍ॅप डेटामध्ये प्रवेश करू शकतो परंतु तसे तो खूप कमी वेळा करू शकतो. याचा अर्थ, उदाहरणार्थ, तुम्ही इमेज टॅप करेपर्यंत त्या प्रदर्शित करणार नाहीत असा असू शकतो."</string>
- <string name="data_saver_enable_title" msgid="4674073932722787417">"डेटा बचतकर्ता चालू करायचा?"</string>
+ <string name="data_saver_enable_title" msgid="4674073932722787417">"डेटा सेव्हर चालू करायचा?"</string>
<string name="data_saver_enable_button" msgid="7147735965247211818">"चालू करा"</string>
<plurals name="zen_mode_duration_minutes_summary" formatted="false" msgid="4367877408072000848">
<item quantity="other">%1$d मिनिटांसाठी (<xliff:g id="FORMATTEDTIME_1">%2$s</xliff:g> पर्यंत)</item>
diff --git a/core/res/res/values-ms/strings.xml b/core/res/res/values-ms/strings.xml
index 0713e41312cb..76261b30b331 100644
--- a/core/res/res/values-ms/strings.xml
+++ b/core/res/res/values-ms/strings.xml
@@ -571,13 +571,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"Sila daftarkan semula wajah anda."</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"Tidak lagi dapat mengecam wajah. Cuba lagi."</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"Terlalu serupa, sila ubah lagak gaya anda."</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"Pusingkan kepala anda kurang sedikit."</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"Pusingkan kepala anda kurang sedikit."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"Sila tegakkan kepala anda."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"Kosongkan ruang di antara kepala anda dgn telefon."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"Sila bersihkan kamera."</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"Tdk dpt sahkan wajah. Perkakasan tidak tersedia."</string>
diff --git a/core/res/res/values-my/strings.xml b/core/res/res/values-my/strings.xml
index 6b41c14cc145..80a08383f18a 100644
--- a/core/res/res/values-my/strings.xml
+++ b/core/res/res/values-my/strings.xml
@@ -302,7 +302,7 @@
<string name="permgrouplab_camera" msgid="4820372495894586615">"ကင်မရာ"</string>
<string name="permgroupdesc_camera" msgid="3250611594678347720">"ဓာတ်ပုံ ရိုက်ပြီးနောက် ဗွီဒီယို မှတ်တမ်းတင်ရန်"</string>
<string name="permgrouprequest_camera" msgid="1299833592069671756">"&lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; အား ဓာတ်ပုံနှင့် ဗီဒီယိုရိုက်ကူးခွင့် ပေးလိုပါသလား။"</string>
- <string name="permgrouplab_calllog" msgid="8798646184930388160">"ခေါ်ဆိုထားသော မှတ်တမ်းများ"</string>
+ <string name="permgrouplab_calllog" msgid="8798646184930388160">"ခေါ်ဆိုမှတ်တမ်း"</string>
<string name="permgroupdesc_calllog" msgid="3006237336748283775">"ဖုန်းခေါ်ဆိုထားသော မှတ်တမ်း ဖတ်ပြီး ရေးရန်"</string>
<string name="permgrouprequest_calllog" msgid="8487355309583773267">"&lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; အား သင်၏ခေါ်ဆိုထားသော မှတ်တမ်းများကို သုံးခွင့်ပေးလိုပါသလား။"</string>
<string name="permgrouplab_phone" msgid="5229115638567440675">"ဖုန်း"</string>
@@ -571,13 +571,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"သင့်မျက်နှာကို ပြန်စာရင်းသွင်းပါ။"</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"မျက်နှာ မမှတ်သားနိုင်တော့ပါ။ ထပ်စမ်းကြည့်ပါ။"</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"ဆင်တူနေသည်၊ အမူအရာ ပြောင်းပါ။"</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"ခေါင်းကို သိပ်မလှည့်ပါနှင့်။"</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"ခေါင်းကို သိပ်မလှည့်ပါနှင့်။"</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"ခေါင်းမတ်မတ်ထားပါ။"</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"သင့်မျက်နှာနှင့် ဖုန်းအကြား ဘာမှကွယ်မထားပါနှင့်။"</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"ကင်မရာကို သန့်ရှင်းရေးလုပ်ပါ။"</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"မျက်နှာကို အတည်ပြု၍ မရပါ။ ဟာ့ဒ်ဝဲ မရနိုင်ပါ။"</string>
diff --git a/core/res/res/values-nb/strings.xml b/core/res/res/values-nb/strings.xml
index 1b9260adf525..ff02690a241d 100644
--- a/core/res/res/values-nb/strings.xml
+++ b/core/res/res/values-nb/strings.xml
@@ -296,7 +296,7 @@
<string name="permgrouplab_microphone" msgid="171539900250043464">"Mikrofon"</string>
<string name="permgroupdesc_microphone" msgid="4988812113943554584">"ta opp lyd"</string>
<string name="permgrouprequest_microphone" msgid="9167492350681916038">"Vil du la &lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; ta opp lyd?"</string>
- <string name="permgrouplab_activityRecognition" msgid="1565108047054378642">"Fysisk aktivitet"</string>
+ <string name="permgrouplab_activityRecognition" msgid="1565108047054378642">"Fysisk aktivitet-"</string>
<string name="permgroupdesc_activityRecognition" msgid="6949472038320473478">"tilgang til den fysiske aktiviteten din"</string>
<string name="permgrouprequest_activityRecognition" msgid="7626438016904799383">"Vil du gi &lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; tilgang til den fysiske aktiviteten din?"</string>
<string name="permgrouplab_camera" msgid="4820372495894586615">"Kamera"</string>
@@ -342,7 +342,7 @@
<string name="permlab_receiveMms" msgid="1821317344668257098">"motta tekstmeldinger (MMS)"</string>
<string name="permdesc_receiveMms" msgid="533019437263212260">"Lar appen motta og behandle multimediemeldinger. Dette betyr at appen kan overvåke eller slette meldinger som er sendt til enheten din uten at du har sett dem."</string>
<string name="permlab_readCellBroadcasts" msgid="1598328843619646166">"lese kringkastede meldinger"</string>
- <string name="permdesc_readCellBroadcasts" msgid="6361972776080458979">"Tillater at appen kan lese kringkastede meldinger enheten din mottar. Kringkastede varsler leveres noen steder for å advare deg om nødsituasjoner. Skadelige apper kan forstyrre ytelsen eller funksjonen til enheten din når en kringkastet nødmelding mottas."</string>
+ <string name="permdesc_readCellBroadcasts" msgid="6361972776080458979">"Tillater at appen kan lese kringkastede meldinger enheten din mottar. Kringkastede varsler leveres noen steder for å advare deg om nødssituasjoner. Skadelige apper kan forstyrre ytelsen eller funksjonen til enheten din når en kringkastet nødmelding mottas."</string>
<string name="permlab_subscribedFeedsRead" msgid="4756609637053353318">"lese abonnement på nyhetskilder"</string>
<string name="permdesc_subscribedFeedsRead" msgid="5557058907906144505">"Lar appen hente inn detaljer om strømmer som er synkroniserte for øyeblikket."</string>
<string name="permlab_sendSms" msgid="7544599214260982981">"sende og lese SMS-meldinger"</string>
@@ -571,13 +571,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"Registrer ansiktet ditt på nytt."</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"Kan ikke gjenkjenne ansiktet lenger. Prøv igjen."</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"For likt – endre posituren din."</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"Vri hodet ditt litt mindre."</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"Vri hodet ditt litt mindre."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"Rett hodet ditt vertikalt."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"Tøm området mellom hodet ditt og telefonen."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"Rengjør kameraet."</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"Kan ikke bekrefte ansikt. Utilgjengelig maskinvare."</string>
diff --git a/core/res/res/values-ne/strings.xml b/core/res/res/values-ne/strings.xml
index 0728c2214e2c..549441cfae7d 100644
--- a/core/res/res/values-ne/strings.xml
+++ b/core/res/res/values-ne/strings.xml
@@ -571,13 +571,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"कृपया आफ्नो अनुहार पुनः दर्ता गर्नुहोस्।"</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"अब उप्रान्त अनुहार पहिचान गर्न सकिएन। फेरि प्रयास गर्नुहोस्।"</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"अनुहार उस्तै भयो, कृपया आफ्नो पोज बदल्नुहोस्।"</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"आफ्नो टाउको अलि थोरै घुमाउनुहोस्।"</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"आफ्नो टाउको अलि थोरै घुमाउनुहोस्।"</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"कृपया आफ्नो अनुहार ठाडो रूपमा सीधा पार्नुहोस्।"</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"आफ्नो टाउको र फोनका बिचको स्थान हटाउनुहोस्।"</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"कृपया क्यामेरा सफा गर्नुहोस्।"</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"अनुहार पुष्टि गर्न सकिएन। हार्डवेयर उपलब्ध छैन।"</string>
diff --git a/core/res/res/values-nl/strings.xml b/core/res/res/values-nl/strings.xml
index 1adfa7fbb374..544d2265656b 100644
--- a/core/res/res/values-nl/strings.xml
+++ b/core/res/res/values-nl/strings.xml
@@ -302,9 +302,9 @@
<string name="permgrouplab_camera" msgid="4820372495894586615">"Camera"</string>
<string name="permgroupdesc_camera" msgid="3250611594678347720">"foto\'s maken en video opnemen"</string>
<string name="permgrouprequest_camera" msgid="1299833592069671756">"&lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; toestaan om foto\'s te maken en video op te nemen?"</string>
- <string name="permgrouplab_calllog" msgid="8798646184930388160">"Gesprekkenlijsten"</string>
- <string name="permgroupdesc_calllog" msgid="3006237336748283775">"gesprekkenlijst lezen en schrijven"</string>
- <string name="permgrouprequest_calllog" msgid="8487355309583773267">"&lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; toegang geven tot je gesprekkenlijsten?"</string>
+ <string name="permgrouplab_calllog" msgid="8798646184930388160">"Gesprekslijsten"</string>
+ <string name="permgroupdesc_calllog" msgid="3006237336748283775">"gesprekslijst lezen en schrijven"</string>
+ <string name="permgrouprequest_calllog" msgid="8487355309583773267">"&lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; toegang geven tot je gesprekslijsten?"</string>
<string name="permgrouplab_phone" msgid="5229115638567440675">"Telefoon"</string>
<string name="permgroupdesc_phone" msgid="6234224354060641055">"telefoneren en gesprekken beheren"</string>
<string name="permgrouprequest_phone" msgid="9166979577750581037">"&lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; toestaan om telefoongesprekken te starten en te beheren?"</string>
@@ -395,12 +395,12 @@
<string name="permdesc_writeContacts" product="tablet" msgid="897243932521953602">"Hiermee kan de app gegevens wijzigen over de contacten die zijn opgeslagen op je tablet, inclusief de frequentie waarmee je hebt gebeld, gemaild of op andere manieren hebt gecommuniceerd met specifieke contacten. Met deze toestemming kunnen apps contactgegevens verwijderen."</string>
<string name="permdesc_writeContacts" product="tv" msgid="5438230957000018959">"Hiermee kan de app gegevens wijzigen over de contacten die zijn opgeslagen op je tv, inclusief de frequentie waarmee je hebt gebeld, gemaild of op andere manieren hebt gecommuniceerd met specifieke contacten. Met deze toestemming kunnen apps contactgegevens verwijderen."</string>
<string name="permdesc_writeContacts" product="default" msgid="589869224625163558">"Hiermee kan de app gegevens wijzigen over de contacten die zijn opgeslagen op je telefoon, inclusief de frequentie waarmee je hebt gebeld, gemaild of op andere manieren hebt gecommuniceerd met specifieke contacten. Met deze toestemming kunnen apps contactgegevens verwijderen."</string>
- <string name="permlab_readCallLog" msgid="3478133184624102739">"gesprekkenlijst lezen"</string>
+ <string name="permlab_readCallLog" msgid="3478133184624102739">"gesprekslijst lezen"</string>
<string name="permdesc_readCallLog" msgid="3204122446463552146">"Deze app kan je gespreksgeschiedenis lezen."</string>
- <string name="permlab_writeCallLog" msgid="8552045664743499354">"gesprekkenlijst schrijven"</string>
- <string name="permdesc_writeCallLog" product="tablet" msgid="6661806062274119245">"Toestaan dat de app de gesprekkenlijst van je tablet aanpast, waaronder gegevens over inkomende en uitgaande gesprekken. Schadelijke apps kunnen hiermee je gesprekkenlijst wissen of aanpassen."</string>
- <string name="permdesc_writeCallLog" product="tv" msgid="4225034892248398019">"Toestaan dat de app de gesprekkenlijst van je tv aanpast, waaronder gegevens over inkomende en uitgaande gesprekken. Schadelijke apps kunnen hiermee je gesprekkenlijst wissen of aanpassen."</string>
- <string name="permdesc_writeCallLog" product="default" msgid="683941736352787842">"Toestaan dat de app de gesprekkenlijst van je telefoon aanpast, waaronder gegevens over inkomende en uitgaande gesprekken. Schadelijke apps kunnen hiermee je gesprekkenlijst wissen of aanpassen."</string>
+ <string name="permlab_writeCallLog" msgid="8552045664743499354">"gesprekslijst schrijven"</string>
+ <string name="permdesc_writeCallLog" product="tablet" msgid="6661806062274119245">"Toestaan dat de app de gesprekslijst van je tablet aanpast, waaronder gegevens over inkomende en uitgaande gesprekken. Schadelijke apps kunnen hiermee je gesprekslijst wissen of aanpassen."</string>
+ <string name="permdesc_writeCallLog" product="tv" msgid="4225034892248398019">"Toestaan dat de app de gesprekslijst van je tv aanpast, waaronder gegevens over inkomende en uitgaande gesprekken. Schadelijke apps kunnen hiermee je gesprekslijst wissen of aanpassen."</string>
+ <string name="permdesc_writeCallLog" product="default" msgid="683941736352787842">"Toestaan dat de app de gesprekslijst van je telefoon aanpast, waaronder gegevens over inkomende en uitgaande gesprekken. Schadelijke apps kunnen hiermee je gesprekslijst wissen of aanpassen."</string>
<string name="permlab_bodySensors" msgid="4683341291818520277">"toegang tot lichaamssensoren (zoals hartslagmeters)"</string>
<string name="permdesc_bodySensors" product="default" msgid="4380015021754180431">"Hiermee kan de app toegang krijgen tot gegevens van sensoren die je lichamelijke conditie controleren, zoals je hartslag."</string>
<string name="permlab_readCalendar" msgid="6716116972752441641">"Agenda-afspraken en -gegevens lezen"</string>
@@ -571,13 +571,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"Registreer je gezicht opnieuw."</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"Herkent gezicht niet meer. Probeer het nog eens."</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"Lijkt te veel op elkaar. Verander je pose."</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"Draai je hoofd iets minder."</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"Draai je hoofd iets minder."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"Houd je hoofd verticaal recht."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"Zorg dat er niks tussen je hoofd en telefoon zit."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"Maak de camera schoon."</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"Kan gezicht niet verifiëren. Hardware niet beschikbaar."</string>
diff --git a/core/res/res/values-or/strings.xml b/core/res/res/values-or/strings.xml
index 52309a2d718c..731f2d081677 100644
--- a/core/res/res/values-or/strings.xml
+++ b/core/res/res/values-or/strings.xml
@@ -571,13 +571,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"ଦୟାକରି ଆପଣଙ୍କର ମୁହଁ ପୁଣି-ଏନ୍‍ରୋଲ୍ କରନ୍ତୁ।"</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"ଆଉ ମୁହଁ ଚିହ୍ନଟ କରିହେଲା ନାହିଁ। ପୁଣି ଚେଷ୍ଟା କରନ୍ତୁ।"</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"ଅତ୍ୟନ୍ତ ସମପରି, ଦୟାକରି ଆପଣଙ୍କର ପୋଜ୍ ବଦଳାନ୍ତୁ।"</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"ଆପଣଙ୍କର ମୁଣ୍ଡକୁ ଟିକିଏ ବୁଲାନ୍ତୁ।"</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"ଆପଣଙ୍କର ମୁଣ୍ଡକୁ ଟିକିଏ ବୁଲାନ୍ତୁ।"</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"ଦୟାକରି ଆପଣଙ୍କର ମୁଣ୍ଡକୁ ସିଧା ରଖନ୍ତୁ।"</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"ଆପଣଙ୍କର ମୁଣ୍ଡ ଏବଂ ଫୋନ୍ ମଧ୍ୟରେ ଥିବା ସ୍ଥାନ କମ୍ କରନ୍ତୁ।"</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"ଦୟାକରି କ୍ୟାମେରାକୁ ସଫା କରନ୍ତୁ।"</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"ମୁହଁ ଚିହ୍ନଟ କରିପାରିଲା ନାହିଁ। ହାର୍ଡୱେୟାର୍ ଉପଲବ୍ଧ ନାହିଁ।"</string>
@@ -1220,7 +1221,7 @@
<string name="volume_music_hint_silent_ringtone_selected" msgid="8310739960973156272">"ରିଙ୍ଗଟୋନ୍‍‍କୁ ନିରବ ଭାବେ ସେଟ୍ କରାଯାଇଛି"</string>
<string name="volume_call" msgid="3941680041282788711">"ଇନ୍‍-କଲ୍‍ ଭଲ୍ୟୁମ୍‌"</string>
<string name="volume_bluetooth_call" msgid="2002891926351151534">"ବ୍ଲୁଟୂଥ୍‍ ଇନ୍-କଲ୍ ଭଲ୍ୟୁମ୍‌"</string>
- <string name="volume_alarm" msgid="1985191616042689100">"ଆଲାର୍ମର ଭଲ୍ୟୁମ୍‌"</string>
+ <string name="volume_alarm" msgid="1985191616042689100">"ଆଲାରାମ୍ ଭଲ୍ୟୁମ୍‌"</string>
<string name="volume_notification" msgid="2422265656744276715">"ବିଜ୍ଞପ୍ତି ଭଲ୍ୟୁମ୍‍"</string>
<string name="volume_unknown" msgid="1400219669770445902">"ଭଲ୍ୟୁମ୍"</string>
<string name="volume_icon_description_bluetooth" msgid="6538894177255964340">"ବ୍ଲୁଟୂଥ୍‍‍ ଭଲ୍ୟୁମ୍‍"</string>
@@ -1597,7 +1598,7 @@
<string name="wireless_display_route_description" msgid="9070346425023979651">"ୱେୟାର୍‍ଲେସ୍‍ ଡିସ୍‍ପ୍ଲେ"</string>
<string name="media_route_button_content_description" msgid="591703006349356016">"କାଷ୍ଟ କରନ୍ତୁ"</string>
<string name="media_route_chooser_title" msgid="1751618554539087622">"ଡିଭାଇସ୍‍ ସଂଯୋଗ କରନ୍ତୁ"</string>
- <string name="media_route_chooser_title_for_remote_display" msgid="3395541745872017583">"ଡିଭାଇସ୍‍ରେ ସ୍କ୍ରୀନ୍‍ କାଷ୍ଟ କରନ୍ତୁ"</string>
+ <string name="media_route_chooser_title_for_remote_display" msgid="3395541745872017583">"ଡିଭାଇସରେ ସ୍କ୍ରିନ୍‍ କାଷ୍ଟ କରନ୍ତୁ"</string>
<string name="media_route_chooser_searching" msgid="4776236202610828706">"ଡିଭାଇସ୍‍ ଖୋଜାଯାଉଛି…"</string>
<string name="media_route_chooser_extended_settings" msgid="87015534236701604">"ସେଟିଙ୍ଗ"</string>
<string name="media_route_controller_disconnect" msgid="8966120286374158649">"ବିଛିନ୍ନ କରନ୍ତୁ"</string>
@@ -1816,7 +1817,7 @@
</plurals>
<plurals name="zen_mode_duration_hours_summary" formatted="false" msgid="736789408293052283">
<item quantity="other">%1$d ଘଣ୍ଟା ପାଇଁ (<xliff:g id="FORMATTEDTIME_1">%2$s</xliff:g> ପର୍ଯ୍ୟନ୍ତ)</item>
- <item quantity="one">, 1 ଘଣ୍ଟା ପାଇଁ (<xliff:g id="FORMATTEDTIME_0">%2$s</xliff:g> ପର୍ଯ୍ୟନ୍ତ)</item>
+ <item quantity="one">1 ଘଣ୍ଟା ପାଇଁ (<xliff:g id="FORMATTEDTIME_0">%2$s</xliff:g> ପର୍ଯ୍ୟନ୍ତ)</item>
</plurals>
<plurals name="zen_mode_duration_hours_summary_short" formatted="false" msgid="4787552595253082371">
<item quantity="other">%1$d ଘଣ୍ଟା ପାଇଁ (<xliff:g id="FORMATTEDTIME_1">%2$s</xliff:g> ପର୍ଯ୍ୟନ୍ତ)</item>
@@ -1832,7 +1833,7 @@
</plurals>
<plurals name="zen_mode_duration_hours" formatted="false" msgid="6571961796799076730">
<item quantity="other">%d ଘଣ୍ଟା ପାଇଁ</item>
- <item quantity="one">, 1 ଘଣ୍ଟା ପାଇଁ</item>
+ <item quantity="one">1 ଘଣ୍ଟା ପାଇଁ</item>
</plurals>
<plurals name="zen_mode_duration_hours_short" formatted="false" msgid="6748277774662434217">
<item quantity="other">%d ଘଣ୍ଟା ପାଇଁ</item>
@@ -1886,7 +1887,7 @@
<string name="language_selection_title" msgid="2680677278159281088">"ଏକ ଭାଷା ଯୋଡ଼ନ୍ତୁ"</string>
<string name="country_selection_title" msgid="2954859441620215513">"ପସନ୍ଦର ଅଞ୍ଚଳ"</string>
<string name="search_language_hint" msgid="7042102592055108574">"ଭାଷାର ନାମ ଟାଇପ୍‍ କରନ୍ତୁ"</string>
- <string name="language_picker_section_suggested" msgid="8414489646861640885">"ପରାମର୍ଶିତ"</string>
+ <string name="language_picker_section_suggested" msgid="8414489646861640885">"ପ୍ରସ୍ତାବିତ"</string>
<string name="language_picker_section_all" msgid="3097279199511617537">"ସମସ୍ତ ଭାଷା"</string>
<string name="region_picker_section_all" msgid="8966316787153001779">"ସମସ୍ତ ଅଞ୍ଚଳ"</string>
<string name="locale_search_menu" msgid="2560710726687249178">"ସର୍ଚ୍ଚ କରନ୍ତୁ"</string>
diff --git a/core/res/res/values-pa/strings.xml b/core/res/res/values-pa/strings.xml
index 218df83ea971..33ad73d48f43 100644
--- a/core/res/res/values-pa/strings.xml
+++ b/core/res/res/values-pa/strings.xml
@@ -571,13 +571,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"ਕਿਰਪਾ ਕਰਕੇ ਆਪਣਾ ਚਿਹਰਾ ਦੁਬਾਰਾ ਦਰਜ ਕਰੋ।"</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"ਹੁਣ ਚਿਹਰਾ ਪਛਾਣਿਆ ਨਹੀਂ ਜਾ ਸਕਦਾ। ਦੁਬਾਰਾ ਕੋਸ਼ਿਸ਼ ਕਰੋ।"</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"ਬਹੁਤ ਮਿਲਦਾ-ਜੁਲਦਾ ਹੈ, ਕਿਰਪਾ ਕਰਕੇ ਆਪਣਾ ਅੰਦਾਜ਼ ਬਦਲੋ।"</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"ਆਪਣਾ ਸਿਰ ਥੋੜਾ ਜਿਹਾ ਝੁਕਾਓ।"</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"ਆਪਣਾ ਸਿਰ ਥੋੜਾ ਜਿਹਾ ਝੁਕਾਓ।"</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"ਕਿਰਪਾ ਕਰਕੇ ਆਪਣੇ ਸਿਰ ਨੂੰ ਸਿੱਧਾ ਖੜ੍ਹਵਾਂ ਰੱਖੋ।"</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"ਤੁਹਾਡੇ ਸਿਰ ਅਤੇ ਫ਼ੋਨ ਵਿਚਾਲੇ ਕੁਝ ਨਾ ਹੋਵੇ।"</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"ਕਿਰਪਾ ਕਰਕੇ ਕੈਮਰਾ ਸਾਫ਼ ਕਰੋ।"</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"ਚਿਹਰੇ ਦੀ ਪੁਸ਼ਟੀ ਨਹੀਂ ਹੋ ਸਕੀ। ਹਾਰਡਵੇਅਰ ਉਪਲਬਧ ਨਹੀਂ।"</string>
diff --git a/core/res/res/values-pl/strings.xml b/core/res/res/values-pl/strings.xml
index 09485e509547..b1b232567c66 100644
--- a/core/res/res/values-pl/strings.xml
+++ b/core/res/res/values-pl/strings.xml
@@ -577,13 +577,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"Zarejestruj swoją twarz ponownie."</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"Nie można już rozpoznać twarzy. Spróbuj ponownie."</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"Za mała różnica. Zmień pozycję."</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"Trochę mniej obróć głowę."</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"Trochę mniej obróć głowę."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"Wyprostuj głowę w pionie."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"Między telefonem a Twoją głową powinno być pusto."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"Wyczyść aparat."</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"Nie można zweryfikować twarzy. Sprzęt niedostępny."</string>
diff --git a/core/res/res/values-pt-rBR/strings.xml b/core/res/res/values-pt-rBR/strings.xml
index 9a64dd3d090b..5e7927d9f7a0 100644
--- a/core/res/res/values-pt-rBR/strings.xml
+++ b/core/res/res/values-pt-rBR/strings.xml
@@ -228,7 +228,7 @@
<string name="global_action_bug_report" msgid="7934010578922304799">"Relatório de bugs"</string>
<string name="global_action_logout" msgid="935179188218826050">"Finalizar sessão"</string>
<string name="global_action_screenshot" msgid="8329831278085426283">"Captura de tela"</string>
- <string name="bugreport_title" msgid="5981047024855257269">"Relatório do bug"</string>
+ <string name="bugreport_title" msgid="5981047024855257269">"Relatório de bug"</string>
<string name="bugreport_message" msgid="398447048750350456">"Isto coletará informações sobre o estado atual do dispositivo para enviá-las em uma mensagem de e-mail. Após iniciar o relatório de bugs, será necessário aguardar algum tempo até que esteja pronto para ser enviado."</string>
<string name="bugreport_option_interactive_title" msgid="8635056131768862479">"Relatório interativo"</string>
<string name="bugreport_option_interactive_summary" msgid="229299488536107968">"Use este recurso na maioria das circunstâncias. Ele permite que você acompanhe o progresso do relatório, informe mais detalhes sobre o problema e faça capturas de tela. É possível que ele omita algumas seções menos utilizadas que levam muito tempo na emissão dos relatórios."</string>
@@ -571,13 +571,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"Registre seu rosto novamente."</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"O rosto não é mais reconhecido. Tente novamente."</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"Muito parecido, mude de posição."</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"Incline a cabeça um pouco menos."</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"Incline a cabeça um pouco menos."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"Alinhe sua cabeça na vertical."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"Libere espaço entre a cabeça e o smartphone."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"Limpe a câmera."</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"Impossível verificar rosto. Hardware indisponível."</string>
diff --git a/core/res/res/values-pt-rPT/strings.xml b/core/res/res/values-pt-rPT/strings.xml
index ac30215a7d8d..09f181f96ed9 100644
--- a/core/res/res/values-pt-rPT/strings.xml
+++ b/core/res/res/values-pt-rPT/strings.xml
@@ -571,13 +571,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"Volte a inscrever o rosto."</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"Impossível reconhecer o rosto. Tente novamente."</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"Muito parecida, mude de pose."</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"Rode a cabeça um pouco menos."</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"Rode a cabeça um pouco menos."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"Endireite a cabeça na vertical."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"Desimpeça o espaço entre a cabeça e o telemóvel."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"Limpe a câmara."</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"Não pode validar o rosto. Hardware não disponível."</string>
diff --git a/core/res/res/values-pt/strings.xml b/core/res/res/values-pt/strings.xml
index 9a64dd3d090b..5e7927d9f7a0 100644
--- a/core/res/res/values-pt/strings.xml
+++ b/core/res/res/values-pt/strings.xml
@@ -228,7 +228,7 @@
<string name="global_action_bug_report" msgid="7934010578922304799">"Relatório de bugs"</string>
<string name="global_action_logout" msgid="935179188218826050">"Finalizar sessão"</string>
<string name="global_action_screenshot" msgid="8329831278085426283">"Captura de tela"</string>
- <string name="bugreport_title" msgid="5981047024855257269">"Relatório do bug"</string>
+ <string name="bugreport_title" msgid="5981047024855257269">"Relatório de bug"</string>
<string name="bugreport_message" msgid="398447048750350456">"Isto coletará informações sobre o estado atual do dispositivo para enviá-las em uma mensagem de e-mail. Após iniciar o relatório de bugs, será necessário aguardar algum tempo até que esteja pronto para ser enviado."</string>
<string name="bugreport_option_interactive_title" msgid="8635056131768862479">"Relatório interativo"</string>
<string name="bugreport_option_interactive_summary" msgid="229299488536107968">"Use este recurso na maioria das circunstâncias. Ele permite que você acompanhe o progresso do relatório, informe mais detalhes sobre o problema e faça capturas de tela. É possível que ele omita algumas seções menos utilizadas que levam muito tempo na emissão dos relatórios."</string>
@@ -571,13 +571,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"Registre seu rosto novamente."</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"O rosto não é mais reconhecido. Tente novamente."</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"Muito parecido, mude de posição."</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"Incline a cabeça um pouco menos."</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"Incline a cabeça um pouco menos."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"Alinhe sua cabeça na vertical."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"Libere espaço entre a cabeça e o smartphone."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"Limpe a câmera."</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"Impossível verificar rosto. Hardware indisponível."</string>
diff --git a/core/res/res/values-ro/strings.xml b/core/res/res/values-ro/strings.xml
index ddeb4e8f912f..0e4c0bafd753 100644
--- a/core/res/res/values-ro/strings.xml
+++ b/core/res/res/values-ro/strings.xml
@@ -574,13 +574,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"Reînregistrați-vă chipul."</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"Nu se mai poate recunoaște fața. Încercați din nou."</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"Prea asemănător, schimbați poziția."</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"Întoarceți capul mai puțin."</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"Întoarceți capul mai puțin."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"Îndreptați capul pe verticală."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"Eliberați spațiul dintre cap și telefon."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"Curățați camera foto."</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"Nu se poate confirma fața. Hardware-ul nu este disponibil."</string>
diff --git a/core/res/res/values-ru/strings.xml b/core/res/res/values-ru/strings.xml
index 311cf11ca212..8c96363aa8bc 100644
--- a/core/res/res/values-ru/strings.xml
+++ b/core/res/res/values-ru/strings.xml
@@ -232,7 +232,7 @@
<string name="global_action_bug_report" msgid="7934010578922304799">"Отчет об ошибке"</string>
<string name="global_action_logout" msgid="935179188218826050">"Закончить сеанс"</string>
<string name="global_action_screenshot" msgid="8329831278085426283">"Скриншот"</string>
- <string name="bugreport_title" msgid="5981047024855257269">"Сообщение об ошибке"</string>
+ <string name="bugreport_title" msgid="5981047024855257269">"Отчет об ошибке"</string>
<string name="bugreport_message" msgid="398447048750350456">"Информация о текущем состоянии вашего устройства будет собрана и отправлена по электронной почте. Подготовка отчета займет некоторое время."</string>
<string name="bugreport_option_interactive_title" msgid="8635056131768862479">"Интерактивный отчет"</string>
<string name="bugreport_option_interactive_summary" msgid="229299488536107968">"Рекомендуем этот вариант в большинстве случаев, чтобы отслеживать статус отчета, указывать дополнительные данные о проблеме и делать скриншоты. Некоторые разделы могут быть исключены, чтобы сократить время подготовки отчета."</string>
@@ -577,13 +577,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"Повторите попытку."</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"Не удалось распознать лицо. Повторите попытку."</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"Слишком похожее выражение лица. Измените позу."</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"Держите голову ровнее."</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"Держите голову ровнее."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"Выровняйте голову по вертикали."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"Лицо не должно быть ничем закрыто."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"Протрите камеру."</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"Не удалось распознать лицо. Сканер недоступен."</string>
diff --git a/core/res/res/values-si/strings.xml b/core/res/res/values-si/strings.xml
index a6dd5bb5828c..90d351819f68 100644
--- a/core/res/res/values-si/strings.xml
+++ b/core/res/res/values-si/strings.xml
@@ -571,13 +571,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"ඔබේ මුහුණ යළි ලියාපදිංචි කරන්න."</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"තවදුරටත් මුහුණ හඳුනාගත නොහැක. නැවත උත්සාහ කරන්න."</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"ඉතා සමානයි, ඔබේ හැඩ ගැසීම වෙනස් කරන්න."</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"ඔබේ හිස ටිකක් අඩුවෙන් කරකවන්න."</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"ඔබේ හිස ටිකක් අඩුවෙන් කරකවන්න."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"ඔබේ හිස සිරස් ආකාරයේ කෙළින් කරන්න."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"ඔබේ හිස සහ දුරකථනය අතර ඉඩ ඉවත් කරන්න."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"කැමරාව පිරිසිදු කරන්න."</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"මුහුණ සත්‍යාපනය කළ නොහැක. දෘඩාංගය නොමැත."</string>
diff --git a/core/res/res/values-sk/strings.xml b/core/res/res/values-sk/strings.xml
index 438eea154590..44192984c4a4 100644
--- a/core/res/res/values-sk/strings.xml
+++ b/core/res/res/values-sk/strings.xml
@@ -78,7 +78,7 @@
<string name="CLIRDefaultOffNextCallOn" msgid="6179425182856418465">"V predvolenom nastavení nie je identifikácia volajúceho obmedzená. Ďalší hovor: Obmedzené"</string>
<string name="CLIRDefaultOffNextCallOff" msgid="2567998633124408552">"V predvolenom nastavení nie je identifikácia volajúceho obmedzená. Ďalší hovor: Bez obmedzenia"</string>
<string name="serviceNotProvisioned" msgid="8614830180508686666">"Služba nie je poskytovaná."</string>
- <string name="CLIRPermanent" msgid="3377371145926835671">"Nemôžete meniť nastavenia identifikácie volajúceho."</string>
+ <string name="CLIRPermanent" msgid="3377371145926835671">"Nemôžete meniť nastavenie identifikácie volajúcich."</string>
<string name="RestrictedOnDataTitle" msgid="5221736429761078014">"Žiadna mobilná dátová služba"</string>
<string name="RestrictedOnEmergencyTitle" msgid="6855466023161191166">"Tiesňové volania nie sú k dispozícii"</string>
<string name="RestrictedOnNormalTitle" msgid="3179574012752700984">"Žiadne hlasové hovory"</string>
@@ -308,9 +308,9 @@
<string name="permgrouplab_camera" msgid="4820372495894586615">"Fotoaparát"</string>
<string name="permgroupdesc_camera" msgid="3250611594678347720">"fotenie a natáčanie videí"</string>
<string name="permgrouprequest_camera" msgid="1299833592069671756">"Povoliť aplikácii &lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; snímať fotky a zaznamenávať video?"</string>
- <string name="permgrouplab_calllog" msgid="8798646184930388160">"Denníky hovorov"</string>
- <string name="permgroupdesc_calllog" msgid="3006237336748283775">"čítanie a zapisovanie do denníka hovorov telefónu"</string>
- <string name="permgrouprequest_calllog" msgid="8487355309583773267">"Povoliť aplikácii &lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; prístup k denníku hovorov telefónu?"</string>
+ <string name="permgrouplab_calllog" msgid="8798646184930388160">"Zoznam hovorov"</string>
+ <string name="permgroupdesc_calllog" msgid="3006237336748283775">"čítať a zapisovať do zoznamu hovorov"</string>
+ <string name="permgrouprequest_calllog" msgid="8487355309583773267">"Povoliť aplikácii &lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; prístup k zoznamu hovorov?"</string>
<string name="permgrouplab_phone" msgid="5229115638567440675">"Telefón"</string>
<string name="permgroupdesc_phone" msgid="6234224354060641055">"telefonovanie a správu hovorov"</string>
<string name="permgrouprequest_phone" msgid="9166979577750581037">"Povoliť aplikácii &lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; uskutočňovať a spravovať telefonické hovory?"</string>
@@ -406,7 +406,7 @@
<string name="permlab_writeCallLog" msgid="8552045664743499354">"zapisovať do denníka hovorov"</string>
<string name="permdesc_writeCallLog" product="tablet" msgid="6661806062274119245">"Umožňuje aplikácii upravovať denník hovorov vo vašom tablete vrátane údajov o prichádzajúcich a odchádzajúcich hovoroch. Škodlivé aplikácie to môžu zneužiť na vymazanie alebo úpravu vášho denníka hovorov."</string>
<string name="permdesc_writeCallLog" product="tv" msgid="4225034892248398019">"Umožňuje aplikácii upravovať denník hovorov vo vašom televízore vrátane údajov o prichádzajúcich a odchádzajúcich hovoroch. Škodlivé aplikácie to môžu zneužiť na vymazanie alebo úpravu vášho denníka hovorov."</string>
- <string name="permdesc_writeCallLog" product="default" msgid="683941736352787842">"Umožňuje aplikácii upravovať denník hovorov vo vašom telefóne vrátane údajov o prichádzajúcich a odchádzajúcich hovoroch. Škodlivé aplikácie to môžu zneužiť na vymazanie alebo úpravu vášho denníka hovorov."</string>
+ <string name="permdesc_writeCallLog" product="default" msgid="683941736352787842">"Umožňuje aplikácii upravovať zoznam hovorov vo vašom telefóne vrátane údajov o prichádzajúcich a odchádzajúcich hovoroch. Škodlivé aplikácie to môžu zneužiť na vymazanie alebo úpravu vášho zoznamu hovorov."</string>
<string name="permlab_bodySensors" msgid="4683341291818520277">"prístup k telesným senzorom (ako sú snímače tepu)"</string>
<string name="permdesc_bodySensors" product="default" msgid="4380015021754180431">"Umožňuje aplikácii získať prístup k údajom senzorov monitorujúcich vašu fyzickú kondíciu (napríklad pulz)."</string>
<string name="permlab_readCalendar" msgid="6716116972752441641">"Čítanie udalostí kalendára a podrobností"</string>
@@ -577,13 +577,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"Znova zaregistrujte svoju tvár."</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"Tvár už nie je možné rozpoznať. Skúste to znova."</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"Príliš rovnaké, zmeňte postoj."</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"Otočte hlavu o niečo menej."</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"Otočte hlavu o niečo menej."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"Zvisle vyrovnajte hlavu."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"Odstráňte prekážky medzi vašou hlavou a telefónom."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"Vyčistite fotoaparát."</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"Tvár sa nedá overiť. Hardvér nie je k dispozícii."</string>
diff --git a/core/res/res/values-sl/strings.xml b/core/res/res/values-sl/strings.xml
index 431672c4a5d3..242754099355 100644
--- a/core/res/res/values-sl/strings.xml
+++ b/core/res/res/values-sl/strings.xml
@@ -231,7 +231,7 @@
<string name="global_action_emergency" msgid="7112311161137421166">"Klic v sili"</string>
<string name="global_action_bug_report" msgid="7934010578922304799">"Poročilo o napakah"</string>
<string name="global_action_logout" msgid="935179188218826050">"Končaj sejo"</string>
- <string name="global_action_screenshot" msgid="8329831278085426283">"Posnetek zaslona"</string>
+ <string name="global_action_screenshot" msgid="8329831278085426283">"Posnetek"</string>
<string name="bugreport_title" msgid="5981047024855257269">"Poročilo o napakah"</string>
<string name="bugreport_message" msgid="398447048750350456">"S tem bodo zbrani podatki o trenutnem stanju naprave, ki bodo poslani v e-poštnem sporočilu. Izvedba poročila o napakah in priprava trajata nekaj časa, zato bodite potrpežljivi."</string>
<string name="bugreport_option_interactive_title" msgid="8635056131768862479">"Interaktivno poročilo"</string>
@@ -577,13 +577,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"Znova prijavite svoj obraz."</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"Obraza ni več mogoče prepoznati. Poskusite znova."</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"Preveč podobno, spremenite položaj."</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"Glejte malce bolj naravnost."</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"Malce manj nagnite glavo."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"Zravnajte glavo."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"Povečajte razmik med glavo in telefonom."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"Očistite fotoaparat."</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"Obraza ni mogoče preveriti. Str. opr. ni na voljo."</string>
diff --git a/core/res/res/values-sq/strings.xml b/core/res/res/values-sq/strings.xml
index 3c0a3e94d288..6946113df9d9 100644
--- a/core/res/res/values-sq/strings.xml
+++ b/core/res/res/values-sq/strings.xml
@@ -304,7 +304,7 @@
<string name="permgrouprequest_camera" msgid="1299833592069671756">"Të lejohet që &lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; të nxjerrë fotografi dhe të regjistrojë video?"</string>
<string name="permgrouplab_calllog" msgid="8798646184930388160">"Evidencat e telefonatave"</string>
<string name="permgroupdesc_calllog" msgid="3006237336748283775">"lexo dhe shkruaj evidencën e telefonatave"</string>
- <string name="permgrouprequest_calllog" msgid="8487355309583773267">"Të &lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; të ketë qasje në evidencat e tua të telefonatave?"</string>
+ <string name="permgrouprequest_calllog" msgid="8487355309583773267">"Të lejohet &lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; të ketë qasje në evidencat e tua të telefonatave?"</string>
<string name="permgrouplab_phone" msgid="5229115638567440675">"Telefoni"</string>
<string name="permgroupdesc_phone" msgid="6234224354060641055">"kryej dhe menaxho telefonata"</string>
<string name="permgrouprequest_phone" msgid="9166979577750581037">"Të lejohet që &lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; të kryejë dhe të menaxhojë telefonata?"</string>
@@ -571,13 +571,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"Regjistroje përsëri fytyrën tënde."</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"Fytyra nuk mund të njihet më. Provo përsëri."</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"Tepër e ngjashme, ndrysho pozën"</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"Ktheje kokën pak më pak."</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"Ktheje kokën pak më pak."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"Drejtoje kokën vertikalisht"</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"Pastroje hapësirën mes kokës sate dhe telefonit."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"Pastro kamerën."</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"Fytyra s\'mund të verifikohet. Hardueri nuk ofrohet."</string>
diff --git a/core/res/res/values-sr/strings.xml b/core/res/res/values-sr/strings.xml
index 963335a88fb7..7767cffe1b07 100644
--- a/core/res/res/values-sr/strings.xml
+++ b/core/res/res/values-sr/strings.xml
@@ -574,13 +574,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"Поново региструјте лице."</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"Више не може да се препозна лице. Пробајте поново."</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"Превише је слично, промените позу."</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"Мало мање померите главу."</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"Мало мање померите главу."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"Исправите главу."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"Ослободите простор између главе и телефона."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"Очистите камеру."</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"Провера лица није успела. Хардвер није доступан."</string>
diff --git a/core/res/res/values-sv/strings.xml b/core/res/res/values-sv/strings.xml
index c95b4cdde2bf..471295268b6c 100644
--- a/core/res/res/values-sv/strings.xml
+++ b/core/res/res/values-sv/strings.xml
@@ -571,13 +571,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"Registrera ansiktet på nytt."</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"Ansiktet kan inte längre kännas igen. Försök igen."</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"För likt. Ändra ansiktsposition."</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"Vrid mindre på huvudet."</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"Vrid mindre på huvudet."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"Räta på huvudet vertikalt."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"Se till att ditt ansikte inte skyms för mobilen."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"Rengör kameran."</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"Ansiktsverifiering går ej. Otillgänglig maskinvara."</string>
diff --git a/core/res/res/values-sw/strings.xml b/core/res/res/values-sw/strings.xml
index 0fc125d6abb7..e08a9f93e32c 100644
--- a/core/res/res/values-sw/strings.xml
+++ b/core/res/res/values-sw/strings.xml
@@ -304,7 +304,7 @@
<string name="permgrouprequest_camera" msgid="1299833592069671756">"Ungependa kuruhusu &lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; kupiga picha na kurekodi video?"</string>
<string name="permgrouplab_calllog" msgid="8798646184930388160">"Rekodi ya nambari za simu"</string>
<string name="permgroupdesc_calllog" msgid="3006237336748283775">"kusoma na kuandika rekodi ya nambari za simu"</string>
- <string name="permgrouprequest_calllog" msgid="8487355309583773267">"Ungependa kuruhusu &lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; ifikie rekodi zako za nambari za simu?"</string>
+ <string name="permgrouprequest_calllog" msgid="8487355309583773267">"Ungependa kuiruhusu &lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; ifikie rekodi zako za nambari za simu?"</string>
<string name="permgrouplab_phone" msgid="5229115638567440675">"Simu"</string>
<string name="permgroupdesc_phone" msgid="6234224354060641055">"piga na udhibiti simu"</string>
<string name="permgrouprequest_phone" msgid="9166979577750581037">"Ungependa kuiruhusu &lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; ipige na kudhibiti simu?"</string>
@@ -571,13 +571,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"Tafadhali sajili uso wako tena."</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"Haiwezi tena kutambua uso. Jaribu tena."</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"Inafanana sana, tafadhali badilisha mkao wako."</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"Geuza kichwa chako kidogo."</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"Geuza kichwa chako kidogo."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"Tafadhali simamisha kichwa chako wima."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"Safisha nafasi iliyo kati ya kichwa chako na simu."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"Tafadhali safisha kamera."</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"Imeshindwa kuthibitisha uso. Maunzi hayapatikani."</string>
diff --git a/core/res/res/values-ta/strings.xml b/core/res/res/values-ta/strings.xml
index 38b3b4659f52..9d9f28066541 100644
--- a/core/res/res/values-ta/strings.xml
+++ b/core/res/res/values-ta/strings.xml
@@ -466,9 +466,9 @@
<string name="permdesc_setTimeZone" product="tv" msgid="888864653946175955">"டிவியின் நேர மண்டலத்தை மாற்ற, ஆப்ஸை அனுமதிக்கிறது."</string>
<string name="permdesc_setTimeZone" product="default" msgid="4499943488436633398">"மொபைலின் நேர மண்டலத்தை மாற்ற, ஆப்ஸை அனுமதிக்கிறது."</string>
<string name="permlab_getAccounts" msgid="1086795467760122114">"சாதனத்தில் கணக்குகளைக் கண்டறிதல்"</string>
- <string name="permdesc_getAccounts" product="tablet" msgid="2741496534769660027">"டேப்லெட் மூலம் அறியப்பட்ட கணக்குகளின் பட்டியலைப் பெற ஆப்ஸை அனுமதிக்கிறது. நீங்கள் நிறுவிய பயன்பாடுகள் மூலம் உருவாக்கப்பட்ட எல்லா கணக்குகளும் இதில் உள்ளடங்கலாம்."</string>
+ <string name="permdesc_getAccounts" product="tablet" msgid="2741496534769660027">"டேப்லெட் மூலம் அறியப்பட்ட கணக்குகளின் பட்டியலைப் பெற ஆப்ஸை அனுமதிக்கிறது. நீங்கள் நிறுவிய ஆப்ஸ் மூலம் உருவாக்கப்பட்ட எல்லா கணக்குகளும் இதில் உள்ளடங்கலாம்."</string>
<string name="permdesc_getAccounts" product="tv" msgid="4190633395633907543">"டிவி அறிந்த கணக்குகளின் பட்டியலைப் பெற, ஆப்ஸை அனுமதிக்கிறது. இதில் நிறுவிய பயன்பாடுகளினால் உருவாக்கப்பட்ட எல்லா கணக்குகளும் அடங்கலாம்."</string>
- <string name="permdesc_getAccounts" product="default" msgid="3448316822451807382">"மொபைல் மூலம் அறியப்பட்ட கணக்குகளின் பட்டியலைப் பெற ஆப்ஸை அனுமதிக்கிறது. நீங்கள் நிறுவிய பயன்பாடுகள் மூலம் உருவாக்கப்பட்ட எல்லா கணக்குகளும் இதில் உள்ளடங்கலாம்."</string>
+ <string name="permdesc_getAccounts" product="default" msgid="3448316822451807382">"மொபைல் மூலம் அறியப்பட்ட கணக்குகளின் பட்டியலைப் பெற ஆப்ஸை அனுமதிக்கிறது. நீங்கள் நிறுவிய ஆப்ஸ் மூலம் உருவாக்கப்பட்ட எல்லா கணக்குகளும் இதில் உள்ளடங்கலாம்."</string>
<string name="permlab_accessNetworkState" msgid="4951027964348974773">"நெட்வொர்க் இணைப்புகளைக் காட்டு"</string>
<string name="permdesc_accessNetworkState" msgid="8318964424675960975">"தற்போது இருக்கும் நெட்வொர்க்குகள் எவை மற்றும் இணைக்கப்பட்டுள்ளவை எவை போன்ற நெட்வொர்க் இணைப்புகள் குறித்த தகவலைப் பார்க்கப் ஆப்ஸை அனுமதிக்கிறது."</string>
<string name="permlab_createNetworkSockets" msgid="7934516631384168107">"முழுமையான நெட்வொர்க் அணுகலைக் கொண்டிருக்கும்"</string>
@@ -553,12 +553,9 @@
<string name="permdesc_manageFace" msgid="8919637120670185330">"உபயோகிப்பதற்காக முக டெம்ப்ளேட்டுகளை சேர்க்கும்/நீக்கும் முறைகளை இயக்க, ஆப்ஸை அனுமதிக்கும்."</string>
<string name="permlab_useFaceAuthentication" msgid="8996134460546804535">"முக அங்கீகாரத்திற்கான வன்பொருளைப் பயன்படுத்துதல்"</string>
<string name="permdesc_useFaceAuthentication" msgid="5011118722951833089">"அடையாளம் காண்பதற்கு, முக அங்கீகார வன்பொருளைப் பயன்படுத்த ஆப்ஸை அனுமதிக்கிறது"</string>
- <!-- no translation found for face_recalibrate_notification_name (3976629945250435054) -->
- <skip />
- <!-- no translation found for face_recalibrate_notification_title (4087620069451499365) -->
- <skip />
- <!-- no translation found for face_recalibrate_notification_content (5530308842361499835) -->
- <skip />
+ <string name="face_recalibrate_notification_name" msgid="3976629945250435054">"முக அங்கீகாரம்"</string>
+ <string name="face_recalibrate_notification_title" msgid="4087620069451499365">"முகத்தை மீண்டும் பதிவுசெய்யவும்"</string>
+ <string name="face_recalibrate_notification_content" msgid="5530308842361499835">"அடையாளத்தை மேம்படுத்த முகத்தை மீண்டும் பதிவுசெய்யவும்"</string>
<string name="face_acquired_insufficient" msgid="2767330364802375742">"முகம் தெளிவாகப் பதிவாகவில்லை. மீண்டும் முயலவும்."</string>
<string name="face_acquired_too_bright" msgid="5005650874582450967">"அதிக ஒளிர்வு. மிதமான ஒளியில் முயலவும்."</string>
<string name="face_acquired_too_dark" msgid="1966194696381394616">"இருட்டாக உள்ளது. பிரகாசமான ஒளியில் முயலவும்."</string>
@@ -578,9 +575,12 @@
<skip />
<!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"உங்கள் தலையை நேராக வைக்கவும்."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"முகத்திற்கும் மொபைலுக்குமான இடைவெளியை குறைக்கவும்."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"கேமராவைத் துடைக்கவும்"</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
+ <skip />
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
+ <skip />
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"முகத்தைச் சரிபார்க்க இயலவில்லை. வன்பொருள் இல்லை."</string>
@@ -1911,7 +1911,7 @@
<string name="profile_encrypted_message" msgid="6964994232310195874">"பணிக் கணக்கை திறக்க, தட்டுக"</string>
<string name="usb_mtp_launch_notification_title" msgid="8359219638312208932">"<xliff:g id="PRODUCT_NAME">%1$s</xliff:g> உடன் இணைக்கப்பட்டது"</string>
<string name="usb_mtp_launch_notification_description" msgid="8541876176425411358">"கோப்புகளைப் பார்க்க, தட்டவும்"</string>
- <string name="app_info" msgid="6856026610594615344">"பயன்பாட்டுத் தகவல்"</string>
+ <string name="app_info" msgid="6856026610594615344">"ஆப்ஸ் தகவல்"</string>
<string name="negative_duration" msgid="5688706061127375131">"−<xliff:g id="TIME">%1$s</xliff:g>"</string>
<string name="demo_starting_message" msgid="5268556852031489931">"டெமோவைத் தொடங்குகிறது…"</string>
<string name="demo_restarting_message" msgid="952118052531642451">"சாதனத்தை மீட்டமைக்கிறது…"</string>
@@ -2033,5 +2033,5 @@
<item quantity="one"><xliff:g id="FILE_NAME_0">%s</xliff:g> + <xliff:g id="COUNT_1">%d</xliff:g> ஃபைல்</item>
</plurals>
<string name="chooser_no_direct_share_targets" msgid="997970693708458895">"நேரடிப் பகிர்வு இல்லை"</string>
- <string name="chooser_all_apps_button_label" msgid="3631524352936289457">"பயன்பாடுகளின் பட்டியல்"</string>
+ <string name="chooser_all_apps_button_label" msgid="3631524352936289457">"ஆப்ஸ் பட்டியல்"</string>
</resources>
diff --git a/core/res/res/values-te/strings.xml b/core/res/res/values-te/strings.xml
index 1a5c702da91a..cc6583f4a5b5 100644
--- a/core/res/res/values-te/strings.xml
+++ b/core/res/res/values-te/strings.xml
@@ -571,13 +571,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"దయచేసి మీ ముఖాన్ని మళ్లీ నమోదు చేయండి."</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"ఇక ముఖం గుర్తించలేదు. మళ్లీ ప్రయత్నించండి."</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"ఒకే మాదిరిగా ఉంది, దయచేసి భంగిమను మార్చండి."</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"మీ తలను ఇంకాస్త తక్కువ తిప్పండి."</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"మీ తలను ఇంకాస్త తక్కువ తిప్పండి."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"దయచేసి మీ తలను నిలువుగా, నిటారుగా ఉంచండి."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"మీ తలకు, ఫోన్‌కు మధ్యన ఏదీ లేదని నిర్దారించుకోండి."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"దయచేసి కెమెరాను శుభ్రం చేయండి."</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"ముఖం ధృవీకరించలేరు. హార్డ్‌వేర్ అందుబాటులో లేదు."</string>
diff --git a/core/res/res/values-th/strings.xml b/core/res/res/values-th/strings.xml
index 52ea48ca7057..3fd84e7378c4 100644
--- a/core/res/res/values-th/strings.xml
+++ b/core/res/res/values-th/strings.xml
@@ -571,13 +571,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"โปรดลงทะเบียนใบหน้าอีกครั้ง"</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"จำใบหน้าไม่ได้แล้ว ลองอีกครั้ง"</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"ใกล้เคียงเกินไป โปรดเปลี่ยนท่าโพส"</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"จัดตำแหน่งศีรษะให้ตรง"</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"จัดตำแหน่งศีรษะให้ตรง"</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"โปรดตั้งศีรษะให้ตรง"</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"ดูว่าไม่มีสิ่งใดขวางระหว่างใบหน้าและโทรศัพท์"</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"โปรดทำความสะอาดกล้อง"</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"ยืนยันใบหน้าไม่ได้ ฮาร์ดแวร์ไม่พร้อมใช้งาน"</string>
@@ -1597,7 +1598,7 @@
<string name="wireless_display_route_description" msgid="9070346425023979651">"การแสดงผลแบบไร้สาย"</string>
<string name="media_route_button_content_description" msgid="591703006349356016">"แคสต์"</string>
<string name="media_route_chooser_title" msgid="1751618554539087622">"เชื่อมต่อกับอุปกรณ์"</string>
- <string name="media_route_chooser_title_for_remote_display" msgid="3395541745872017583">"ส่งหน้าจอไปยังอุปกรณ์"</string>
+ <string name="media_route_chooser_title_for_remote_display" msgid="3395541745872017583">"แคสต์หน้าจอไปยังอุปกรณ์"</string>
<string name="media_route_chooser_searching" msgid="4776236202610828706">"กำลังค้นหาอุปกรณ์…"</string>
<string name="media_route_chooser_extended_settings" msgid="87015534236701604">"การตั้งค่า"</string>
<string name="media_route_controller_disconnect" msgid="8966120286374158649">"ยกเลิกการเชื่อมต่อ"</string>
diff --git a/core/res/res/values-tl/strings.xml b/core/res/res/values-tl/strings.xml
index c326250578e9..c01937b275d6 100644
--- a/core/res/res/values-tl/strings.xml
+++ b/core/res/res/values-tl/strings.xml
@@ -571,13 +571,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"Paki-enroll muli ang iyong mukha."</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"Hindi na makilala ang mukha. Subukang muli."</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"Masyadong magkatulad, pakibago ang pose mo."</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"Huwag masyadong lumingon."</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"Huwag masyadong tumingala o yumuko."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"Pakituwid ang iyong mukha."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"Alisin ang nasa pagitan ng ulo mo at ng telepono."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"Pakilinis ang camera."</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"Di ma-verify ang mukha. Di available ang hardware."</string>
diff --git a/core/res/res/values-tr/strings.xml b/core/res/res/values-tr/strings.xml
index 9f92288086a0..72cd38993c6e 100644
--- a/core/res/res/values-tr/strings.xml
+++ b/core/res/res/values-tr/strings.xml
@@ -571,13 +571,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"Lütfen yüzünüzü yeniden kaydedin."</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"Yüz artık tanınamıyor. Tekrar deneyin."</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"Duruşunuz çok benzer, lütfen pozunuzu değiştirin."</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"Başınızı biraz daha az çevirin."</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"Başınızı biraz daha az çevirin."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"Lütfen başınızı tam dik olacak şekilde tutun."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"Başınız ve telefon arasındaki engelleri ortadan kaldırın."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"Lütfen kamerayı temizleyin."</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"Yüz doğrulanamıyor. Donanım kullanılamıyor."</string>
diff --git a/core/res/res/values-uk/strings.xml b/core/res/res/values-uk/strings.xml
index b469cdd362cb..2914281e9a46 100644
--- a/core/res/res/values-uk/strings.xml
+++ b/core/res/res/values-uk/strings.xml
@@ -296,7 +296,7 @@
<string name="permgrouplab_sms" msgid="228308803364967808">"SMS"</string>
<string name="permgroupdesc_sms" msgid="4656988620100940350">"надсилати та переглядати SMS-повідомлення"</string>
<string name="permgrouprequest_sms" msgid="7168124215838204719">"Дозволити додатку &lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; надсилати та переглядати SMS?"</string>
- <string name="permgrouplab_storage" msgid="1971118770546336966">"Зберігання"</string>
+ <string name="permgrouplab_storage" msgid="1971118770546336966">"Пам’ять"</string>
<string name="permgroupdesc_storage" msgid="637758554581589203">"отримувати доступ до фотографій, мультимедійного вмісту та файлів на вашому пристрої"</string>
<string name="permgrouprequest_storage" msgid="7885942926944299560">"Надати додатку &lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; доступ до фото, медіа та файлів на пристрої?"</string>
<string name="permgrouplab_microphone" msgid="171539900250043464">"Мікрофон"</string>
@@ -577,13 +577,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"Повторно проскануйте обличчя."</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"Розпізнати обличчя вже не вдається. Повторіть спробу."</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"Надто схоже на попередню спробу, змініть позу."</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"Трохи перемістіть обличчя."</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"Трохи перемістіть обличчя."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"Тримайте голову вертикально."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"Щось затуляє ваше обличчя."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"Протріть камеру."</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"Не вдається перевірити обличчя. Апаратне забезпечення недоступне."</string>
diff --git a/core/res/res/values-ur/strings.xml b/core/res/res/values-ur/strings.xml
index 10c5b2ddbf76..ebf715afd758 100644
--- a/core/res/res/values-ur/strings.xml
+++ b/core/res/res/values-ur/strings.xml
@@ -291,7 +291,7 @@
<string name="permgroupdesc_sms" msgid="4656988620100940350">"‏SMS پیغامات بھیجیں اور دیکھیں"</string>
<string name="permgrouprequest_sms" msgid="7168124215838204719">"‏&lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; کو SMS پیغامات بھیجنے اور انہیں ملاحظہ کرنے کی اجازت دیں؟"</string>
<string name="permgrouplab_storage" msgid="1971118770546336966">"اسٹوریج"</string>
- <string name="permgroupdesc_storage" msgid="637758554581589203">"اپنے آلہ پر تصاویر، میڈیا اور فائلوں تک رسائی حاصل کریں"</string>
+ <string name="permgroupdesc_storage" msgid="637758554581589203">"آپ کے آلہ پر تصاویر، میڈیا اور فائلوں تک رسائی حاصل کر سکتی ہیں"</string>
<string name="permgrouprequest_storage" msgid="7885942926944299560">"‏&lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; کو آپ کے آلہ پر تصاویر، میڈیا اور فائلوں تک رسائی کی اجازت دیں؟"</string>
<string name="permgrouplab_microphone" msgid="171539900250043464">"مائکروفون"</string>
<string name="permgroupdesc_microphone" msgid="4988812113943554584">"آڈیو ریکارڈ کریں"</string>
@@ -571,13 +571,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"براہ کرم اپنے چہرے کو دوبارہ مندرج کریں۔"</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"اب چہرے کی شناخت نہیں کر سکتے۔ پھر آزمائيں۔"</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"کافی ملتا جلتا ہے، براہ کرم اپنا پوز بدلیں۔"</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"اپنا سر تھوڑا کم کریں۔"</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"اپنا سر تھوڑا کم کریں۔"</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"براہ کرم اپنا سر عمودی طور پر سیدھا کریں۔"</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"اپنے سر اور فون کے درمیان جگہ ختم کریں۔"</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"براہ کرم کیمرا صاف کریں۔"</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"چہرے کی توثیق نہیں کی جا سکی۔ ہارڈ ویئر دستیاب نہیں ہے۔"</string>
diff --git a/core/res/res/values-uz/strings.xml b/core/res/res/values-uz/strings.xml
index 787fd1dfe925..e5c485dd8e9d 100644
--- a/core/res/res/values-uz/strings.xml
+++ b/core/res/res/values-uz/strings.xml
@@ -571,13 +571,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"Yuzingizni qaytadan qayd qildiring."</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"Yuz tanilmadi. Qaytadan urining."</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"Yuz ifodasi oldingiday. Holatingizni oʻzgartiring."</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"Boshingizni asta buring."</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"Boshingizni asta buring."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"Boshingizni tik tuting."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"Boshingiz va telefon orasidagi joyni olib tashlang."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"Kamerani tozalang."</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"Yuzingiz tasdiqlanmadi. Qurilma ishlamayapti."</string>
@@ -1598,8 +1599,8 @@
<string name="wireless_display_route_description" msgid="9070346425023979651">"Simsiz monitor"</string>
<string name="media_route_button_content_description" msgid="591703006349356016">"Translatsiya qilish"</string>
<string name="media_route_chooser_title" msgid="1751618554539087622">"Qurilmaga ulanish"</string>
- <string name="media_route_chooser_title_for_remote_display" msgid="3395541745872017583">"Ekrandagi tasvirni qurilmaga uzatish"</string>
- <string name="media_route_chooser_searching" msgid="4776236202610828706">"Qurilmalar izlanmoqda..."</string>
+ <string name="media_route_chooser_title_for_remote_display" msgid="3395541745872017583">"Ekran translatsiyasi"</string>
+ <string name="media_route_chooser_searching" msgid="4776236202610828706">"Qurilmalar qidirilmoqda..."</string>
<string name="media_route_chooser_extended_settings" msgid="87015534236701604">"Sozlamalar"</string>
<string name="media_route_controller_disconnect" msgid="8966120286374158649">"Uzish"</string>
<string name="media_route_status_scanning" msgid="7279908761758293783">"Qidirilmoqda..."</string>
diff --git a/core/res/res/values-vi/strings.xml b/core/res/res/values-vi/strings.xml
index fe7cdfc90211..d6dca0ab26d6 100644
--- a/core/res/res/values-vi/strings.xml
+++ b/core/res/res/values-vi/strings.xml
@@ -571,13 +571,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"Vui lòng đăng ký lại khuôn mặt của bạn."</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"Không nhận ra khuôn mặt. Hãy thử lại."</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"Khuôn mặt quá giống nhau, vui lòng đổi tư thế."</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"Hãy bớt di chuyển đầu."</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"Hãy bớt di chuyển đầu."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"Vui lòng giữ thẳng đầu."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"Loại bỏ vật chắn giữa đầu và điện thoại."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"Vui lòng lau sạch máy ảnh."</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"Không thể xác minh khuôn mặt. Phần cứng không có sẵn."</string>
diff --git a/core/res/res/values-zh-rCN/strings.xml b/core/res/res/values-zh-rCN/strings.xml
index 6596e57bcaac..01c9c238fa17 100644
--- a/core/res/res/values-zh-rCN/strings.xml
+++ b/core/res/res/values-zh-rCN/strings.xml
@@ -575,9 +575,12 @@
<skip />
<!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"请将头摆正。"</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"请清除头部和手机之间的障碍物。"</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"请将摄像头擦拭干净。"</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
+ <skip />
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
+ <skip />
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"无法验证人脸。硬件无法使用。"</string>
diff --git a/core/res/res/values-zh-rHK/strings.xml b/core/res/res/values-zh-rHK/strings.xml
index 8ba7c8cc588b..35fbaa6dec33 100644
--- a/core/res/res/values-zh-rHK/strings.xml
+++ b/core/res/res/values-zh-rHK/strings.xml
@@ -227,7 +227,7 @@
<string name="global_action_emergency" msgid="7112311161137421166">"緊急"</string>
<string name="global_action_bug_report" msgid="7934010578922304799">"錯誤報告"</string>
<string name="global_action_logout" msgid="935179188218826050">"結束工作階段"</string>
- <string name="global_action_screenshot" msgid="8329831278085426283">"擷取螢幕畫面"</string>
+ <string name="global_action_screenshot" msgid="8329831278085426283">"螢幕截圖"</string>
<string name="bugreport_title" msgid="5981047024855257269">"錯誤報告"</string>
<string name="bugreport_message" msgid="398447048750350456">"這會收集您目前裝置狀態的相關資訊,並以電郵傳送給您。從開始建立錯誤報告到準備傳送需要一段時間,請耐心等候。"</string>
<string name="bugreport_option_interactive_title" msgid="8635056131768862479">"互動報告"</string>
@@ -571,13 +571,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"請重新註冊臉孔。"</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"無法再識別臉孔。請再試一次。"</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"臉孔位置太相近,請改變您的姿勢。"</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"減少頭部左右轉動幅度。"</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"減少頭部上下轉動幅度。"</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"請保持頭部垂直。"</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"請移除頭部與手機之間的障礙物。"</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"請清潔相機。"</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"無法驗證臉孔,硬件無法使用。"</string>
@@ -1597,7 +1598,7 @@
<string name="wireless_display_route_description" msgid="9070346425023979651">"無線螢幕分享"</string>
<string name="media_route_button_content_description" msgid="591703006349356016">"投放"</string>
<string name="media_route_chooser_title" msgid="1751618554539087622">"連接裝置"</string>
- <string name="media_route_chooser_title_for_remote_display" msgid="3395541745872017583">"在裝置上放送螢幕"</string>
+ <string name="media_route_chooser_title_for_remote_display" msgid="3395541745872017583">"螢幕投放到裝置"</string>
<string name="media_route_chooser_searching" msgid="4776236202610828706">"正在搜尋裝置…"</string>
<string name="media_route_chooser_extended_settings" msgid="87015534236701604">"設定"</string>
<string name="media_route_controller_disconnect" msgid="8966120286374158649">"停止連接"</string>
diff --git a/core/res/res/values-zh-rTW/strings.xml b/core/res/res/values-zh-rTW/strings.xml
index 69990774b930..141706da6c11 100644
--- a/core/res/res/values-zh-rTW/strings.xml
+++ b/core/res/res/values-zh-rTW/strings.xml
@@ -571,13 +571,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"請重新註冊你的臉孔。"</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"已無法辨識臉孔,請再試一次。"</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"與先前的姿勢太相似,請換一個姿勢。"</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"請將你的頭部稍微向左或向右轉動。"</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"請將你的頭部稍微向上或向下傾斜。"</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"請將頭擺正。"</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"請清除頭部與手機之間的障礙物。"</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"請清理鏡頭。"</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"相關硬體無法使用,因此無法驗證臉孔。"</string>
@@ -1597,7 +1598,7 @@
<string name="wireless_display_route_description" msgid="9070346425023979651">"無線螢幕分享"</string>
<string name="media_route_button_content_description" msgid="591703006349356016">"投放"</string>
<string name="media_route_chooser_title" msgid="1751618554539087622">"連線至裝置"</string>
- <string name="media_route_chooser_title_for_remote_display" msgid="3395541745872017583">"將螢幕投放到裝置上"</string>
+ <string name="media_route_chooser_title_for_remote_display" msgid="3395541745872017583">"將螢幕畫面投放到裝置上"</string>
<string name="media_route_chooser_searching" msgid="4776236202610828706">"正在搜尋裝置..."</string>
<string name="media_route_chooser_extended_settings" msgid="87015534236701604">"設定"</string>
<string name="media_route_controller_disconnect" msgid="8966120286374158649">"中斷連線"</string>
diff --git a/core/res/res/values-zu/strings.xml b/core/res/res/values-zu/strings.xml
index 8b6fa671af7e..d770e85203f5 100644
--- a/core/res/res/values-zu/strings.xml
+++ b/core/res/res/values-zu/strings.xml
@@ -304,7 +304,7 @@
<string name="permgrouprequest_camera" msgid="1299833592069671756">"Vumela i-&lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; ukuthatha izithombe iphinde irekhode ividiyo?"</string>
<string name="permgrouplab_calllog" msgid="8798646184930388160">"Amarekhodi wamakholi"</string>
<string name="permgroupdesc_calllog" msgid="3006237336748283775">"funda futhi ubhale irekhodi lamakholi efoni"</string>
- <string name="permgrouprequest_calllog" msgid="8487355309583773267">"Vumela i-&lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; ukufinyelela irekhodi lakho lamakholi wefoni?"</string>
+ <string name="permgrouprequest_calllog" msgid="8487355309583773267">"Vumela i-&lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; ukufinyelela kurekhodi lakho lamakholi wefoni?"</string>
<string name="permgrouplab_phone" msgid="5229115638567440675">"Ifoni"</string>
<string name="permgroupdesc_phone" msgid="6234224354060641055">"yenza uphinde uphathe amakholi wefoni"</string>
<string name="permgrouprequest_phone" msgid="9166979577750581037">"Vumela i-&lt;b&gt;<xliff:g id="APP_NAME">%1$s</xliff:g>&lt;/b&gt; ukuthi yenze iphinde iphathe amakholi efoni?"</string>
@@ -571,13 +571,14 @@
<string name="face_acquired_recalibrate" msgid="8077949502893707539">"Sicela uphinde ubhalise ubuso bakho."</string>
<string name="face_acquired_too_different" msgid="7663983770123789694">"Ayisakwazi ukubona ubuso. Zama futhi."</string>
<string name="face_acquired_too_similar" msgid="1508776858407646460">"Kufana kakhulu, sicela ushintshe ukuma kwakho."</string>
- <!-- no translation found for face_acquired_pan_too_extreme (4581629343077288178) -->
+ <string name="face_acquired_pan_too_extreme" msgid="4581629343077288178">"Jikisa ikhanda lakho kancane."</string>
+ <string name="face_acquired_tilt_too_extreme" msgid="4019954263012496468">"Jikisa ikhanda lakho kancane."</string>
+ <!-- no translation found for face_acquired_roll_too_extreme (6312973147689664409) -->
<skip />
- <!-- no translation found for face_acquired_tilt_too_extreme (4019954263012496468) -->
+ <!-- no translation found for face_acquired_obscured (5357207702967893283) -->
+ <skip />
+ <!-- no translation found for face_acquired_sensor_dirty (2535761002815565222) -->
<skip />
- <string name="face_acquired_roll_too_extreme" msgid="1444829237745898619">"Sicela uqondise ikhanda lakho ngokumile."</string>
- <string name="face_acquired_obscured" msgid="5747521031647744553">"Susa isikhala esiphakathi kwekhanda lakho nefoni."</string>
- <string name="face_acquired_sensor_dirty" msgid="364493868630891300">"Sicela uhlanze ikhamera."</string>
<string-array name="face_acquired_vendor">
</string-array>
<string name="face_error_hw_not_available" msgid="396883585636963908">"Ayikwazi ukuqinisekisa ubuso. Izingxenyekazi zekhompyutha azitholakali."</string>
diff --git a/core/res/res/values/config.xml b/core/res/res/values/config.xml
index 4c6ae812f1ee..ab708e53dc7e 100644
--- a/core/res/res/values/config.xml
+++ b/core/res/res/values/config.xml
@@ -3328,9 +3328,8 @@
-->
<integer name="config_dockedStackDividerSnapMode">0</integer>
- <!-- The maximum aspect ratio (longerSide/shorterSide) that is treated as close-to-square. If
- config_forceDefaultOrientation is set to true, the rotation on a close-to-square display
- will be fixed. -->
+ <!-- The maximum aspect ratio (longerSide/shorterSide) that is treated as close-to-square. The
+ orientation requests from apps would be ignored if the display is close-to-square. -->
<item name="config_closeToSquareDisplayMaxAspectRatio" format="float" type="dimen">1.333</item>
<!-- List of comma separated package names for which we the system will not show crash, ANR,
diff --git a/core/res/res/values/dimens_car.xml b/core/res/res/values/dimens_car.xml
index f22a91ff75c1..880f9ccebd6e 100644
--- a/core/res/res/values/dimens_car.xml
+++ b/core/res/res/values/dimens_car.xml
@@ -137,4 +137,8 @@
<!-- Dialog image margin start -->
<dimen name="image_margin_start">@*android:dimen/car_keyline_1</dimen>
+ <dimen name="car_preference_icon_size">@dimen/car_primary_icon_size</dimen>
+ <dimen name="car_preference_category_icon_size">@dimen/car_primary_icon_size</dimen>
+ <dimen name="car_preference_row_vertical_margin">@dimen/car_padding_2</dimen>
+
</resources>
diff --git a/core/res/res/values/styles_device_defaults.xml b/core/res/res/values/styles_device_defaults.xml
index b7c86d266070..c63be7b2adbe 100644
--- a/core/res/res/values/styles_device_defaults.xml
+++ b/core/res/res/values/styles_device_defaults.xml
@@ -90,7 +90,10 @@ easier.
<item name="subtitleTextStyle">@style/TextAppearance.DeviceDefault.Widget.ActionMode.Subtitle</item>
</style>
<style name="Widget.DeviceDefault.ActionButton.CloseMode" parent="Widget.Material.ActionButton.CloseMode"/>
- <style name="Widget.DeviceDefault.ActionBar" parent="Widget.Material.ActionBar"/>
+ <style name="Widget.DeviceDefault.ActionBar" parent="Widget.Material.ActionBar">
+ <item name="titleTextStyle">@style/TextAppearance.DeviceDefault.Widget.ActionBar.Title</item>
+ <item name="subtitleTextStyle">@style/TextAppearance.DeviceDefault.Widget.ActionBar.Subtitle</item>
+ </style>
<style name="Widget.DeviceDefault.Button.Borderless" parent="Widget.Material.Button.Borderless"/>
<!-- Colored borderless ink button -->
<style name="Widget.DeviceDefault.Button.Borderless.Colored">
@@ -105,10 +108,15 @@ easier.
<style name="Widget.DeviceDefault.CalendarView" parent="Widget.Material.CalendarView"/>
<style name="Widget.DeviceDefault.DatePicker" parent="Widget.Material.DatePicker"/>
<style name="Widget.DeviceDefault.ActionBar.TabView" parent="Widget.Material.ActionBar.TabView"/>
- <style name="Widget.DeviceDefault.ActionBar.TabText" parent="Widget.Material.ActionBar.TabText"/>
+ <style name="Widget.DeviceDefault.ActionBar.TabText" parent="Widget.Material.ActionBar.TabText">
+ <item name="titleTextStyle">@style/TextAppearance.DeviceDefault.Widget.ActionBar.Title</item>
+ <item name="subtitleTextStyle">@style/TextAppearance.DeviceDefault.Widget.ActionBar.Subtitle</item>
+ <item name="textAppearance">@style/TextAppearance.DeviceDefault.Widget.TabWidget</item>
+ </style>
<style name="Widget.DeviceDefault.ActionBar.TabBar" parent="Widget.Material.ActionBar.TabBar"/>
<style name="Widget.DeviceDefault.ActionBar.Solid" parent="Widget.Material.ActionBar.Solid">
<item name="titleTextStyle">@style/TextAppearance.DeviceDefault.Widget.ActionBar.Title</item>
+ <item name="subtitleTextStyle">@style/TextAppearance.DeviceDefault.Widget.ActionBar.Subtitle</item>
<item name="background">?attr/colorPrimaryDark</item>
<item name="backgroundStacked">?attr/colorPrimaryDark</item>
<item name="backgroundSplit">?attr/colorPrimaryDark</item>
@@ -159,7 +167,6 @@ easier.
<item name="titleTextAppearance">@style/TextAppearance.DeviceDefault.Widget.Toolbar.Title</item>
<item name="subtitleTextAppearance">@style/TextAppearance.DeviceDefault.Widget.Toolbar.Subtitle</item>
</style>
-
<style name="Widget.DeviceDefault.Light" parent="Widget.Material.Light"/>
<style name="Widget.DeviceDefault.Light.Button" parent="Widget.Material.Light.Button"/>
<style name="Widget.DeviceDefault.Light.Button.Small" parent="Widget.Material.Light.Button.Small"/>
@@ -211,13 +218,16 @@ easier.
<style name="Widget.DeviceDefault.Light.Button.Borderless.Small" parent="Widget.Material.Light.Button.Borderless.Small"/>
<style name="Widget.DeviceDefault.Light.ActionButton" parent="Widget.Material.Light.ActionButton"/>
<style name="Widget.DeviceDefault.Light.ActionButton.Overflow" parent="Widget.Material.Light.ActionButton.Overflow"/>
- <style name="Widget.DeviceDefault.Light.ActionMode" parent="Widget.Material.Light.ActionMode"/>
+ <style name="Widget.DeviceDefault.Light.ActionMode" parent="Widget.DeviceDefault.ActionMode"/>
<style name="Widget.DeviceDefault.Light.ActionButton.CloseMode" parent="Widget.Material.Light.ActionButton.CloseMode"/>
- <style name="Widget.DeviceDefault.Light.ActionBar" parent="Widget.Material.Light.ActionBar"/>
+ <style name="Widget.DeviceDefault.Light.ActionBar" parent="Widget.DeviceDefault.ActionBar"/>
<style name="Widget.DeviceDefault.Light.ActionBar.TabView" parent="Widget.DeviceDefault.ActionBar.TabView" />
<style name="Widget.DeviceDefault.Light.ActionBar.TabText" parent="Widget.DeviceDefault.ActionBar.TabText" />
<style name="Widget.DeviceDefault.Light.ActionBar.TabBar" parent="Widget.DeviceDefault.ActionBar.TabBar" />
- <style name="Widget.DeviceDefault.Light.ActionBar.Solid" parent="Widget.DeviceDefault.ActionBar.Solid" />
+ <style name="Widget.DeviceDefault.Light.ActionBar.Solid" parent="Widget.Material.Light.ActionBar.Solid">
+ <item name="titleTextStyle">@style/TextAppearance.DeviceDefault.Widget.ActionBar.Title</item>
+ <item name="subtitleTextStyle">@style/TextAppearance.DeviceDefault.Widget.ActionBar.Subtitle</item>
+ </style>
<!-- @deprecated Action bars are now themed using the inheritable android:theme attribute. -->
<style name="Widget.DeviceDefault.Light.ActionBar.Solid.Inverse" parent="Widget.Holo.Light.ActionBar.Solid.Inverse"/>
<!-- @deprecated Action bars are now themed using the inheritable android:theme attribute. -->
diff --git a/core/tests/coretests/src/android/provider/SettingsBackupTest.java b/core/tests/coretests/src/android/provider/SettingsBackupTest.java
index 71a6b3099008..9fa04ef2dda2 100644
--- a/core/tests/coretests/src/android/provider/SettingsBackupTest.java
+++ b/core/tests/coretests/src/android/provider/SettingsBackupTest.java
@@ -721,7 +721,8 @@ public class SettingsBackupTest {
Settings.Secure.LOCATION_ACCESS_CHECK_DELAY_MILLIS,
Settings.Secure.BIOMETRIC_DEBUG_ENABLED,
Settings.Secure.FACE_UNLOCK_ATTENTION_REQUIRED,
- Settings.Secure.FACE_UNLOCK_DIVERSITY_REQUIRED);
+ Settings.Secure.FACE_UNLOCK_DIVERSITY_REQUIRED,
+ Settings.Secure.FACE_UNLOCK_EDUCATION_INFO_DISPLAYED);
@Test
public void systemSettingsBackedUpOrBlacklisted() {
diff --git a/data/etc/privapp-permissions-platform.xml b/data/etc/privapp-permissions-platform.xml
index 27e859c3987c..75a6b83e4d4f 100644
--- a/data/etc/privapp-permissions-platform.xml
+++ b/data/etc/privapp-permissions-platform.xml
@@ -49,13 +49,6 @@ applications that come with the platform
<permission name="android.permission.START_ACTIVITIES_FROM_BACKGROUND"/>
</privapp-permissions>
- <privapp-permissions package="com.android.defcontainer">
- <permission name="android.permission.ACCESS_CACHE_FILESYSTEM"/>
- <permission name="android.permission.ALLOCATE_AGGRESSIVE"/>
- <permission name="android.permission.INTERACT_ACROSS_USERS"/>
- <permission name="android.permission.WRITE_MEDIA_STORAGE"/>
- </privapp-permissions>
-
<privapp-permissions package="com.android.externalstorage">
<permission name="android.permission.MOUNT_UNMOUNT_FILESYSTEMS"/>
<permission name="android.permission.WRITE_MEDIA_STORAGE"/>
diff --git a/libs/protoutil/src/ProtoFileReader.cpp b/libs/protoutil/src/ProtoFileReader.cpp
index c7f1129fbbaa..bbb1fe374f0e 100644
--- a/libs/protoutil/src/ProtoFileReader.cpp
+++ b/libs/protoutil/src/ProtoFileReader.cpp
@@ -99,7 +99,6 @@ ProtoFileReader::next()
// Shouldn't get to here. Always call hasNext() before calling next().
return 0;
}
- mPos++;
return mBuffer[mOffset++];
}
@@ -131,7 +130,6 @@ ProtoFileReader::move(size_t amt)
const size_t chunk =
mMaxOffset - mOffset > amt ? amt : mMaxOffset - mOffset;
mOffset += chunk;
- mPos += chunk;
amt -= chunk;
}
}
diff --git a/location/java/com/android/internal/location/GpsNetInitiatedHandler.java b/location/java/com/android/internal/location/GpsNetInitiatedHandler.java
index b4be21987cf7..04e7bab0542b 100644
--- a/location/java/com/android/internal/location/GpsNetInitiatedHandler.java
+++ b/location/java/com/android/internal/location/GpsNetInitiatedHandler.java
@@ -357,8 +357,10 @@ public class GpsNetInitiatedHandler {
}
}
- // Sets the NI notification.
- private synchronized void setNiNotification(GpsNiNotification notif) {
+ /**
+ * Posts a notification in the status bar using the contents in {@code notif} object.
+ */
+ public synchronized void setNiNotification(GpsNiNotification notif) {
NotificationManager notificationManager = (NotificationManager) mContext
.getSystemService(Context.NOTIFICATION_SERVICE);
if (notificationManager == null) {
@@ -539,14 +541,14 @@ public class GpsNetInitiatedHandler {
*/
static private String decodeString(String original, boolean isHex, int coding)
{
+ if (coding == GPS_ENC_NONE) {
+ return original;
+ }
+
String decoded = original;
byte[] input = stringToByteArray(original, isHex);
switch (coding) {
- case GPS_ENC_NONE:
- decoded = original;
- break;
-
case GPS_ENC_SUPL_GSM_DEFAULT:
decoded = decodeGSMPackedString(input);
break;
diff --git a/media/java/android/media/AudioManager.java b/media/java/android/media/AudioManager.java
index bcc57d203fc2..23dfb777362b 100644
--- a/media/java/android/media/AudioManager.java
+++ b/media/java/android/media/AudioManager.java
@@ -3774,7 +3774,7 @@ public class AudioManager {
/** @hide */
public static final int RECORD_CONFIG_EVENT_UPDATE = 2;
/** @hide */
- public static final int RECORD_CONFIG_EVENT_DEATH = 3;
+ public static final int RECORD_CONFIG_EVENT_RELEASE = 3;
/**
* keep in sync with frameworks/native/include/audiomanager/AudioManager.h
*/
diff --git a/media/java/android/media/AudioRecord.java b/media/java/android/media/AudioRecord.java
index eeb7655abff9..ce9b07dd0c0e 100644
--- a/media/java/android/media/AudioRecord.java
+++ b/media/java/android/media/AudioRecord.java
@@ -838,6 +838,7 @@ public class AudioRecord implements AudioRouting, MicrophoneDirection,
}
if (mAudioCapturePolicy != null) {
AudioManager.unregisterAudioPolicyAsyncStatic(mAudioCapturePolicy);
+ mAudioCapturePolicy = null;
}
native_release();
mState = STATE_UNINITIALIZED;
diff --git a/media/java/android/media/AudioRecordingConfiguration.java b/media/java/android/media/AudioRecordingConfiguration.java
index 74e661834818..874a215e4975 100644
--- a/media/java/android/media/AudioRecordingConfiguration.java
+++ b/media/java/android/media/AudioRecordingConfiguration.java
@@ -157,7 +157,7 @@ public final class AudioRecordingConfiguration implements Parcelable {
return new AudioRecordingConfiguration( /*anonymized uid*/ -1,
in.mClientSessionId, in.mClientSource, in.mClientFormat,
in.mDeviceFormat, in.mPatchHandle, "" /*empty package name*/,
- /*anonymized portId*/ -1, in.mClientSilenced, in.mDeviceSource, in.mClientEffects,
+ in.mClientPortId, in.mClientSilenced, in.mDeviceSource, in.mClientEffects,
in.mDeviceEffects);
}
diff --git a/media/java/android/media/IAudioService.aidl b/media/java/android/media/IAudioService.aidl
index 81ddcdb4e27e..a790441aa36e 100644
--- a/media/java/android/media/IAudioService.aidl
+++ b/media/java/android/media/IAudioService.aidl
@@ -64,6 +64,8 @@ interface IAudioService {
oneway void recorderEvent(in int riid, in int event);
+ oneway void releaseRecorder(in int riid);
+
// Java-only methods below.
oneway void adjustSuggestedStreamVolume(int direction, int suggestedStreamType, int flags,
diff --git a/media/java/android/media/MediaParceledListSlice.aidl b/media/java/android/media/MediaParceledListSlice.aidl
deleted file mode 100644
index 5c0e5bc84720..000000000000
--- a/media/java/android/media/MediaParceledListSlice.aidl
+++ /dev/null
@@ -1,20 +0,0 @@
-/*
- * Copyright 2019 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package android.media;
-
-/** @hide */
-parcelable MediaParceledListSlice;
diff --git a/media/java/android/media/MediaParceledListSlice.java b/media/java/android/media/MediaParceledListSlice.java
deleted file mode 100644
index e90d9a4000ba..000000000000
--- a/media/java/android/media/MediaParceledListSlice.java
+++ /dev/null
@@ -1,200 +0,0 @@
-/*
- * Copyright 2019 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package android.media;
-
-import android.os.Binder;
-import android.os.IBinder;
-import android.os.Parcel;
-import android.os.Parcelable;
-import android.os.RemoteException;
-import android.util.Log;
-
-import java.util.ArrayList;
-import java.util.List;
-
-/**
- * Transfer a large list of objects across an IPC. Splits into multiple transactions if needed.
- * Note: Only use classes declared final in order to avoid subclasses overriding reading/writing
- * parcel logic.
- *
- * TODO: Add test for sending large data
- * @param <T> A Parcelable class which will be sent over the binder calls.
- * @hide
- */
-public class MediaParceledListSlice<T extends Parcelable> implements Parcelable {
- private static final String TAG = "MediaParceledListSlice";
- private static final boolean DEBUG = false;
-
- private static final int MAX_IPC_SIZE = 64 * 1024; // IBinder.MAX_IPC_SIZE
-
- final List<T> mList;
-
- public MediaParceledListSlice(List<T> list) {
- if (list == null) {
- throw new IllegalArgumentException("list shouldn't be null");
- }
- mList = list;
- }
-
- MediaParceledListSlice(Parcel p) {
- final int itemCount = p.readInt();
- mList = new ArrayList<>(itemCount);
- if (DEBUG) {
- Log.d(TAG, "Retrieving " + itemCount + " items");
- }
- if (itemCount <= 0) {
- return;
- }
-
- int i = 0;
- while (i < itemCount) {
- if (p.readInt() == 0) {
- break;
- }
-
- final T parcelable = p.readParcelable(null);
- mList.add(parcelable);
-
- if (DEBUG) {
- Log.d(TAG, "Read inline #" + i + ": " + mList.get(mList.size() - 1));
- }
- i++;
- }
- if (i >= itemCount) {
- return;
- }
- final IBinder retriever = p.readStrongBinder();
- while (i < itemCount) {
- if (DEBUG) {
- Log.d(TAG, "Reading more @" + i + " of " + itemCount + ": retriever=" + retriever);
- }
- Parcel data = Parcel.obtain();
- Parcel reply = Parcel.obtain();
- data.writeInt(i);
- try {
- retriever.transact(IBinder.FIRST_CALL_TRANSACTION, data, reply, 0);
- } catch (RemoteException e) {
- Log.w(TAG, "Failure retrieving array; only received " + i + " of " + itemCount, e);
- return;
- }
- while (i < itemCount && reply.readInt() != 0) {
- final T parcelable = reply.readParcelable(null);
- mList.add(parcelable);
-
- if (DEBUG) {
- Log.d(TAG, "Read extra #" + i + ": " + mList.get(mList.size() - 1));
- }
- i++;
- }
- reply.recycle();
- data.recycle();
- }
- }
-
- public List<T> getList() {
- return mList;
- }
-
- /**
- * Write this to another Parcel. Note that this discards the internal Parcel
- * and should not be used anymore. This is so we can pass this to a Binder
- * where we won't have a chance to call recycle on this.
- */
- @Override
- public void writeToParcel(Parcel dest, int flags) {
- final int itemCount = mList.size();
- dest.writeInt(itemCount);
- if (DEBUG) {
- Log.d(TAG, "Writing " + itemCount + " items");
- }
- if (itemCount > 0) {
- int i = 0;
- while (i < itemCount && dest.dataSize() < MAX_IPC_SIZE) {
- dest.writeInt(1);
-
- final T parcelable = mList.get(i);
- dest.writeParcelable(parcelable, flags);
-
- if (DEBUG) {
- Log.d(TAG, "Wrote inline #" + i + ": " + mList.get(i));
- }
- i++;
- }
- if (i < itemCount) {
- dest.writeInt(0);
- Binder retriever = new Binder() {
- @Override
- protected boolean onTransact(int code, Parcel data, Parcel reply, int flags)
- throws RemoteException {
- if (code != FIRST_CALL_TRANSACTION) {
- return super.onTransact(code, data, reply, flags);
- }
- int i = data.readInt();
- if (DEBUG) {
- Log.d(TAG, "Writing more @" + i + " of " + itemCount);
- }
- while (i < itemCount && reply.dataSize() < MAX_IPC_SIZE) {
- reply.writeInt(1);
-
- final T parcelable = mList.get(i);
- reply.writeParcelable(parcelable, flags);
-
- if (DEBUG) {
- Log.d(TAG, "Wrote extra #" + i + ": " + mList.get(i));
- }
- i++;
- }
- if (i < itemCount) {
- if (DEBUG) {
- Log.d(TAG, "Breaking @" + i + " of " + itemCount);
- }
- reply.writeInt(0);
- }
- return true;
- }
- };
- if (DEBUG) {
- Log.d(TAG, "Breaking @" + i + " of " + itemCount + ": retriever=" + retriever);
- }
- dest.writeStrongBinder(retriever);
- }
- }
- }
-
- @Override
- public int describeContents() {
- int contents = 0;
- final List<T> list = getList();
- for (int i = 0; i < list.size(); i++) {
- contents |= list.get(i).describeContents();
- }
- return contents;
- }
-
- public static final @android.annotation.NonNull Parcelable.Creator<MediaParceledListSlice> CREATOR =
- new Parcelable.Creator<MediaParceledListSlice>() {
- @Override
- public MediaParceledListSlice createFromParcel(Parcel in) {
- return new MediaParceledListSlice(in);
- }
-
- @Override
- public MediaParceledListSlice[] newArray(int size) {
- return new MediaParceledListSlice[size];
- }
- };
-}
diff --git a/media/java/android/media/browse/MediaBrowser.java b/media/java/android/media/browse/MediaBrowser.java
index 65255a1bebf7..3c2be5f93e30 100644
--- a/media/java/android/media/browse/MediaBrowser.java
+++ b/media/java/android/media/browse/MediaBrowser.java
@@ -23,8 +23,8 @@ import android.content.ComponentName;
import android.content.Context;
import android.content.Intent;
import android.content.ServiceConnection;
+import android.content.pm.ParceledListSlice;
import android.media.MediaDescription;
-import android.media.MediaParceledListSlice;
import android.media.session.MediaController;
import android.media.session.MediaSession;
import android.os.Binder;
@@ -653,7 +653,7 @@ public final class MediaBrowser {
}
private void onLoadChildren(final IMediaBrowserServiceCallbacks callback,
- final String parentId, final MediaParceledListSlice list, final Bundle options) {
+ final String parentId, final ParceledListSlice list, final Bundle options) {
mHandler.post(new Runnable() {
@Override
public void run() {
@@ -1107,12 +1107,12 @@ public final class MediaBrowser {
}
@Override
- public void onLoadChildren(String parentId, MediaParceledListSlice list) {
+ public void onLoadChildren(String parentId, ParceledListSlice list) {
onLoadChildrenWithOptions(parentId, list, null);
}
@Override
- public void onLoadChildrenWithOptions(String parentId, MediaParceledListSlice list,
+ public void onLoadChildrenWithOptions(String parentId, ParceledListSlice list,
final Bundle options) {
MediaBrowser mediaBrowser = mMediaBrowser.get();
if (mediaBrowser != null) {
diff --git a/media/java/android/media/session/ISession.aidl b/media/java/android/media/session/ISession.aidl
index fcde95aa38a2..4d68a6ae52e4 100644
--- a/media/java/android/media/session/ISession.aidl
+++ b/media/java/android/media/session/ISession.aidl
@@ -16,9 +16,9 @@
package android.media.session;
import android.app.PendingIntent;
+import android.content.pm.ParceledListSlice;
import android.media.AudioAttributes;
import android.media.MediaMetadata;
-import android.media.MediaParceledListSlice;
import android.media.session.ISessionController;
import android.media.session.PlaybackState;
import android.media.session.MediaSession;
@@ -41,7 +41,7 @@ interface ISession {
// These commands are for the TransportPerformer
void setMetadata(in MediaMetadata metadata, long duration, String metadataDescription);
void setPlaybackState(in PlaybackState state);
- void setQueue(in MediaParceledListSlice queue);
+ void setQueue(in ParceledListSlice queue);
void setQueueTitle(CharSequence title);
void setExtras(in Bundle extras);
void setRatingType(int type);
diff --git a/media/java/android/media/session/ISessionController.aidl b/media/java/android/media/session/ISessionController.aidl
index 9b1223cc48ba..e1039fd26940 100644
--- a/media/java/android/media/session/ISessionController.aidl
+++ b/media/java/android/media/session/ISessionController.aidl
@@ -17,8 +17,8 @@ package android.media.session;
import android.app.PendingIntent;
import android.content.Intent;
+import android.content.pm.ParceledListSlice;
import android.media.MediaMetadata;
-import android.media.MediaParceledListSlice;
import android.media.Rating;
import android.media.session.ISessionControllerCallback;
import android.media.session.MediaController;
@@ -82,7 +82,7 @@ interface ISessionController {
String action, in Bundle args);
MediaMetadata getMetadata();
PlaybackState getPlaybackState();
- MediaParceledListSlice getQueue();
+ ParceledListSlice getQueue();
CharSequence getQueueTitle();
Bundle getExtras();
int getRatingType();
diff --git a/media/java/android/media/session/ISessionControllerCallback.aidl b/media/java/android/media/session/ISessionControllerCallback.aidl
index f284133708fe..9da3e3bb114b 100644
--- a/media/java/android/media/session/ISessionControllerCallback.aidl
+++ b/media/java/android/media/session/ISessionControllerCallback.aidl
@@ -15,8 +15,8 @@
package android.media.session;
+import android.content.pm.ParceledListSlice;
import android.media.MediaMetadata;
-import android.media.MediaParceledListSlice;
import android.media.session.MediaController;
import android.media.session.PlaybackState;
import android.os.Bundle;
@@ -31,7 +31,7 @@ oneway interface ISessionControllerCallback {
// These callbacks are for the TransportController
void onPlaybackStateChanged(in PlaybackState state);
void onMetadataChanged(in MediaMetadata metadata);
- void onQueueChanged(in MediaParceledListSlice queue);
+ void onQueueChanged(in ParceledListSlice queue);
void onQueueTitleChanged(CharSequence title);
void onExtrasChanged(in Bundle extras);
void onVolumeInfoChanged(in MediaController.PlaybackInfo info);
diff --git a/media/java/android/media/session/MediaController.java b/media/java/android/media/session/MediaController.java
index 55692437d8d5..c1c7fcac0a8d 100644
--- a/media/java/android/media/session/MediaController.java
+++ b/media/java/android/media/session/MediaController.java
@@ -21,10 +21,10 @@ import android.annotation.Nullable;
import android.annotation.UnsupportedAppUsage;
import android.app.PendingIntent;
import android.content.Context;
+import android.content.pm.ParceledListSlice;
import android.media.AudioAttributes;
import android.media.AudioManager;
import android.media.MediaMetadata;
-import android.media.MediaParceledListSlice;
import android.media.Rating;
import android.media.VolumeProvider;
import android.media.session.MediaSession.QueueItem;
@@ -174,7 +174,7 @@ public final class MediaController {
*/
public @Nullable List<MediaSession.QueueItem> getQueue() {
try {
- MediaParceledListSlice list = mSessionBinder.getQueue();
+ ParceledListSlice list = mSessionBinder.getQueue();
return list == null ? null : list.getList();
} catch (RemoteException e) {
Log.wtf(TAG, "Error calling getQueue.", e);
@@ -1116,7 +1116,7 @@ public final class MediaController {
}
@Override
- public void onQueueChanged(MediaParceledListSlice queue) {
+ public void onQueueChanged(ParceledListSlice queue) {
MediaController controller = mController.get();
if (controller != null) {
controller.postMessage(MSG_UPDATE_QUEUE, queue, null);
@@ -1174,7 +1174,7 @@ public final class MediaController {
break;
case MSG_UPDATE_QUEUE:
mCallback.onQueueChanged(msg.obj == null ? null :
- (List<QueueItem>) ((MediaParceledListSlice) msg.obj).getList());
+ (List<QueueItem>) ((ParceledListSlice) msg.obj).getList());
break;
case MSG_UPDATE_QUEUE_TITLE:
mCallback.onQueueTitleChanged((CharSequence) msg.obj);
diff --git a/media/java/android/media/session/MediaSession.java b/media/java/android/media/session/MediaSession.java
index cee869ba4808..c4085f876136 100644
--- a/media/java/android/media/session/MediaSession.java
+++ b/media/java/android/media/session/MediaSession.java
@@ -24,10 +24,10 @@ import android.app.Activity;
import android.app.PendingIntent;
import android.content.Context;
import android.content.Intent;
+import android.content.pm.ParceledListSlice;
import android.media.AudioAttributes;
import android.media.MediaDescription;
import android.media.MediaMetadata;
-import android.media.MediaParceledListSlice;
import android.media.Rating;
import android.media.VolumeProvider;
import android.media.session.MediaSessionManager.RemoteUserInfo;
@@ -473,7 +473,7 @@ public final class MediaSession {
*/
public void setQueue(@Nullable List<QueueItem> queue) {
try {
- mBinder.setQueue(queue == null ? null : new MediaParceledListSlice(queue));
+ mBinder.setQueue(queue == null ? null : new ParceledListSlice(queue));
} catch (RemoteException e) {
Log.wtf("Dead object in setQueue.", e);
}
diff --git a/media/java/android/service/media/IMediaBrowserServiceCallbacks.aidl b/media/java/android/service/media/IMediaBrowserServiceCallbacks.aidl
index 507a8f72ea57..8238b8c4898d 100644
--- a/media/java/android/service/media/IMediaBrowserServiceCallbacks.aidl
+++ b/media/java/android/service/media/IMediaBrowserServiceCallbacks.aidl
@@ -2,7 +2,7 @@
package android.service.media;
-import android.media.MediaParceledListSlice;
+import android.content.pm.ParceledListSlice;
import android.media.session.MediaSession;
import android.os.Bundle;
@@ -21,7 +21,7 @@ oneway interface IMediaBrowserServiceCallbacks {
*/
void onConnect(String root, in MediaSession.Token session, in Bundle extras);
void onConnectFailed();
- void onLoadChildren(String mediaId, in MediaParceledListSlice list);
- void onLoadChildrenWithOptions(String mediaId, in MediaParceledListSlice list,
+ void onLoadChildren(String mediaId, in ParceledListSlice list);
+ void onLoadChildrenWithOptions(String mediaId, in ParceledListSlice list,
in Bundle options);
}
diff --git a/media/java/android/service/media/MediaBrowserService.java b/media/java/android/service/media/MediaBrowserService.java
index d9ef6ae40dfb..86a1076af122 100644
--- a/media/java/android/service/media/MediaBrowserService.java
+++ b/media/java/android/service/media/MediaBrowserService.java
@@ -25,7 +25,7 @@ import android.annotation.UnsupportedAppUsage;
import android.app.Service;
import android.content.Intent;
import android.content.pm.PackageManager;
-import android.media.MediaParceledListSlice;
+import android.content.pm.ParceledListSlice;
import android.media.browse.MediaBrowser;
import android.media.browse.MediaBrowserUtils;
import android.media.session.MediaSession;
@@ -684,8 +684,8 @@ public abstract class MediaBrowserService extends Service {
List<MediaBrowser.MediaItem> filteredList =
(flag & RESULT_FLAG_OPTION_NOT_HANDLED) != 0
? applyOptions(list, options) : list;
- final MediaParceledListSlice<MediaBrowser.MediaItem> pls =
- filteredList == null ? null : new MediaParceledListSlice<>(filteredList);
+ final ParceledListSlice<MediaBrowser.MediaItem> pls =
+ filteredList == null ? null : new ParceledListSlice<>(filteredList);
try {
connection.callbacks.onLoadChildrenWithOptions(parentId, pls, options);
} catch (RemoteException ex) {
diff --git a/packages/CaptivePortalLogin/AndroidManifest.xml b/packages/CaptivePortalLogin/AndroidManifest.xml
index a8f9c3b6aa87..86d6d442c672 100644
--- a/packages/CaptivePortalLogin/AndroidManifest.xml
+++ b/packages/CaptivePortalLogin/AndroidManifest.xml
@@ -31,6 +31,7 @@
<uses-permission android:name="android.permission.MAINLINE_NETWORK_STACK" />
<application android:label="@string/app_name"
+ android:icon="@drawable/app_icon"
android:usesCleartextTraffic="true"
android:supportsRtl="true" >
<activity
diff --git a/packages/CaptivePortalLogin/res/drawable/app_icon.xml b/packages/CaptivePortalLogin/res/drawable/app_icon.xml
new file mode 100644
index 000000000000..456ca83f5227
--- /dev/null
+++ b/packages/CaptivePortalLogin/res/drawable/app_icon.xml
@@ -0,0 +1,26 @@
+<!--
+ Copyright (C) 2019 The Android Open Source Project
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+-->
+<adaptive-icon xmlns:android="http://schemas.android.com/apk/res/android">
+ <background>
+ <color android:color="@*android:color/accent_device_default_light" />
+ </background>
+ <foreground>
+ <inset
+ android:drawable="@drawable/maybe_wifi"
+ android:inset="25%">
+ </inset>
+ </foreground>
+</adaptive-icon>
diff --git a/packages/CaptivePortalLogin/res/drawable/maybe_wifi.xml b/packages/CaptivePortalLogin/res/drawable/maybe_wifi.xml
new file mode 100644
index 000000000000..207aade406ef
--- /dev/null
+++ b/packages/CaptivePortalLogin/res/drawable/maybe_wifi.xml
@@ -0,0 +1,27 @@
+<!--
+Copyright (C) 2019 The Android Open Source Project
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+-->
+<vector xmlns:android="http://schemas.android.com/apk/res/android"
+ android:width="26.0dp"
+ android:height="24.0dp"
+ android:viewportWidth="26.0"
+ android:viewportHeight="24.0">
+ <path
+ android:fillColor="#4DFFFFFF"
+ android:pathData="M19.1,14l-3.4,0l0,-1.5c0,-1.8 0.8,-2.8 1.5,-3.4C18.1,8.3 19.200001,8 20.6,8c1.2,0 2.3,0.3 3.1,0.8l1.9,-2.3C25.1,6.1 20.299999,2.1 13,2.1S0.9,6.1 0.4,6.5L13,22l0,0l0,0l0,0l0,0l6.5,-8.1L19.1,14z"/>
+ <path
+ android:fillColor="#FFFFFFFF"
+ android:pathData="M19.5,17.799999c0,-0.8 0.1,-1.3 0.2,-1.6c0.2,-0.3 0.5,-0.7 1.1,-1.2c0.4,-0.4 0.7,-0.8 1,-1.1s0.4,-0.8 0.4,-1.2c0,-0.5 -0.1,-0.9 -0.4,-1.2c-0.3,-0.3 -0.7,-0.4 -1.2,-0.4c-0.4,0 -0.8,0.1 -1.1,0.3c-0.3,0.2 -0.4,0.6 -0.4,1.1l-1.9,0c0,-1 0.3,-1.7 1,-2.2c0.6,-0.5 1.5,-0.8 2.5,-0.8c1.1,0 2,0.3 2.6,0.8c0.6,0.5 0.9,1.3 0.9,2.3c0,0.7 -0.2,1.3 -0.6,1.8c-0.4,0.6 -0.9,1.1 -1.5,1.6c-0.3,0.3 -0.5,0.5 -0.6,0.7c-0.1,0.2 -0.1,0.6 -0.1,1L19.5,17.700001zM21.4,21l-1.9,0l0,-1.8l1.9,0L21.4,21z"/>
+</vector>
diff --git a/packages/DefaultContainerService/Android.bp b/packages/DefaultContainerService/Android.bp
deleted file mode 100644
index d4ba6e8980e6..000000000000
--- a/packages/DefaultContainerService/Android.bp
+++ /dev/null
@@ -1,8 +0,0 @@
-android_app {
- name: "DefaultContainerService",
- srcs: ["**/*.java"],
- platform_apis: true,
- jni_libs: ["libdefcontainer_jni"],
- certificate: "platform",
- privileged: true,
-}
diff --git a/packages/DefaultContainerService/AndroidManifest.xml b/packages/DefaultContainerService/AndroidManifest.xml
deleted file mode 100644
index 9f546525942b..000000000000
--- a/packages/DefaultContainerService/AndroidManifest.xml
+++ /dev/null
@@ -1,23 +0,0 @@
-<manifest xmlns:android="http://schemas.android.com/apk/res/android"
- package="com.android.defcontainer" coreApp="true">
- <uses-permission android:name="android.permission.ALLOCATE_AGGRESSIVE"/>
- <uses-permission android:name="android.permission.ASEC_ACCESS"/>
- <uses-permission android:name="android.permission.ASEC_CREATE"/>
- <uses-permission android:name="android.permission.ASEC_DESTROY"/>
- <uses-permission android:name="android.permission.ASEC_MOUNT_UNMOUNT"/>
- <uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />
- <uses-permission android:name="android.permission.ACCESS_CACHE_FILESYSTEM" />
- <uses-permission android:name="android.permission.INTERACT_ACROSS_USERS" />
-
- <application android:label="@string/service_name"
- android:allowBackup="false"
- android:defaultToDeviceProtectedStorage="true"
- android:directBootAware="true">
-
- <service android:name=".DefaultContainerService"
- android:enabled="true"
- android:exported="true"
- android:permission="android.permission.COPY_PROTECTED_DATA"/>
- </application>
-
-</manifest>
diff --git a/packages/DefaultContainerService/jni/Android.bp b/packages/DefaultContainerService/jni/Android.bp
deleted file mode 100644
index 7d7b09599dfe..000000000000
--- a/packages/DefaultContainerService/jni/Android.bp
+++ /dev/null
@@ -1,36 +0,0 @@
-//
-// Copyright (C) 2010 The Android Open Source Project
-//
-// Licensed under the Apache License, Version 2.0 (the "License");
-// you may not use this file except in compliance with the License.
-// You may obtain a copy of the License at
-//
-// http://www.apache.org/licenses/LICENSE-2.0
-//
-// Unless required by applicable law or agreed to in writing, software
-// distributed under the License is distributed on an "AS IS" BASIS,
-// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-// See the License for the specific language governing permissions and
-// limitations under the License.
-//
-
-cc_library_shared {
- name: "libdefcontainer_jni",
-
- srcs: ["com_android_defcontainer_MeasurementUtils.cpp"],
-
- shared_libs: [
- "libnativehelper",
- "libutils",
- "liblog",
- ],
-
- static_libs: ["libdiskusage"],
-
- cflags: [
- "-Wall",
- "-Werror",
- "-Wunused",
- "-Wunreachable-code",
- ],
-}
diff --git a/packages/DefaultContainerService/jni/com_android_defcontainer_MeasurementUtils.cpp b/packages/DefaultContainerService/jni/com_android_defcontainer_MeasurementUtils.cpp
deleted file mode 100644
index 53cdc9d96b43..000000000000
--- a/packages/DefaultContainerService/jni/com_android_defcontainer_MeasurementUtils.cpp
+++ /dev/null
@@ -1,76 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#define LOG_TAG "DefContainer-JNI"
-
-#include <nativehelper/JNIHelp.h>
-
-#include <diskusage/dirsize.h>
-#include <utils/Log.h>
-
-#include <sys/types.h>
-#include <sys/stat.h>
-#include <errno.h>
-#include <fcntl.h>
-#include <string.h>
-
-namespace android {
-
-static jlong native_measureDirectory(JNIEnv* env, jobject /* clazz */, jstring directory) {
- jlong ret = 0L;
-
- const char* path = env->GetStringUTFChars(directory, NULL);
- if (path == NULL) {
- return ret;
- }
-
- int dirfd = open(path, O_DIRECTORY, O_RDONLY);
- if (dirfd < 0) {
- ALOGI("error opening: %s: %s", path, strerror(errno));
- } else {
- ret = calculate_dir_size(dirfd);
- close(dirfd);
- }
-
- env->ReleaseStringUTFChars(directory, path);
-
- return ret;
-}
-
-static const JNINativeMethod g_methods[] = {
- { "native_measureDirectory", "(Ljava/lang/String;)J", (void*)native_measureDirectory },
-};
-
-int register_com_android_defcontainer(JNIEnv *env) {
- if (jniRegisterNativeMethods(
- env, "com/android/defcontainer/MeasurementUtils", g_methods, NELEM(g_methods)) < 0) {
- return JNI_ERR;
- }
-
- return JNI_VERSION_1_6;
-}
-
-} // namespace android
-
-int JNI_OnLoad(JavaVM *jvm, void* /* reserved */) {
- JNIEnv *env;
-
- if (jvm->GetEnv((void**)&env, JNI_VERSION_1_6)) {
- return JNI_ERR;
- }
-
- return android::register_com_android_defcontainer(env);
-}
diff --git a/packages/DefaultContainerService/res/values-af/strings.xml b/packages/DefaultContainerService/res/values-af/strings.xml
deleted file mode 100644
index 5fa075b0aa55..000000000000
--- a/packages/DefaultContainerService/res/values-af/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"Pakkettoegangshelper"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-am/strings.xml b/packages/DefaultContainerService/res/values-am/strings.xml
deleted file mode 100644
index 1101a4550aa7..000000000000
--- a/packages/DefaultContainerService/res/values-am/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"ጥቅል ድረስ አጋዥ"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-ar/strings.xml b/packages/DefaultContainerService/res/values-ar/strings.xml
deleted file mode 100644
index 823e472030f6..000000000000
--- a/packages/DefaultContainerService/res/values-ar/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"مساعد الدخول إلى الحزمة"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-as/strings.xml b/packages/DefaultContainerService/res/values-as/strings.xml
deleted file mode 100644
index 1b6391c8b967..000000000000
--- a/packages/DefaultContainerService/res/values-as/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"পেকেজ চোৱা সহায়ক"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-az/strings.xml b/packages/DefaultContainerService/res/values-az/strings.xml
deleted file mode 100644
index cae7d024708e..000000000000
--- a/packages/DefaultContainerService/res/values-az/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"Paket Giriş Yardımçısı"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-b+sr+Latn/strings.xml b/packages/DefaultContainerService/res/values-b+sr+Latn/strings.xml
deleted file mode 100644
index a0e1734fc85d..000000000000
--- a/packages/DefaultContainerService/res/values-b+sr+Latn/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"Pomoćnik za pristup paketu"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-be/strings.xml b/packages/DefaultContainerService/res/values-be/strings.xml
deleted file mode 100644
index 68621b6dbc09..000000000000
--- a/packages/DefaultContainerService/res/values-be/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"Памочнік дост. да пакетаў"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-bg/strings.xml b/packages/DefaultContainerService/res/values-bg/strings.xml
deleted file mode 100644
index 7f8939a0fd1a..000000000000
--- a/packages/DefaultContainerService/res/values-bg/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"Помощ в достъпа до пакети"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-bn/strings.xml b/packages/DefaultContainerService/res/values-bn/strings.xml
deleted file mode 100644
index 23b197fa86c5..000000000000
--- a/packages/DefaultContainerService/res/values-bn/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"প্যাকেজ অ্যাক্সেস সাহায়ক"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-bs/strings.xml b/packages/DefaultContainerService/res/values-bs/strings.xml
deleted file mode 100644
index 9be3873ef529..000000000000
--- a/packages/DefaultContainerService/res/values-bs/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"Asistent pristupa paketu"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-ca/strings.xml b/packages/DefaultContainerService/res/values-ca/strings.xml
deleted file mode 100644
index e19c72c8f5ee..000000000000
--- a/packages/DefaultContainerService/res/values-ca/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"Assist. d\'accés a paquets"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-cs/strings.xml b/packages/DefaultContainerService/res/values-cs/strings.xml
deleted file mode 100644
index 216d715996c7..000000000000
--- a/packages/DefaultContainerService/res/values-cs/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"Package Access Helper"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-da/strings.xml b/packages/DefaultContainerService/res/values-da/strings.xml
deleted file mode 100644
index 5243028ed9da..000000000000
--- a/packages/DefaultContainerService/res/values-da/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"Hjælp til pakkeadgang"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-de/strings.xml b/packages/DefaultContainerService/res/values-de/strings.xml
deleted file mode 100644
index 216d715996c7..000000000000
--- a/packages/DefaultContainerService/res/values-de/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"Package Access Helper"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-el/strings.xml b/packages/DefaultContainerService/res/values-el/strings.xml
deleted file mode 100644
index a4d81441b363..000000000000
--- a/packages/DefaultContainerService/res/values-el/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"Βοηθός πρόσβασης πακέτου"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-en-rAU/strings.xml b/packages/DefaultContainerService/res/values-en-rAU/strings.xml
deleted file mode 100644
index 216d715996c7..000000000000
--- a/packages/DefaultContainerService/res/values-en-rAU/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"Package Access Helper"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-en-rCA/strings.xml b/packages/DefaultContainerService/res/values-en-rCA/strings.xml
deleted file mode 100644
index 216d715996c7..000000000000
--- a/packages/DefaultContainerService/res/values-en-rCA/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"Package Access Helper"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-en-rGB/strings.xml b/packages/DefaultContainerService/res/values-en-rGB/strings.xml
deleted file mode 100644
index 216d715996c7..000000000000
--- a/packages/DefaultContainerService/res/values-en-rGB/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"Package Access Helper"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-en-rIN/strings.xml b/packages/DefaultContainerService/res/values-en-rIN/strings.xml
deleted file mode 100644
index 216d715996c7..000000000000
--- a/packages/DefaultContainerService/res/values-en-rIN/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"Package Access Helper"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-en-rXC/strings.xml b/packages/DefaultContainerService/res/values-en-rXC/strings.xml
deleted file mode 100644
index 913f4bd1fc91..000000000000
--- a/packages/DefaultContainerService/res/values-en-rXC/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"‎‏‎‎‎‎‎‏‎‏‏‏‎‎‎‎‎‎‏‎‎‏‎‎‎‎‏‏‏‏‏‏‏‏‎‎‎‎‏‏‎‎‏‏‎‎‎‎‎‏‏‎‏‏‏‎‏‏‏‏‏‏‎‏‏‎‏‎‎‎‏‎‏‎‎‎‎‎‎‎‎‏‎‎‎‏‎‎‎‏‏‎‎‎‎‏‎Package Access Helper‎‏‎‎‏‎"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-es-rUS/strings.xml b/packages/DefaultContainerService/res/values-es-rUS/strings.xml
deleted file mode 100644
index 19fd6552bac4..000000000000
--- a/packages/DefaultContainerService/res/values-es-rUS/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"Asist. acceso al paquete"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-es/strings.xml b/packages/DefaultContainerService/res/values-es/strings.xml
deleted file mode 100644
index 022c461379d1..000000000000
--- a/packages/DefaultContainerService/res/values-es/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"Ayudante acceso a paquete"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-et/strings.xml b/packages/DefaultContainerService/res/values-et/strings.xml
deleted file mode 100644
index 216d715996c7..000000000000
--- a/packages/DefaultContainerService/res/values-et/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"Package Access Helper"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-eu/strings.xml b/packages/DefaultContainerService/res/values-eu/strings.xml
deleted file mode 100644
index 4df24e12a63a..000000000000
--- a/packages/DefaultContainerService/res/values-eu/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"Paketeak atzitzeko laguntzailea"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-fa/strings.xml b/packages/DefaultContainerService/res/values-fa/strings.xml
deleted file mode 100644
index 8c1a5d462d13..000000000000
--- a/packages/DefaultContainerService/res/values-fa/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"راهنمای دسترسی به بسته"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-fi/strings.xml b/packages/DefaultContainerService/res/values-fi/strings.xml
deleted file mode 100644
index 216d715996c7..000000000000
--- a/packages/DefaultContainerService/res/values-fi/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"Package Access Helper"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-fr-rCA/strings.xml b/packages/DefaultContainerService/res/values-fr-rCA/strings.xml
deleted file mode 100644
index 353d0b47841f..000000000000
--- a/packages/DefaultContainerService/res/values-fr-rCA/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"Aide Accès au paquet"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-fr/strings.xml b/packages/DefaultContainerService/res/values-fr/strings.xml
deleted file mode 100644
index 216d715996c7..000000000000
--- a/packages/DefaultContainerService/res/values-fr/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"Package Access Helper"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-gl/strings.xml b/packages/DefaultContainerService/res/values-gl/strings.xml
deleted file mode 100644
index c1ae01845fdb..000000000000
--- a/packages/DefaultContainerService/res/values-gl/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"Asistente acceso paquetes"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-gu/strings.xml b/packages/DefaultContainerService/res/values-gu/strings.xml
deleted file mode 100644
index cbebdd26704d..000000000000
--- a/packages/DefaultContainerService/res/values-gu/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"પેકેજ અ‍ૅક્સેસ હેલ્પર"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-hi/strings.xml b/packages/DefaultContainerService/res/values-hi/strings.xml
deleted file mode 100644
index ad8537931413..000000000000
--- a/packages/DefaultContainerService/res/values-hi/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"पैकेज पहुंच सहायक"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-hr/strings.xml b/packages/DefaultContainerService/res/values-hr/strings.xml
deleted file mode 100644
index 56b7db12b48e..000000000000
--- a/packages/DefaultContainerService/res/values-hr/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"Pomoćnik pristupa paketu"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-hu/strings.xml b/packages/DefaultContainerService/res/values-hu/strings.xml
deleted file mode 100644
index 78ca9fa1b1ac..000000000000
--- a/packages/DefaultContainerService/res/values-hu/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"Csomaghozzáférés-segéd"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-hy/strings.xml b/packages/DefaultContainerService/res/values-hy/strings.xml
deleted file mode 100644
index 1e2f587e55e3..000000000000
--- a/packages/DefaultContainerService/res/values-hy/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"Փաթեթի մուտքի օժանդակող"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-in/strings.xml b/packages/DefaultContainerService/res/values-in/strings.xml
deleted file mode 100644
index da6bf8bf204c..000000000000
--- a/packages/DefaultContainerService/res/values-in/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"Pembantu Akses Paket"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-is/strings.xml b/packages/DefaultContainerService/res/values-is/strings.xml
deleted file mode 100644
index 41ca8278b5e4..000000000000
--- a/packages/DefaultContainerService/res/values-is/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"Pakkaaðgangshjálp"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-it/strings.xml b/packages/DefaultContainerService/res/values-it/strings.xml
deleted file mode 100644
index 216d715996c7..000000000000
--- a/packages/DefaultContainerService/res/values-it/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"Package Access Helper"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-iw/strings.xml b/packages/DefaultContainerService/res/values-iw/strings.xml
deleted file mode 100644
index 4a93179d6333..000000000000
--- a/packages/DefaultContainerService/res/values-iw/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"מסייע בגישה לחבילה"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-ja/strings.xml b/packages/DefaultContainerService/res/values-ja/strings.xml
deleted file mode 100644
index 2f57e4eda475..000000000000
--- a/packages/DefaultContainerService/res/values-ja/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"パッケージアクセス支援ツール"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-ka/strings.xml b/packages/DefaultContainerService/res/values-ka/strings.xml
deleted file mode 100644
index 216d715996c7..000000000000
--- a/packages/DefaultContainerService/res/values-ka/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"Package Access Helper"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-kk/strings.xml b/packages/DefaultContainerService/res/values-kk/strings.xml
deleted file mode 100644
index 216d715996c7..000000000000
--- a/packages/DefaultContainerService/res/values-kk/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"Package Access Helper"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-km/strings.xml b/packages/DefaultContainerService/res/values-km/strings.xml
deleted file mode 100644
index 1006d56a0c9e..000000000000
--- a/packages/DefaultContainerService/res/values-km/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"កម្មវិធី​ជំនួយ​ចូល​ដំណើរការ​កញ្ចប់"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-kn/strings.xml b/packages/DefaultContainerService/res/values-kn/strings.xml
deleted file mode 100644
index 13af0cc46a8d..000000000000
--- a/packages/DefaultContainerService/res/values-kn/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"ಪ್ಯಾಕೇಜ್ ಪ್ರವೇಶದ ಸಹಾಯಕ"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-ko/strings.xml b/packages/DefaultContainerService/res/values-ko/strings.xml
deleted file mode 100644
index 03049728fbc2..000000000000
--- a/packages/DefaultContainerService/res/values-ko/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"패키지 액세스 도움말"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-ky/strings.xml b/packages/DefaultContainerService/res/values-ky/strings.xml
deleted file mode 100644
index d91e67ddd0a1..000000000000
--- a/packages/DefaultContainerService/res/values-ky/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"Топтомго уруксат берүү"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-lo/strings.xml b/packages/DefaultContainerService/res/values-lo/strings.xml
deleted file mode 100644
index 216d715996c7..000000000000
--- a/packages/DefaultContainerService/res/values-lo/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"Package Access Helper"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-lt/strings.xml b/packages/DefaultContainerService/res/values-lt/strings.xml
deleted file mode 100644
index 3faf8cc36983..000000000000
--- a/packages/DefaultContainerService/res/values-lt/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"Pak. pagalb. prm. prieiga"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-lv/strings.xml b/packages/DefaultContainerService/res/values-lv/strings.xml
deleted file mode 100644
index 63beee537df1..000000000000
--- a/packages/DefaultContainerService/res/values-lv/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"Pakotnes piekļuves palīgs"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-mk/strings.xml b/packages/DefaultContainerService/res/values-mk/strings.xml
deleted file mode 100644
index 875cc2f9b8f4..000000000000
--- a/packages/DefaultContainerService/res/values-mk/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"Помошник за пристап кон пакет"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-ml/strings.xml b/packages/DefaultContainerService/res/values-ml/strings.xml
deleted file mode 100644
index 7bb450f5d532..000000000000
--- a/packages/DefaultContainerService/res/values-ml/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"പാക്കേജ് ആക്‌സസ്സ് സഹായി"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-mn/strings.xml b/packages/DefaultContainerService/res/values-mn/strings.xml
deleted file mode 100644
index d9fe6477ca11..000000000000
--- a/packages/DefaultContainerService/res/values-mn/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"Багц хандалтын тусламж"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-mr/strings.xml b/packages/DefaultContainerService/res/values-mr/strings.xml
deleted file mode 100644
index 898a37887199..000000000000
--- a/packages/DefaultContainerService/res/values-mr/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"पॅकेज प्रवेश मदतनीस"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-ms/strings.xml b/packages/DefaultContainerService/res/values-ms/strings.xml
deleted file mode 100644
index 77d79273cc0c..000000000000
--- a/packages/DefaultContainerService/res/values-ms/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"Pembantu Akses Pakej"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-my/strings.xml b/packages/DefaultContainerService/res/values-my/strings.xml
deleted file mode 100644
index 8dfb72b1ce60..000000000000
--- a/packages/DefaultContainerService/res/values-my/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"Packageအသုံးပြုကူညီသူ"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-nb/strings.xml b/packages/DefaultContainerService/res/values-nb/strings.xml
deleted file mode 100644
index 637f54d707c5..000000000000
--- a/packages/DefaultContainerService/res/values-nb/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"Hjelpeprogram for pakketilgang"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-ne/strings.xml b/packages/DefaultContainerService/res/values-ne/strings.xml
deleted file mode 100644
index 5b70ce11a44d..000000000000
--- a/packages/DefaultContainerService/res/values-ne/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"प्याकेज पहुँच सहयोगी"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-nl/strings.xml b/packages/DefaultContainerService/res/values-nl/strings.xml
deleted file mode 100644
index 2501099fa00d..000000000000
--- a/packages/DefaultContainerService/res/values-nl/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"Helper pakkettoegang"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-or/strings.xml b/packages/DefaultContainerService/res/values-or/strings.xml
deleted file mode 100644
index 394c2782921a..000000000000
--- a/packages/DefaultContainerService/res/values-or/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"ପ୍ୟାକେଜ୍‌ ଆକ୍ସେସ୍‍ ସହାୟକ"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-pa/strings.xml b/packages/DefaultContainerService/res/values-pa/strings.xml
deleted file mode 100644
index a784a0688a60..000000000000
--- a/packages/DefaultContainerService/res/values-pa/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"ਪੈਕੇਜ ਪਹੁੰਚ ਸਹਾਇਕ"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-pl/strings.xml b/packages/DefaultContainerService/res/values-pl/strings.xml
deleted file mode 100644
index 216d715996c7..000000000000
--- a/packages/DefaultContainerService/res/values-pl/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"Package Access Helper"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-pt-rBR/strings.xml b/packages/DefaultContainerService/res/values-pt-rBR/strings.xml
deleted file mode 100644
index 5fbd949339a7..000000000000
--- a/packages/DefaultContainerService/res/values-pt-rBR/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"Assistente de pacote"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-pt-rPT/strings.xml b/packages/DefaultContainerService/res/values-pt-rPT/strings.xml
deleted file mode 100644
index 647334b1196b..000000000000
--- a/packages/DefaultContainerService/res/values-pt-rPT/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"Ajuda acesso a pacotes"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-pt/strings.xml b/packages/DefaultContainerService/res/values-pt/strings.xml
deleted file mode 100644
index 5fbd949339a7..000000000000
--- a/packages/DefaultContainerService/res/values-pt/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"Assistente de pacote"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-ro/strings.xml b/packages/DefaultContainerService/res/values-ro/strings.xml
deleted file mode 100644
index 69de00f1f1e0..000000000000
--- a/packages/DefaultContainerService/res/values-ro/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"Ajutor accesare pachet"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-ru/strings.xml b/packages/DefaultContainerService/res/values-ru/strings.xml
deleted file mode 100644
index ccb0c5388101..000000000000
--- a/packages/DefaultContainerService/res/values-ru/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"Мастер доступа к пакетам"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-si/strings.xml b/packages/DefaultContainerService/res/values-si/strings.xml
deleted file mode 100644
index 522ec6cde70b..000000000000
--- a/packages/DefaultContainerService/res/values-si/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"පැකේජ ප්‍රවේශ උදව්කරු"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-sk/strings.xml b/packages/DefaultContainerService/res/values-sk/strings.xml
deleted file mode 100644
index 216d715996c7..000000000000
--- a/packages/DefaultContainerService/res/values-sk/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"Package Access Helper"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-sl/strings.xml b/packages/DefaultContainerService/res/values-sl/strings.xml
deleted file mode 100644
index af2b13cc94c8..000000000000
--- a/packages/DefaultContainerService/res/values-sl/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"Pomočnik za dostop do paketa"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-sq/strings.xml b/packages/DefaultContainerService/res/values-sq/strings.xml
deleted file mode 100644
index d352edf1e8c5..000000000000
--- a/packages/DefaultContainerService/res/values-sq/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"Ndihmësi i qasjes në paketë"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-sr/strings.xml b/packages/DefaultContainerService/res/values-sr/strings.xml
deleted file mode 100644
index b5d77ac2c5fa..000000000000
--- a/packages/DefaultContainerService/res/values-sr/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"Помоћник за приступ пакету"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-sv/strings.xml b/packages/DefaultContainerService/res/values-sv/strings.xml
deleted file mode 100644
index 097a709612a1..000000000000
--- a/packages/DefaultContainerService/res/values-sv/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"Hjälp med paketåtkomst"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-sw/strings.xml b/packages/DefaultContainerService/res/values-sw/strings.xml
deleted file mode 100644
index 8d1f515052eb..000000000000
--- a/packages/DefaultContainerService/res/values-sw/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"Kisaidizi cha Kufikia Furushi"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-ta/strings.xml b/packages/DefaultContainerService/res/values-ta/strings.xml
deleted file mode 100644
index a7ba82d0a4b8..000000000000
--- a/packages/DefaultContainerService/res/values-ta/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"தொகுப்பு அணுகலுக்கான உதவி"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-te/strings.xml b/packages/DefaultContainerService/res/values-te/strings.xml
deleted file mode 100644
index 5be53e5409e6..000000000000
--- a/packages/DefaultContainerService/res/values-te/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"ప్యాకేజీ యాక్సెస్ సహాయకం"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-th/strings.xml b/packages/DefaultContainerService/res/values-th/strings.xml
deleted file mode 100644
index 621d7ed31500..000000000000
--- a/packages/DefaultContainerService/res/values-th/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"ตัวช่วยเหลือของการเข้าถึงแพ็กเกจ"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-tl/strings.xml b/packages/DefaultContainerService/res/values-tl/strings.xml
deleted file mode 100644
index 216d715996c7..000000000000
--- a/packages/DefaultContainerService/res/values-tl/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"Package Access Helper"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-tr/strings.xml b/packages/DefaultContainerService/res/values-tr/strings.xml
deleted file mode 100644
index 12ea67455640..000000000000
--- a/packages/DefaultContainerService/res/values-tr/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"Paket Erişim Yardımcısı"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-uk/strings.xml b/packages/DefaultContainerService/res/values-uk/strings.xml
deleted file mode 100644
index 1226bd4cd16d..000000000000
--- a/packages/DefaultContainerService/res/values-uk/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"Майстер доступу до пакетів"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-ur/strings.xml b/packages/DefaultContainerService/res/values-ur/strings.xml
deleted file mode 100644
index 3872b86390d3..000000000000
--- a/packages/DefaultContainerService/res/values-ur/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"پیکیج رسائی کا مددگار"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-uz/strings.xml b/packages/DefaultContainerService/res/values-uz/strings.xml
deleted file mode 100644
index 216d715996c7..000000000000
--- a/packages/DefaultContainerService/res/values-uz/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"Package Access Helper"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-vi/strings.xml b/packages/DefaultContainerService/res/values-vi/strings.xml
deleted file mode 100644
index 885946cc34de..000000000000
--- a/packages/DefaultContainerService/res/values-vi/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"Trình trợ giúp truy cập gói"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-zh-rCN/strings.xml b/packages/DefaultContainerService/res/values-zh-rCN/strings.xml
deleted file mode 100644
index 2bcc6b756a75..000000000000
--- a/packages/DefaultContainerService/res/values-zh-rCN/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"软件包权限帮助程序"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-zh-rHK/strings.xml b/packages/DefaultContainerService/res/values-zh-rHK/strings.xml
deleted file mode 100644
index 9a43509436fb..000000000000
--- a/packages/DefaultContainerService/res/values-zh-rHK/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"套件存取輔助程式"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-zh-rTW/strings.xml b/packages/DefaultContainerService/res/values-zh-rTW/strings.xml
deleted file mode 100644
index 9a43509436fb..000000000000
--- a/packages/DefaultContainerService/res/values-zh-rTW/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"套件存取輔助程式"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values-zu/strings.xml b/packages/DefaultContainerService/res/values-zu/strings.xml
deleted file mode 100644
index d50116523c22..000000000000
--- a/packages/DefaultContainerService/res/values-zu/strings.xml
+++ /dev/null
@@ -1,24 +0,0 @@
-<?xml version="1.0" encoding="UTF-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
- -->
-
-<resources xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <string name="service_name" msgid="4841491635055379553">"Umsizi Wokufinyelela Kwiphakheji"</string>
-</resources>
diff --git a/packages/DefaultContainerService/res/values/strings.xml b/packages/DefaultContainerService/res/values/strings.xml
deleted file mode 100644
index ffd6b591cc4c..000000000000
--- a/packages/DefaultContainerService/res/values/strings.xml
+++ /dev/null
@@ -1,23 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<!--
-/*
-**
-** Copyright 2008, The Android Open Source Project
-**
-** Licensed under the Apache License, Version 2.0 (the "License");
-** you may not use this file except in compliance with the License.
-** You may obtain a copy of the License at
-**
-** http://www.apache.org/licenses/LICENSE-2.0
-**
-** Unless required by applicable law or agreed to in writing, software
-** distributed under the License is distributed on an "AS IS" BASIS,
-** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
-** See the License for the specific language governing permissions and
-** limitations under the License.
-*/
--->
-<resources xmlns:xliff="urn:oasis:names:tc:xliff:document:1.2">
- <!-- service name [CHAR LIMIT=25] -->
- <string name="service_name">Package Access Helper</string>
-</resources>
diff --git a/packages/DefaultContainerService/src/com/android/defcontainer/DefaultContainerService.java b/packages/DefaultContainerService/src/com/android/defcontainer/DefaultContainerService.java
deleted file mode 100644
index 97a67c202739..000000000000
--- a/packages/DefaultContainerService/src/com/android/defcontainer/DefaultContainerService.java
+++ /dev/null
@@ -1,211 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.defcontainer;
-
-import android.app.Service;
-import android.content.Context;
-import android.content.Intent;
-import android.content.pm.PackageInfoLite;
-import android.content.pm.PackageManager;
-import android.content.pm.PackageParser;
-import android.content.pm.PackageParser.PackageLite;
-import android.content.pm.PackageParser.PackageParserException;
-import android.content.res.ObbInfo;
-import android.content.res.ObbScanner;
-import android.os.Binder;
-import android.os.FileUtils;
-import android.os.IBinder;
-import android.os.ParcelFileDescriptor;
-import android.os.RemoteException;
-import android.util.Slog;
-
-import com.android.internal.app.IMediaContainerService;
-import com.android.internal.content.PackageHelper;
-import com.android.internal.os.IParcelFileDescriptorFactory;
-import com.android.internal.util.ArrayUtils;
-
-import libcore.io.IoUtils;
-
-import java.io.File;
-import java.io.FileInputStream;
-import java.io.IOException;
-import java.io.InputStream;
-import java.io.OutputStream;
-
-/**
- * Service that offers to inspect and copy files that may reside on removable
- * storage. This is designed to prevent the system process from holding onto
- * open files that cause the kernel to kill it when the underlying device is
- * removed.
- */
-public class DefaultContainerService extends Service {
- private static final String TAG = "DefContainer";
-
- // TODO: migrate native code unpacking to always be a derivative work
-
- private IMediaContainerService.Stub mBinder = new IMediaContainerService.Stub() {
- /**
- * Copy package to the target location.
- *
- * @param packagePath absolute path to the package to be copied. Can be
- * a single monolithic APK file or a cluster directory
- * containing one or more APKs.
- * @return returns status code according to those in
- * {@link PackageManager}
- */
- @Override
- public int copyPackage(String packagePath, IParcelFileDescriptorFactory target) {
- if (packagePath == null || target == null) {
- return PackageManager.INSTALL_FAILED_INVALID_URI;
- }
-
- PackageLite pkg = null;
- try {
- final File packageFile = new File(packagePath);
- pkg = PackageParser.parsePackageLite(packageFile, 0);
- return copyPackageInner(pkg, target);
- } catch (PackageParserException | IOException | RemoteException e) {
- Slog.w(TAG, "Failed to copy package at " + packagePath + ": " + e);
- return PackageManager.INSTALL_FAILED_INSUFFICIENT_STORAGE;
- }
- }
-
- /**
- * Parse given package and return minimal details.
- *
- * @param packagePath absolute path to the package to be copied. Can be
- * a single monolithic APK file or a cluster directory
- * containing one or more APKs.
- */
- @Override
- public PackageInfoLite getMinimalPackageInfo(String packagePath, int flags,
- String abiOverride) {
- final Context context = DefaultContainerService.this;
-
- PackageInfoLite ret = new PackageInfoLite();
- if (packagePath == null) {
- Slog.i(TAG, "Invalid package file " + packagePath);
- ret.recommendedInstallLocation = PackageHelper.RECOMMEND_FAILED_INVALID_APK;
- return ret;
- }
-
- final File packageFile = new File(packagePath);
- final PackageParser.PackageLite pkg;
- final long sizeBytes;
- try {
- pkg = PackageParser.parsePackageLite(packageFile, 0);
- sizeBytes = PackageHelper.calculateInstalledSize(pkg, abiOverride);
- } catch (PackageParserException | IOException e) {
- Slog.w(TAG, "Failed to parse package at " + packagePath + ": " + e);
-
- if (!packageFile.exists()) {
- ret.recommendedInstallLocation = PackageHelper.RECOMMEND_FAILED_INVALID_URI;
- } else {
- ret.recommendedInstallLocation = PackageHelper.RECOMMEND_FAILED_INVALID_APK;
- }
-
- return ret;
- }
-
- final int recommendedInstallLocation;
- final long token = Binder.clearCallingIdentity();
- try {
- recommendedInstallLocation = PackageHelper.resolveInstallLocation(context,
- pkg.packageName, pkg.installLocation, sizeBytes, flags);
- } finally {
- Binder.restoreCallingIdentity(token);
- }
-
- ret.packageName = pkg.packageName;
- ret.splitNames = pkg.splitNames;
- ret.versionCode = pkg.versionCode;
- ret.versionCodeMajor = pkg.versionCodeMajor;
- ret.baseRevisionCode = pkg.baseRevisionCode;
- ret.splitRevisionCodes = pkg.splitRevisionCodes;
- ret.installLocation = pkg.installLocation;
- ret.verifiers = pkg.verifiers;
- ret.recommendedInstallLocation = recommendedInstallLocation;
- ret.multiArch = pkg.multiArch;
-
- return ret;
- }
-
- @Override
- public ObbInfo getObbInfo(String filename) {
- try {
- return ObbScanner.getObbInfo(filename);
- } catch (IOException e) {
- Slog.d(TAG, "Couldn't get OBB info for " + filename);
- return null;
- }
- }
-
- /**
- * Calculate estimated footprint of given package post-installation.
- *
- * @param packagePath absolute path to the package to be copied. Can be
- * a single monolithic APK file or a cluster directory
- * containing one or more APKs.
- */
- @Override
- public long calculateInstalledSize(String packagePath, String abiOverride)
- throws RemoteException {
- final File packageFile = new File(packagePath);
- final PackageParser.PackageLite pkg;
- try {
- pkg = PackageParser.parsePackageLite(packageFile, 0);
- return PackageHelper.calculateInstalledSize(pkg, abiOverride);
- } catch (PackageParserException | IOException e) {
- Slog.w(TAG, "Failed to calculate installed size: " + e);
- return Long.MAX_VALUE;
- }
- }
- };
-
- @Override
- public IBinder onBind(Intent intent) {
- return mBinder;
- }
-
- private int copyPackageInner(PackageLite pkg, IParcelFileDescriptorFactory target)
- throws IOException, RemoteException {
- copyFile(pkg.baseCodePath, target, "base.apk");
- if (!ArrayUtils.isEmpty(pkg.splitNames)) {
- for (int i = 0; i < pkg.splitNames.length; i++) {
- copyFile(pkg.splitCodePaths[i], target, "split_" + pkg.splitNames[i] + ".apk");
- }
- }
-
- return PackageManager.INSTALL_SUCCEEDED;
- }
-
- private void copyFile(String sourcePath, IParcelFileDescriptorFactory target, String targetName)
- throws IOException, RemoteException {
- Slog.d(TAG, "Copying " + sourcePath + " to " + targetName);
- InputStream in = null;
- OutputStream out = null;
- try {
- in = new FileInputStream(sourcePath);
- out = new ParcelFileDescriptor.AutoCloseOutputStream(
- target.open(targetName, ParcelFileDescriptor.MODE_READ_WRITE));
- FileUtils.copy(in, out);
- } finally {
- IoUtils.closeQuietly(out);
- IoUtils.closeQuietly(in);
- }
- }
-}
diff --git a/packages/DefaultContainerService/src/com/android/defcontainer/MeasurementUtils.java b/packages/DefaultContainerService/src/com/android/defcontainer/MeasurementUtils.java
deleted file mode 100644
index 6f5f53bfa440..000000000000
--- a/packages/DefaultContainerService/src/com/android/defcontainer/MeasurementUtils.java
+++ /dev/null
@@ -1,29 +0,0 @@
-/*
- * Copyright (C) 2010 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.defcontainer;
-
-public class MeasurementUtils {
- static {
- System.loadLibrary("defcontainer_jni");
- }
-
- public static long measureDirectory(String path) {
- return native_measureDirectory(path);
- }
-
- private native static long native_measureDirectory(String path);
-}
diff --git a/packages/ExtServices/src/android/ext/services/autofill/EditDistanceScorer.java b/packages/ExtServices/src/android/ext/services/autofill/EditDistanceScorer.java
index 6a47901aa58e..196257162058 100644
--- a/packages/ExtServices/src/android/ext/services/autofill/EditDistanceScorer.java
+++ b/packages/ExtServices/src/android/ext/services/autofill/EditDistanceScorer.java
@@ -83,7 +83,7 @@ final class EditDistanceScorer {
* the edit distance is at least as big as the {@code max} parameter
*/
// Note: copied verbatim from com.android.tools.lint.detector.api.LintUtils.java
- private static int editDistance(@NonNull String s, @NonNull String t, int max) {
+ public static int editDistance(@NonNull String s, @NonNull String t, int max) {
if (s.equals(t)) {
return 0;
}
diff --git a/packages/ExtServices/tests/src/android/ext/services/autofill/EditDistanceScorerTest.java b/packages/ExtServices/tests/src/android/ext/services/autofill/EditDistanceScorerTest.java
index 9b9d4be59929..3d754f7fa9d9 100644
--- a/packages/ExtServices/tests/src/android/ext/services/autofill/EditDistanceScorerTest.java
+++ b/packages/ExtServices/tests/src/android/ext/services/autofill/EditDistanceScorerTest.java
@@ -16,6 +16,7 @@
package android.ext.services.autofill;
import static android.ext.services.autofill.EditDistanceScorer.calculateScore;
+import static android.ext.services.autofill.EditDistanceScorer.editDistance;
import static com.google.common.truth.Truth.assertThat;
@@ -73,9 +74,12 @@ public class EditDistanceScorerTest {
assertFloat(calculateScore(AutofillValue.forText("DUDx"), "Dude"), 0.75F);
}
+ @Test
+ public void testEditDistance_maxDistance() {
+ assertFloat(editDistance("testing", "b", 4), Integer.MAX_VALUE);
+ }
+
public static void assertFloat(float actualValue, float expectedValue) {
assertThat(actualValue).isWithin(0.01F).of(expectedValue);
}
-
-
}
diff --git a/packages/NetworkStack/src/android/net/NetworkStackIpMemoryStore.java b/packages/NetworkStack/src/android/net/NetworkStackIpMemoryStore.java
index 475f8261fdc1..41715b2a4798 100644
--- a/packages/NetworkStack/src/android/net/NetworkStackIpMemoryStore.java
+++ b/packages/NetworkStack/src/android/net/NetworkStackIpMemoryStore.java
@@ -19,6 +19,9 @@ package android.net;
import android.annotation.NonNull;
import android.content.Context;
+import java.util.concurrent.ExecutionException;
+import java.util.function.Consumer;
+
/**
* service used to communicate with the ip memory store service in network stack,
* which is running in the same module.
@@ -35,8 +38,7 @@ public class NetworkStackIpMemoryStore extends IpMemoryStoreClient {
}
@Override
- @NonNull
- protected IIpMemoryStore getService() {
- return mService;
+ protected void runWhenServiceReady(Consumer<IIpMemoryStore> cb) throws ExecutionException {
+ cb.accept(mService);
}
}
diff --git a/packages/NetworkStack/src/com/android/server/connectivity/NetworkMonitor.java b/packages/NetworkStack/src/com/android/server/connectivity/NetworkMonitor.java
index bacec78e5699..d6355bc111c2 100644
--- a/packages/NetworkStack/src/com/android/server/connectivity/NetworkMonitor.java
+++ b/packages/NetworkStack/src/com/android/server/connectivity/NetworkMonitor.java
@@ -279,8 +279,8 @@ public class NetworkMonitor extends StateMachine {
private final Context mContext;
private final INetworkMonitorCallbacks mCallback;
+ private final Network mCleartextDnsNetwork;
private final Network mNetwork;
- private final Network mNonPrivateDnsBypassNetwork;
private final TelephonyManager mTelephonyManager;
private final WifiManager mWifiManager;
private final ConnectivityManager mCm;
@@ -370,8 +370,8 @@ public class NetworkMonitor extends StateMachine {
mCallback = cb;
mDependencies = deps;
mDetectionStatsUtils = detectionStatsUtils;
- mNonPrivateDnsBypassNetwork = network;
- mNetwork = deps.getPrivateDnsBypassNetwork(network);
+ mNetwork = network;
+ mCleartextDnsNetwork = deps.getPrivateDnsBypassNetwork(network);
mTelephonyManager = (TelephonyManager) context.getSystemService(Context.TELEPHONY_SERVICE);
mWifiManager = (WifiManager) context.getSystemService(Context.WIFI_SERVICE);
mCm = (ConnectivityManager) context.getSystemService(Context.CONNECTIVITY_SERVICE);
@@ -496,7 +496,7 @@ public class NetworkMonitor extends StateMachine {
@Override
protected void log(String s) {
- if (DBG) Log.d(TAG + "/" + mNetwork.toString(), s);
+ if (DBG) Log.d(TAG + "/" + mCleartextDnsNetwork.toString(), s);
}
private void validationLog(int probeType, Object url, String msg) {
@@ -769,7 +769,7 @@ public class NetworkMonitor extends StateMachine {
case CMD_LAUNCH_CAPTIVE_PORTAL_APP:
final Bundle appExtras = new Bundle();
// OneAddressPerFamilyNetwork is not parcelable across processes.
- final Network network = new Network(mNetwork);
+ final Network network = new Network(mCleartextDnsNetwork);
appExtras.putParcelable(ConnectivityManager.EXTRA_NETWORK, network);
final CaptivePortalProbeResult probeRes = mLastPortalProbeResult;
appExtras.putString(EXTRA_CAPTIVE_PORTAL_URL, probeRes.detectUrl);
@@ -881,7 +881,7 @@ public class NetworkMonitor extends StateMachine {
CustomIntentReceiver(String action, int token, int what) {
mToken = token;
mWhat = what;
- mAction = action + "_" + mNetwork.getNetworkHandle() + "_" + token;
+ mAction = action + "_" + mCleartextDnsNetwork.getNetworkHandle() + "_" + token;
mContext.registerReceiver(this, new IntentFilter(mAction));
}
public PendingIntent getPendingIntent() {
@@ -994,7 +994,8 @@ public class NetworkMonitor extends StateMachine {
private void resolveStrictModeHostname() {
try {
// Do a blocking DNS resolution using the network-assigned nameservers.
- final InetAddress[] ips = mNetwork.getAllByName(mPrivateDnsProviderHostname);
+ final InetAddress[] ips = mCleartextDnsNetwork.getAllByName(
+ mPrivateDnsProviderHostname);
mPrivateDnsConfig = new PrivateDnsConfig(mPrivateDnsProviderHostname, ips);
validationLog("Strict mode hostname resolved: " + mPrivateDnsConfig);
} catch (UnknownHostException uhe) {
@@ -1033,7 +1034,7 @@ public class NetworkMonitor extends StateMachine {
+ oneTimeHostnameSuffix;
final Stopwatch watch = new Stopwatch().start();
try {
- final InetAddress[] ips = mNonPrivateDnsBypassNetwork.getAllByName(host);
+ final InetAddress[] ips = mNetwork.getAllByName(host);
final long time = watch.stop();
final String strIps = Arrays.toString(ips);
final boolean success = (ips != null && ips.length > 0);
@@ -1506,7 +1507,7 @@ public class NetworkMonitor extends StateMachine {
final int oldTag = TrafficStats.getAndSetThreadStatsTag(
TrafficStatsConstants.TAG_SYSTEM_PROBE);
- mDependencies.getDnsResolver().query(mNetwork, host, DnsResolver.FLAG_EMPTY,
+ mDependencies.getDnsResolver().query(mCleartextDnsNetwork, host, DnsResolver.FLAG_EMPTY,
r -> r.run() /* executor */, null /* cancellationSignal */, callback);
TrafficStats.setThreadStatsTag(oldTag);
@@ -1565,7 +1566,7 @@ public class NetworkMonitor extends StateMachine {
final int oldTag = TrafficStats.getAndSetThreadStatsTag(
TrafficStatsConstants.TAG_SYSTEM_PROBE);
try {
- urlConnection = (HttpURLConnection) mNetwork.openConnection(url);
+ urlConnection = (HttpURLConnection) mCleartextDnsNetwork.openConnection(url);
urlConnection.setInstanceFollowRedirects(probeType == ValidationProbeEvent.PROBE_PAC);
urlConnection.setConnectTimeout(SOCKET_TIMEOUT_MS);
urlConnection.setReadTimeout(SOCKET_TIMEOUT_MS);
@@ -1814,7 +1815,7 @@ public class NetworkMonitor extends StateMachine {
private void logNetworkEvent(int evtype) {
int[] transports = mNetworkCapabilities.getTransportTypes();
- mMetricsLog.log(mNetwork, transports, new NetworkEvent(evtype));
+ mMetricsLog.log(mCleartextDnsNetwork, transports, new NetworkEvent(evtype));
}
private int networkEventType(ValidationStage s, EvaluationResult r) {
@@ -1836,7 +1837,7 @@ public class NetworkMonitor extends StateMachine {
private void maybeLogEvaluationResult(int evtype) {
if (mEvaluationTimer.isRunning()) {
int[] transports = mNetworkCapabilities.getTransportTypes();
- mMetricsLog.log(mNetwork, transports,
+ mMetricsLog.log(mCleartextDnsNetwork, transports,
new NetworkEvent(evtype, mEvaluationTimer.stop()));
mEvaluationTimer.reset();
}
@@ -1850,7 +1851,7 @@ public class NetworkMonitor extends StateMachine {
.setReturnCode(probeResult)
.setDurationMs(durationMs)
.build();
- mMetricsLog.log(mNetwork, transports, ev);
+ mMetricsLog.log(mCleartextDnsNetwork, transports, ev);
}
@VisibleForTesting
diff --git a/packages/NetworkStack/tests/src/com/android/server/connectivity/NetworkMonitorTest.java b/packages/NetworkStack/tests/src/com/android/server/connectivity/NetworkMonitorTest.java
index 0dc1cbf8a984..6f5c27edb9d5 100644
--- a/packages/NetworkStack/tests/src/com/android/server/connectivity/NetworkMonitorTest.java
+++ b/packages/NetworkStack/tests/src/com/android/server/connectivity/NetworkMonitorTest.java
@@ -42,10 +42,10 @@ import static org.mockito.ArgumentMatchers.eq;
import static org.mockito.Mockito.any;
import static org.mockito.Mockito.anyInt;
import static org.mockito.Mockito.doAnswer;
-import static org.mockito.Mockito.doNothing;
import static org.mockito.Mockito.doReturn;
import static org.mockito.Mockito.doThrow;
import static org.mockito.Mockito.never;
+import static org.mockito.Mockito.reset;
import static org.mockito.Mockito.timeout;
import static org.mockito.Mockito.times;
import static org.mockito.Mockito.verify;
@@ -66,6 +66,7 @@ import android.net.NetworkCapabilities;
import android.net.NetworkInfo;
import android.net.captiveportal.CaptivePortalProbeResult;
import android.net.metrics.IpConnectivityLog;
+import android.net.shared.PrivateDnsConfig;
import android.net.util.SharedLog;
import android.net.wifi.WifiInfo;
import android.net.wifi.WifiManager;
@@ -73,6 +74,7 @@ import android.os.Bundle;
import android.os.ConditionVariable;
import android.os.Handler;
import android.os.Looper;
+import android.os.Process;
import android.os.RemoteException;
import android.os.SystemClock;
import android.provider.Settings;
@@ -131,7 +133,8 @@ public class NetworkMonitorTest {
private @Mock Random mRandom;
private @Mock NetworkMonitor.Dependencies mDependencies;
private @Mock INetworkMonitorCallbacks mCallbacks;
- private @Spy Network mNetwork = new Network(TEST_NETID);
+ private @Spy Network mCleartextDnsNetwork = new Network(TEST_NETID);
+ private @Mock Network mNetwork;
private @Mock DataStallStatsUtils mDataStallStatsUtils;
private @Mock WifiInfo mWifiInfo;
private @Captor ArgumentCaptor<String> mNetworkTestedRedirectUrlCaptor;
@@ -166,35 +169,97 @@ public class NetworkMonitorTest {
private static final NetworkCapabilities NO_INTERNET_CAPABILITIES = new NetworkCapabilities()
.addTransportType(NetworkCapabilities.TRANSPORT_CELLULAR);
- private void setDnsAnswers(String[] answers) throws UnknownHostException {
- if (answers == null) {
- doThrow(new UnknownHostException()).when(mNetwork).getAllByName(any());
- doNothing().when(mDnsResolver).query(any(), any(), anyInt(), any(), any(), any());
- return;
+ /**
+ * Fakes DNS responses.
+ *
+ * Allows test methods to configure the IP addresses that will be resolved by
+ * Network#getAllByName and by DnsResolver#query.
+ */
+ class FakeDns {
+ private final ArrayMap<String, List<InetAddress>> mAnswers = new ArrayMap<>();
+ private boolean mNonBypassPrivateDnsWorking = true;
+
+ /** Whether DNS queries on mNonBypassPrivateDnsWorking should succeed. */
+ private void setNonBypassPrivateDnsWorking(boolean working) {
+ mNonBypassPrivateDnsWorking = working;
}
- List<InetAddress> answerList = new ArrayList<>();
- for (String answer : answers) {
- answerList.add(InetAddresses.parseNumericAddress(answer));
+ /** Clears all DNS entries. */
+ private synchronized void clearAll() {
+ mAnswers.clear();
}
- InetAddress[] answerArray = answerList.toArray(new InetAddress[0]);
- doReturn(answerArray).when(mNetwork).getAllByName(any());
+ /** Returns the answer for a given name on the given mock network. */
+ private synchronized List<InetAddress> getAnswer(Object mock, String hostname) {
+ if (mock == mNetwork && !mNonBypassPrivateDnsWorking) {
+ return null;
+ }
+ if (mAnswers.containsKey(hostname)) {
+ return mAnswers.get(hostname);
+ }
+ return mAnswers.get("*");
+ }
- doAnswer((invocation) -> {
- Executor executor = (Executor) invocation.getArgument(3);
- DnsResolver.Callback<List<InetAddress>> callback = invocation.getArgument(5);
- new Handler(Looper.getMainLooper()).post(() -> {
- executor.execute(() -> callback.onAnswer(answerList, 0));
- });
- return null;
- }).when(mDnsResolver).query(eq(mNetwork), any(), anyInt(), any(), any(), any());
+ /** Sets the answer for a given name. */
+ private synchronized void setAnswer(String hostname, String[] answer)
+ throws UnknownHostException {
+ if (answer == null) {
+ mAnswers.remove(hostname);
+ } else {
+ List<InetAddress> answerList = new ArrayList<>();
+ for (String addr : answer) {
+ answerList.add(InetAddresses.parseNumericAddress(addr));
+ }
+ mAnswers.put(hostname, answerList);
+ }
+ }
+
+ /** Simulates a getAllByName call for the specified name on the specified mock network. */
+ private InetAddress[] getAllByName(Object mock, String hostname)
+ throws UnknownHostException {
+ List<InetAddress> answer = getAnswer(mock, hostname);
+ if (answer == null || answer.size() == 0) {
+ throw new UnknownHostException(hostname);
+ }
+ return answer.toArray(new InetAddress[0]);
+ }
+
+ /** Starts mocking DNS queries. */
+ private void startMocking() throws UnknownHostException {
+ // Queries on mCleartextDnsNetwork using getAllByName.
+ doAnswer(invocation -> {
+ return getAllByName(invocation.getMock(), invocation.getArgument(0));
+ }).when(mCleartextDnsNetwork).getAllByName(any());
+
+ // Queries on mNetwork using getAllByName.
+ doAnswer(invocation -> {
+ return getAllByName(invocation.getMock(), invocation.getArgument(0));
+ }).when(mNetwork).getAllByName(any());
+
+ // Queries on mCleartextDnsNetwork using DnsResolver#query.
+ doAnswer(invocation -> {
+ String hostname = (String) invocation.getArgument(1);
+ Executor executor = (Executor) invocation.getArgument(3);
+ DnsResolver.Callback<List<InetAddress>> callback = invocation.getArgument(5);
+
+ List<InetAddress> answer = getAnswer(invocation.getMock(), hostname);
+ if (answer != null && answer.size() > 0) {
+ new Handler(Looper.getMainLooper()).post(() -> {
+ executor.execute(() -> callback.onAnswer(answer, 0));
+ });
+ }
+ // If no answers, do nothing. sendDnsProbeWithTimeout will time out and throw UHE.
+ return null;
+ }).when(mDnsResolver).query(any(), any(), anyInt(), any(), any(), any());
+ }
}
+ private FakeDns mFakeDns;
+
@Before
public void setUp() throws IOException {
MockitoAnnotations.initMocks(this);
- when(mDependencies.getPrivateDnsBypassNetwork(any())).thenReturn(mNetwork);
+ when(mDependencies.getPrivateDnsBypassNetwork(any())).thenReturn(mCleartextDnsNetwork);
when(mDependencies.getDnsResolver()).thenReturn(mDnsResolver);
when(mDependencies.getRandom()).thenReturn(mRandom);
when(mDependencies.getSetting(any(), eq(Settings.Global.CAPTIVE_PORTAL_MODE), anyInt()))
@@ -206,7 +271,7 @@ public class NetworkMonitorTest {
when(mDependencies.getSetting(any(), eq(Settings.Global.CAPTIVE_PORTAL_HTTPS_URL), any()))
.thenReturn(TEST_HTTPS_URL);
- doReturn(mNetwork).when(mNetwork).getPrivateDnsBypassingCopy();
+ doReturn(mCleartextDnsNetwork).when(mNetwork).getPrivateDnsBypassingCopy();
when(mContext.getSystemService(Context.CONNECTIVITY_SERVICE)).thenReturn(mCm);
when(mContext.getSystemService(Context.TELEPHONY_SERVICE)).thenReturn(mTelephony);
@@ -222,6 +287,9 @@ public class NetworkMonitorTest {
setFallbackSpecs(null); // Test with no fallback spec by default
when(mRandom.nextInt()).thenReturn(0);
+ when(mResources.getInteger(eq(R.integer.config_captive_portal_dns_probe_timeout)))
+ .thenReturn(500);
+
doAnswer((invocation) -> {
URL url = invocation.getArgument(0);
switch(url.toString()) {
@@ -237,11 +305,13 @@ public class NetworkMonitorTest {
fail("URL not mocked: " + url.toString());
return null;
}
- }).when(mNetwork).openConnection(any());
+ }).when(mCleartextDnsNetwork).openConnection(any());
when(mHttpConnection.getRequestProperties()).thenReturn(new ArrayMap<>());
when(mHttpsConnection.getRequestProperties()).thenReturn(new ArrayMap<>());
- setDnsAnswers(new String[]{"2001:db8::1", "192.0.2.2"});
+ mFakeDns = new FakeDns();
+ mFakeDns.startMocking();
+ mFakeDns.setAnswer("*", new String[]{"2001:db8::1", "192.0.2.2"});
when(mContext.registerReceiver(any(BroadcastReceiver.class), any())).then((invocation) -> {
mRegisteredReceivers.add(invocation.getArgument(0));
@@ -264,6 +334,7 @@ public class NetworkMonitorTest {
@After
public void tearDown() {
+ mFakeDns.clearAll();
assertTrue(mCreatedNetworkMonitors.size() > 0);
// Make a local copy of mCreatedNetworkMonitors because during the iteration below,
// WrappedNetworkMonitor#onQuitting will delete elements from it on the handler threads.
@@ -284,8 +355,8 @@ public class NetworkMonitorTest {
private final ConditionVariable mQuitCv = new ConditionVariable(false);
WrappedNetworkMonitor() {
- super(mContext, mCallbacks, mNetwork, mLogger, mValidationLogger, mDependencies,
- mDataStallStatsUtils);
+ super(mContext, mCallbacks, mNetwork, mLogger, mValidationLogger,
+ mDependencies, mDataStallStatsUtils);
}
@Override
@@ -314,23 +385,22 @@ public class NetworkMonitorTest {
}
}
- private WrappedNetworkMonitor makeMonitor() {
+ private WrappedNetworkMonitor makeMonitor(NetworkCapabilities nc) {
final WrappedNetworkMonitor nm = new WrappedNetworkMonitor();
nm.start();
+ setNetworkCapabilities(nm, nc);
waitForIdle(nm.getHandler());
mCreatedNetworkMonitors.add(nm);
return nm;
}
private WrappedNetworkMonitor makeMeteredNetworkMonitor() {
- final WrappedNetworkMonitor nm = makeMonitor();
- setNetworkCapabilities(nm, METERED_CAPABILITIES);
+ final WrappedNetworkMonitor nm = makeMonitor(METERED_CAPABILITIES);
return nm;
}
private WrappedNetworkMonitor makeNotMeteredNetworkMonitor() {
- final WrappedNetworkMonitor nm = makeMonitor();
- setNetworkCapabilities(nm, NOT_METERED_CAPABILITIES);
+ final WrappedNetworkMonitor nm = makeMonitor(NOT_METERED_CAPABILITIES);
return nm;
}
@@ -595,7 +665,7 @@ public class NetworkMonitorTest {
@Test
public void testNoInternetCapabilityValidated() throws Exception {
runNetworkTest(NO_INTERNET_CAPABILITIES, NETWORK_TEST_RESULT_VALID);
- verify(mNetwork, never()).openConnection(any());
+ verify(mCleartextDnsNetwork, never()).openConnection(any());
}
@Test
@@ -603,7 +673,7 @@ public class NetworkMonitorTest {
setSslException(mHttpsConnection);
setPortal302(mHttpConnection);
- final NetworkMonitor nm = makeMonitor();
+ final NetworkMonitor nm = makeMonitor(METERED_CAPABILITIES);
nm.notifyNetworkConnected(TEST_LINK_PROPERTIES, METERED_CAPABILITIES);
verify(mCallbacks, timeout(HANDLER_TIMEOUT_MS).times(1))
@@ -638,6 +708,63 @@ public class NetworkMonitorTest {
}
@Test
+ public void testPrivateDnsSuccess() throws Exception {
+ setStatus(mHttpsConnection, 204);
+ setStatus(mHttpConnection, 204);
+ mFakeDns.setAnswer("dns.google", new String[]{"2001:db8::53"});
+
+ WrappedNetworkMonitor wnm = makeNotMeteredNetworkMonitor();
+ wnm.notifyPrivateDnsSettingsChanged(new PrivateDnsConfig("dns.google", new InetAddress[0]));
+ wnm.notifyNetworkConnected(TEST_LINK_PROPERTIES, NOT_METERED_CAPABILITIES);
+ verify(mCallbacks, timeout(HANDLER_TIMEOUT_MS).times(1))
+ .notifyNetworkTested(eq(NETWORK_TEST_RESULT_VALID), eq(null));
+ }
+
+ @Test
+ public void testPrivateDnsResolutionRetryUpdate() throws Exception {
+ // Set a private DNS hostname that doesn't resolve and expect validation to fail.
+ mFakeDns.setAnswer("dns.google", new String[0]);
+ setStatus(mHttpsConnection, 204);
+ setStatus(mHttpConnection, 204);
+
+ WrappedNetworkMonitor wnm = makeNotMeteredNetworkMonitor();
+ wnm.notifyPrivateDnsSettingsChanged(new PrivateDnsConfig("dns.google", new InetAddress[0]));
+ wnm.notifyNetworkConnected(TEST_LINK_PROPERTIES, NOT_METERED_CAPABILITIES);
+ verify(mCallbacks, timeout(HANDLER_TIMEOUT_MS).times(1))
+ .notifyNetworkTested(eq(NETWORK_TEST_RESULT_INVALID), eq(null));
+
+ // Fix DNS and retry, expect validation to succeed.
+ reset(mCallbacks);
+ mFakeDns.setAnswer("dns.google", new String[]{"2001:db8::1"});
+
+ wnm.forceReevaluation(Process.myUid());
+ verify(mCallbacks, timeout(HANDLER_TIMEOUT_MS).times(1))
+ .notifyNetworkTested(eq(NETWORK_TEST_RESULT_VALID), eq(null));
+
+ // Change configuration to an invalid DNS name, expect validation to fail.
+ reset(mCallbacks);
+ mFakeDns.setAnswer("dns.bad", new String[0]);
+ wnm.notifyPrivateDnsSettingsChanged(new PrivateDnsConfig("dns.bad", new InetAddress[0]));
+ verify(mCallbacks, timeout(HANDLER_TIMEOUT_MS).times(1))
+ .notifyNetworkTested(eq(NETWORK_TEST_RESULT_INVALID), eq(null));
+
+ // Change configuration back to working again, but make private DNS not work.
+ // Expect validation to fail.
+ reset(mCallbacks);
+ mFakeDns.setNonBypassPrivateDnsWorking(false);
+ wnm.notifyPrivateDnsSettingsChanged(new PrivateDnsConfig("dns.google", new InetAddress[0]));
+ verify(mCallbacks, timeout(HANDLER_TIMEOUT_MS).times(1))
+ .notifyNetworkTested(eq(NETWORK_TEST_RESULT_INVALID), eq(null));
+
+ // Make private DNS work again. Expect validation to succeed.
+ reset(mCallbacks);
+ mFakeDns.setNonBypassPrivateDnsWorking(true);
+ wnm.forceReevaluation(Process.myUid());
+ verify(mCallbacks, timeout(HANDLER_TIMEOUT_MS).times(1))
+ .notifyNetworkTested(eq(NETWORK_TEST_RESULT_VALID), eq(null));
+ }
+
+ @Test
public void testDataStall_StallSuspectedAndSendMetrics() throws IOException {
WrappedNetworkMonitor wrappedMonitor = makeNotMeteredNetworkMonitor();
wrappedMonitor.setLastProbeTime(SystemClock.elapsedRealtime() - 1000);
@@ -728,25 +855,27 @@ public class NetworkMonitorTest {
WrappedNetworkMonitor wnm = makeNotMeteredNetworkMonitor();
final int shortTimeoutMs = 200;
+ // Clear the wildcard DNS response created in setUp.
+ mFakeDns.setAnswer("*", null);
+
String[] expected = new String[]{"2001:db8::"};
- setDnsAnswers(expected);
+ mFakeDns.setAnswer("www.google.com", expected);
InetAddress[] actual = wnm.sendDnsProbeWithTimeout("www.google.com", shortTimeoutMs);
assertIpAddressArrayEquals(expected, actual);
expected = new String[]{"2001:db8::", "192.0.2.1"};
- setDnsAnswers(expected);
- actual = wnm.sendDnsProbeWithTimeout("www.google.com", shortTimeoutMs);
+ mFakeDns.setAnswer("www.googleapis.com", expected);
+ actual = wnm.sendDnsProbeWithTimeout("www.googleapis.com", shortTimeoutMs);
assertIpAddressArrayEquals(expected, actual);
- expected = new String[0];
- setDnsAnswers(expected);
+ mFakeDns.setAnswer("www.google.com", new String[0]);
try {
wnm.sendDnsProbeWithTimeout("www.google.com", shortTimeoutMs);
fail("No DNS results, expected UnknownHostException");
} catch (UnknownHostException e) {
}
- setDnsAnswers(null);
+ mFakeDns.setAnswer("www.google.com", null);
try {
wnm.sendDnsProbeWithTimeout("www.google.com", shortTimeoutMs);
fail("DNS query timed out, expected UnknownHostException");
@@ -841,7 +970,7 @@ public class NetworkMonitorTest {
}
private NetworkMonitor runNetworkTest(NetworkCapabilities nc, int testResult) {
- final NetworkMonitor monitor = makeMonitor();
+ final NetworkMonitor monitor = makeMonitor(nc);
monitor.notifyNetworkConnected(TEST_LINK_PROPERTIES, nc);
try {
verify(mCallbacks, timeout(HANDLER_TIMEOUT_MS).times(1))
diff --git a/packages/SettingsLib/src/com/android/settingslib/net/DataUsageController.java b/packages/SettingsLib/src/com/android/settingslib/net/DataUsageController.java
index 8cb252ed6283..2bfcc91bbc29 100644
--- a/packages/SettingsLib/src/com/android/settingslib/net/DataUsageController.java
+++ b/packages/SettingsLib/src/com/android/settingslib/net/DataUsageController.java
@@ -42,6 +42,8 @@ import android.util.Log;
import android.util.Range;
import com.android.internal.R;
+import com.android.internal.annotations.VisibleForTesting;
+import com.android.internal.util.ArrayUtils;
import java.time.ZonedDateTime;
import java.util.Iterator;
@@ -57,7 +59,6 @@ public class DataUsageController {
PERIOD_BUILDER, Locale.getDefault());
private final Context mContext;
- private final TelephonyManager mTelephonyManager;
private final ConnectivityManager mConnectivityManager;
private final INetworkStatsService mStatsService;
private final NetworkPolicyManager mPolicyManager;
@@ -70,7 +71,6 @@ public class DataUsageController {
public DataUsageController(Context context) {
mContext = context;
- mTelephonyManager = TelephonyManager.from(context);
mConnectivityManager = ConnectivityManager.from(context);
mStatsService = INetworkStatsService.Stub.asInterface(
ServiceManager.getService(Context.NETWORK_STATS_SERVICE));
@@ -115,7 +115,8 @@ public class DataUsageController {
return warn("no subscriber id");
}
NetworkTemplate template = NetworkTemplate.buildTemplateMobileAll(subscriberId);
- template = NetworkTemplate.normalize(template, mTelephonyManager.getMergedSubscriberIds());
+ template = NetworkTemplate.normalize(template, getTelephonyManager()
+ .getMergedSubscriberIds());
return getDataUsageInfo(template);
}
@@ -212,9 +213,29 @@ public class DataUsageController {
.append(']').toString();
}
+ @VisibleForTesting
+ public TelephonyManager getTelephonyManager() {
+ int subscriptionId = mSubscriptionId;
+
+ // If mSubscriptionId is invalid, get default data sub.
+ if (!SubscriptionManager.isValidSubscriptionId(subscriptionId)) {
+ subscriptionId = SubscriptionManager.getDefaultDataSubscriptionId();
+ }
+
+ // If data sub is also invalid, get any active sub.
+ if (!SubscriptionManager.isValidSubscriptionId(subscriptionId)) {
+ int[] activeSubIds = SubscriptionManager.from(mContext).getActiveSubscriptionIdList();
+ if (!ArrayUtils.isEmpty(activeSubIds)) {
+ subscriptionId = activeSubIds[0];
+ }
+ }
+
+ return TelephonyManager.from(mContext).createForSubscriptionId(subscriptionId);
+ }
+
public void setMobileDataEnabled(boolean enabled) {
Log.d(TAG, "setMobileDataEnabled: enabled=" + enabled);
- mTelephonyManager.setDataEnabled(enabled);
+ getTelephonyManager().setDataEnabled(enabled);
if (mCallback != null) {
mCallback.onMobileDataEnabled(enabled);
}
@@ -223,11 +244,11 @@ public class DataUsageController {
public boolean isMobileDataSupported() {
// require both supported network and ready SIM
return mConnectivityManager.isNetworkSupported(TYPE_MOBILE)
- && mTelephonyManager.getSimState() == SIM_STATE_READY;
+ && getTelephonyManager().getSimState() == SIM_STATE_READY;
}
public boolean isMobileDataEnabled() {
- return mTelephonyManager.getDataEnabled();
+ return getTelephonyManager().isDataEnabled();
}
static int getNetworkType(NetworkTemplate networkTemplate) {
@@ -250,12 +271,7 @@ public class DataUsageController {
}
private String getActiveSubscriberId() {
- final TelephonyManager tele = TelephonyManager.from(mContext);
- int subscriptionId = mSubscriptionId;
- if (subscriptionId == SubscriptionManager.INVALID_SUBSCRIPTION_ID) {
- subscriptionId = SubscriptionManager.getDefaultDataSubscriptionId();
- }
- final String actualSubscriberId = tele.getSubscriberId(subscriptionId);
+ final String actualSubscriberId = getTelephonyManager().getSubscriberId();
return actualSubscriberId;
}
diff --git a/packages/SettingsLib/src/com/android/settingslib/wifi/WifiTracker.java b/packages/SettingsLib/src/com/android/settingslib/wifi/WifiTracker.java
index 49c8ce32658b..3e359d216234 100644
--- a/packages/SettingsLib/src/com/android/settingslib/wifi/WifiTracker.java
+++ b/packages/SettingsLib/src/com/android/settingslib/wifi/WifiTracker.java
@@ -555,8 +555,6 @@ public class WifiTracker implements LifecycleObserver, OnStart, OnStop, OnDestro
configsByKey.put(AccessPoint.getKey(config), config);
}
}
- ArrayMap<String, List<ScanResult>> scanResultsByApKey =
- updateScanResultCache(newScanResults);
WifiConfiguration connectionConfig = null;
if (mLastInfo != null) {
@@ -566,6 +564,9 @@ public class WifiTracker implements LifecycleObserver, OnStart, OnStop, OnDestro
// Rather than dropping and reacquiring the lock multiple times in this method, we lock
// once for efficiency of lock acquisition time and readability
synchronized (mLock) {
+ ArrayMap<String, List<ScanResult>> scanResultsByApKey =
+ updateScanResultCache(newScanResults);
+
// Swap the current access points into a cached list for maintaining AP listeners
List<AccessPoint> cachedAccessPoints;
cachedAccessPoints = new ArrayList<>(mInternalAccessPoints);
diff --git a/packages/SettingsLib/tests/robotests/src/com/android/settingslib/net/DataUsageControllerTest.java b/packages/SettingsLib/tests/robotests/src/com/android/settingslib/net/DataUsageControllerTest.java
index 220463b1f06c..a28bb6ce44c5 100644
--- a/packages/SettingsLib/tests/robotests/src/com/android/settingslib/net/DataUsageControllerTest.java
+++ b/packages/SettingsLib/tests/robotests/src/com/android/settingslib/net/DataUsageControllerTest.java
@@ -36,6 +36,7 @@ import android.net.INetworkStatsSession;
import android.net.NetworkStatsHistory;
import android.net.NetworkTemplate;
import android.os.RemoteException;
+import android.telephony.SubscriptionManager;
import android.telephony.TelephonyManager;
import android.text.format.DateUtils;
@@ -57,26 +58,31 @@ public class DataUsageControllerTest {
@Mock
private TelephonyManager mTelephonyManager;
@Mock
+ private SubscriptionManager mSubscriptionManager;
+ @Mock
private NetworkStatsManager mNetworkStatsManager;
@Mock
private Context mContext;
private DataUsageController mController;
private NetworkStatsHistory mNetworkStatsHistory;
+ private final int mDefaultSubscriptionId = 1234;
@Before
public void setUp() throws RemoteException {
MockitoAnnotations.initMocks(this);
+ when(mTelephonyManager.createForSubscriptionId(anyInt())).thenReturn(mTelephonyManager);
when(mContext.getSystemService(Context.TELEPHONY_SERVICE)).thenReturn(mTelephonyManager);
+ when(mContext.getSystemService(Context.TELEPHONY_SUBSCRIPTION_SERVICE))
+ .thenReturn(mSubscriptionManager);
when(mContext.getSystemService(NetworkStatsManager.class)).thenReturn(mNetworkStatsManager);
mController = new DataUsageController(mContext);
mNetworkStatsHistory = spy(
new NetworkStatsHistory(DateUtils.DAY_IN_MILLIS /* bucketDuration */));
doReturn(mNetworkStatsHistory)
.when(mSession).getHistoryForNetwork(any(NetworkTemplate.class), anyInt());
- final int defaultSubscriptionId = 1234;
- ShadowSubscriptionManager.setDefaultDataSubscriptionId(defaultSubscriptionId);
- doReturn(SUB_ID).when(mTelephonyManager).getSubscriberId(eq(defaultSubscriptionId));
+ ShadowSubscriptionManager.setDefaultDataSubscriptionId(mDefaultSubscriptionId);
+ doReturn(SUB_ID).when(mTelephonyManager).getSubscriberId();
}
@Test
@@ -130,19 +136,63 @@ public class DataUsageControllerTest {
final NetworkStats.Bucket nonDefaultSubscriberBucket = mock(NetworkStats.Bucket.class);
when(nonDefaultSubscriberBucket.getRxBytes()).thenReturn(nonDefaultSubRx);
when(nonDefaultSubscriberBucket.getTxBytes()).thenReturn(nonDefaultSubTx);
- final int explictSubscriptionId = 55;
+ final int explicitSubscriptionId = 55;
final String subscriberId2 = "Test Subscriber 2";
when(mNetworkStatsManager.querySummaryForDevice(eq(ConnectivityManager.TYPE_MOBILE),
eq(subscriberId2), eq(0L)/* startTime */, anyLong() /* endTime */)).thenReturn(
nonDefaultSubscriberBucket);
- doReturn(subscriberId2).when(mTelephonyManager).getSubscriberId(explictSubscriptionId);
+ doReturn(subscriberId2).when(mTelephonyManager).getSubscriberId();
// Now verify that when we're asking for stats on the non-default subscription, we get
// the data back for that subscription and *not* the default one.
- mController.setSubscriptionId(explictSubscriptionId);
+ mController.setSubscriptionId(explicitSubscriptionId);
assertThat(mController.getHistoricalUsageLevel(
NetworkTemplate.buildTemplateMobileAll(subscriberId2))).isEqualTo(
nonDefaultSubRx + nonDefaultSubTx);
+
+ verify(mTelephonyManager).createForSubscriptionId(explicitSubscriptionId);
+ }
+
+ @Test
+ public void getTelephonyManager_shouldCreateWithExplicitSubId() throws Exception {
+ int explicitSubId = 1;
+ TelephonyManager tmForSub1 = new TelephonyManager(mContext, explicitSubId);
+ when(mTelephonyManager.createForSubscriptionId(eq(explicitSubId))).thenReturn(tmForSub1);
+
+ // Set a specific subId.
+ mController.setSubscriptionId(explicitSubId);
+
+ assertThat(mController.getTelephonyManager()).isEqualTo(tmForSub1);
+ verify(mTelephonyManager).createForSubscriptionId(eq(explicitSubId));
+ }
+
+ @Test
+ public void getTelephonyManager_noExplicitSubId_shouldCreateWithDefaultDataSubId()
+ throws Exception {
+ TelephonyManager tmForDefaultSub = new TelephonyManager(mContext, mDefaultSubscriptionId);
+ when(mTelephonyManager.createForSubscriptionId(mDefaultSubscriptionId))
+ .thenReturn(tmForDefaultSub);
+
+ // No subId is set. It should use default data sub.
+ assertThat(mController.getTelephonyManager()).isEqualTo(tmForDefaultSub);
+ verify(mTelephonyManager).createForSubscriptionId(mDefaultSubscriptionId);
+ }
+
+ @Test
+ public void getTelephonyManager_noExplicitSubIdOrDefaultSub_shouldCreateWithActiveSub()
+ throws Exception {
+ int activeSubId = 2;
+ ShadowSubscriptionManager.setDefaultDataSubscriptionId(
+ SubscriptionManager.INVALID_SUBSCRIPTION_ID);
+ when(mSubscriptionManager.getActiveSubscriptionIdList())
+ .thenReturn(new int[] {activeSubId});
+ TelephonyManager tmForActiveSub = new TelephonyManager(mContext, activeSubId);
+ when(mTelephonyManager.createForSubscriptionId(activeSubId))
+ .thenReturn(tmForActiveSub);
+
+ // No subId is set, default data subId is also not set. So should use the only active subId.
+ assertThat(mController.getTelephonyManager()).isEqualTo(tmForActiveSub);
+ verify(mTelephonyManager).createForSubscriptionId(activeSubId);
}
}
diff --git a/packages/SettingsProvider/res/values/defaults.xml b/packages/SettingsProvider/res/values/defaults.xml
index 348f01eaa004..715e1ebe31ac 100644
--- a/packages/SettingsProvider/res/values/defaults.xml
+++ b/packages/SettingsProvider/res/values/defaults.xml
@@ -229,4 +229,10 @@
<!-- Default for Settings.Secure.AWARE_ENABLED -->
<bool name="def_aware_enabled">false</bool>
+
+ <!-- Default for Settings.Secure.SKIP_GESTURE -->
+ <bool name="def_skip_gesture">false</bool>
+
+ <!-- Default for Settings.Secure.SILENCE_GESTURE -->
+ <bool name="def_silence_gesture">false</bool>
</resources>
diff --git a/packages/SettingsProvider/src/com/android/providers/settings/SettingsProvider.java b/packages/SettingsProvider/src/com/android/providers/settings/SettingsProvider.java
index 2f3a42fdcc3f..82592ceeb710 100644
--- a/packages/SettingsProvider/src/com/android/providers/settings/SettingsProvider.java
+++ b/packages/SettingsProvider/src/com/android/providers/settings/SettingsProvider.java
@@ -3237,7 +3237,7 @@ public class SettingsProvider extends ContentProvider {
}
private final class UpgradeController {
- private static final int SETTINGS_VERSION = 178;
+ private static final int SETTINGS_VERSION = 179;
private final int mUserId;
@@ -4356,6 +4356,37 @@ public class SettingsProvider extends ContentProvider {
currentVersion = 178;
}
+ if (currentVersion == 178) {
+ // Version 178: Set the default value for Secure Settings:
+ // SKIP_GESTURE & SILENCE_GESTURE
+
+ final SettingsState secureSettings = getSecureSettingsLocked(userId);
+
+ final Setting skipGesture = secureSettings.getSettingLocked(
+ Secure.SKIP_GESTURE);
+
+ if (skipGesture.isNull()) {
+ final boolean defSkipGesture = getContext().getResources().getBoolean(
+ R.bool.def_skip_gesture);
+ secureSettings.insertSettingLocked(
+ Secure.SKIP_GESTURE, defSkipGesture ? "1" : "0",
+ null, true, SettingsState.SYSTEM_PACKAGE_NAME);
+ }
+
+ final Setting silenceGesture = secureSettings.getSettingLocked(
+ Secure.SILENCE_GESTURE);
+
+ if (silenceGesture.isNull()) {
+ final boolean defSilenceGesture = getContext().getResources().getBoolean(
+ R.bool.def_silence_gesture);
+ secureSettings.insertSettingLocked(
+ Secure.SILENCE_GESTURE, defSilenceGesture ? "1" : "0",
+ null, true, SettingsState.SYSTEM_PACKAGE_NAME);
+ }
+
+ currentVersion = 179;
+ }
+
// vXXX: Add new settings above this point.
diff --git a/packages/SystemUI/plugin/src/com/android/systemui/plugins/GlobalActionsPanelPlugin.java b/packages/SystemUI/plugin/src/com/android/systemui/plugins/GlobalActionsPanelPlugin.java
index 68d2ed7d4689..d0694ab124c6 100644
--- a/packages/SystemUI/plugin/src/com/android/systemui/plugins/GlobalActionsPanelPlugin.java
+++ b/packages/SystemUI/plugin/src/com/android/systemui/plugins/GlobalActionsPanelPlugin.java
@@ -16,7 +16,9 @@
package com.android.systemui.plugins;
+import android.annotation.Nullable;
import android.app.PendingIntent;
+import android.graphics.drawable.Drawable;
import android.view.View;
import com.android.systemui.plugins.annotations.DependsOn;
@@ -98,5 +100,13 @@ public interface GlobalActionsPanelPlugin extends Plugin {
* Invoked when the device is either locked or unlocked.
*/
void onDeviceLockStateChanged(boolean locked);
+
+ /**
+ * Optionally returns a drawable to be used as the background for Global Actions.
+ */
+ @Nullable
+ default Drawable getBackgroundDrawable() {
+ return null;
+ }
}
}
diff --git a/packages/SystemUI/plugin/src/com/android/systemui/plugins/statusbar/phone/NavBarButtonProvider.java b/packages/SystemUI/plugin/src/com/android/systemui/plugins/statusbar/phone/NavBarButtonProvider.java
deleted file mode 100644
index e25930c18947..000000000000
--- a/packages/SystemUI/plugin/src/com/android/systemui/plugins/statusbar/phone/NavBarButtonProvider.java
+++ /dev/null
@@ -1,56 +0,0 @@
-/*
- * Copyright (C) 2016 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file
- * except in compliance with the License. You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software distributed under the
- * License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- * KIND, either express or implied. See the License for the specific language governing
- * permissions and limitations under the License.
- */
-
-package com.android.systemui.plugins.statusbar.phone;
-
-import android.annotation.Nullable;
-import android.graphics.drawable.Drawable;
-import android.view.View;
-import android.view.ViewGroup;
-
-import com.android.systemui.plugins.Plugin;
-import com.android.systemui.plugins.annotations.ProvidesInterface;
-
-@ProvidesInterface(action = NavBarButtonProvider.ACTION, version = NavBarButtonProvider.VERSION)
-public interface NavBarButtonProvider extends Plugin {
-
- public static final String ACTION = "com.android.systemui.action.PLUGIN_NAV_BUTTON";
-
- public static final int VERSION = 2;
-
- /**
- * Returns a view in the nav bar. If the id is set "back", "home", "recent_apps", "menu",
- * or "ime_switcher", it is expected to implement ButtonInterface.
- */
- public View createView(String spec, ViewGroup parent);
-
- /**
- * Interface for button actions.
- */
- interface ButtonInterface {
-
- void setImageDrawable(@Nullable Drawable drawable);
-
- void abortCurrentGesture();
-
- void setVertical(boolean vertical);
-
- default void setCarMode(boolean carMode) {
- }
-
- void setDarkIntensity(float intensity);
-
- void setDelayTouchFeedback(boolean shouldDelay);
- }
-}
diff --git a/packages/SystemUI/plugin/src/com/android/systemui/plugins/statusbar/phone/NavGesture.java b/packages/SystemUI/plugin/src/com/android/systemui/plugins/statusbar/phone/NavGesture.java
deleted file mode 100644
index 99cc3a37d739..000000000000
--- a/packages/SystemUI/plugin/src/com/android/systemui/plugins/statusbar/phone/NavGesture.java
+++ /dev/null
@@ -1,54 +0,0 @@
-/*
- * Copyright (C) 2016 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file
- * except in compliance with the License. You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software distributed under the
- * License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- * KIND, either express or implied. See the License for the specific language governing
- * permissions and limitations under the License.
- */
-
-package com.android.systemui.plugins.statusbar.phone;
-
-import android.graphics.Canvas;
-import android.view.MotionEvent;
-import android.view.View;
-
-import com.android.systemui.plugins.Plugin;
-import com.android.systemui.plugins.annotations.ProvidesInterface;
-import java.io.PrintWriter;
-
-@ProvidesInterface(action = NavGesture.ACTION, version = NavGesture.VERSION)
-public interface NavGesture extends Plugin {
-
- public static final String ACTION = "com.android.systemui.action.PLUGIN_NAV_GESTURE";
-
- public static final int VERSION = 1;
-
- public GestureHelper getGestureHelper();
-
- public interface GestureHelper {
- public boolean onTouchEvent(MotionEvent event);
-
- public boolean onInterceptTouchEvent(MotionEvent event);
-
- public void setBarState(boolean isRtl, int navBarPosition);
-
- public void onDraw(Canvas canvas);
-
- public void onDarkIntensityChange(float intensity);
-
- public void onLayout(boolean changed, int left, int top, int right, int bottom);
-
- public void onNavigationButtonLongPress(View v);
-
- public default void destroy() { }
-
- public default void dump(PrintWriter pw) { }
- }
-
-}
diff --git a/packages/SystemUI/res-keyguard/layout/digital_clock.xml b/packages/SystemUI/res-keyguard/layout/digital_clock.xml
index 7c15fe62f762..38ee081b8327 100644
--- a/packages/SystemUI/res-keyguard/layout/digital_clock.xml
+++ b/packages/SystemUI/res-keyguard/layout/digital_clock.xml
@@ -26,6 +26,7 @@
android:layout_height="wrap_content"
android:layout_gravity="center_horizontal"
android:gravity="center_horizontal"
+ android:paddingBottom="@dimen/widget_vertical_padding_clock"
android:letterSpacing="0.03"
android:textColor="?attr/wallpaperTextColor"
android:singleLine="true"
diff --git a/packages/SystemUI/res-keyguard/layout/keyguard_bouncer.xml b/packages/SystemUI/res-keyguard/layout/keyguard_bouncer.xml
index 8c80e78733ef..79868093fb12 100644
--- a/packages/SystemUI/res-keyguard/layout/keyguard_bouncer.xml
+++ b/packages/SystemUI/res-keyguard/layout/keyguard_bouncer.xml
@@ -19,8 +19,7 @@
android:layout_height="match_parent"
android:background="@android:color/transparent"
android:clipChildren="false"
- android:clipToPadding="false"
- android:fitsSystemWindows="true">
+ android:clipToPadding="false">
<include
style="@style/BouncerSecurityContainer"
diff --git a/packages/SystemUI/res-keyguard/layout/keyguard_clock_switch.xml b/packages/SystemUI/res-keyguard/layout/keyguard_clock_switch.xml
index 1967dd1013f9..bf2963cd0b7f 100644
--- a/packages/SystemUI/res-keyguard/layout/keyguard_clock_switch.xml
+++ b/packages/SystemUI/res-keyguard/layout/keyguard_clock_switch.xml
@@ -36,7 +36,8 @@
android:layout_height="wrap_content"
android:layout_gravity="center_horizontal"
android:gravity="center_horizontal"
- android:letterSpacing="0.03"
+ android:paddingBottom="@dimen/title_clock_padding"
+ android:letterSpacing="0.02"
android:textColor="?attr/wallpaperTextColor"
android:singleLine="true"
style="@style/widget_big"
diff --git a/packages/SystemUI/res-keyguard/layout/keyguard_status_area.xml b/packages/SystemUI/res-keyguard/layout/keyguard_status_area.xml
index dc45b4b51925..a84ddaf29e52 100644
--- a/packages/SystemUI/res-keyguard/layout/keyguard_status_area.xml
+++ b/packages/SystemUI/res-keyguard/layout/keyguard_status_area.xml
@@ -32,8 +32,9 @@
android:id="@+id/title"
android:layout_width="match_parent"
android:layout_height="wrap_content"
- android:paddingStart="64dp"
- android:paddingEnd="64dp"
+ android:paddingStart="44dp"
+ android:paddingEnd="44dp"
+ android:letterSpacing="0.02"
android:visibility="gone"
android:textColor="?attr/wallpaperTextColor"
android:theme="@style/TextAppearance.Keyguard"
@@ -45,4 +46,4 @@
android:orientation="horizontal"
android:gravity="center"
/>
-</com.android.keyguard.KeyguardSliceView> \ No newline at end of file
+</com.android.keyguard.KeyguardSliceView>
diff --git a/packages/SystemUI/res-keyguard/layout/keyguard_status_view.xml b/packages/SystemUI/res-keyguard/layout/keyguard_status_view.xml
index 10fea9d50112..04d6afc1935f 100644
--- a/packages/SystemUI/res-keyguard/layout/keyguard_status_view.xml
+++ b/packages/SystemUI/res-keyguard/layout/keyguard_status_view.xml
@@ -29,6 +29,7 @@
androidprv:layout_maxHeight="@dimen/keyguard_security_height"
android:gravity="center_horizontal|top">
<LinearLayout
+ android:id="@+id/status_view_container"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_marginBottom="@dimen/widget_vertical_padding"
diff --git a/packages/SystemUI/res-keyguard/values-ca/strings.xml b/packages/SystemUI/res-keyguard/values-ca/strings.xml
index 07142b0e9227..bb48226a8930 100644
--- a/packages/SystemUI/res-keyguard/values-ca/strings.xml
+++ b/packages/SystemUI/res-keyguard/values-ca/strings.xml
@@ -41,9 +41,9 @@
<string name="keyguard_low_battery" msgid="9218432555787624490">"Connecta el carregador."</string>
<string name="keyguard_instructions_when_pattern_disabled" msgid="8566679946700751371">"Prem Menú per desbloquejar."</string>
<string name="keyguard_network_locked_message" msgid="6743537524631420759">"La xarxa està bloquejada"</string>
- <string name="keyguard_missing_sim_message_short" msgid="6327533369959764518">"No hi ha cap targeta SIM"</string>
- <string name="keyguard_missing_sim_message" product="tablet" msgid="4550152848200783542">"No hi ha cap targeta SIM a la tauleta."</string>
- <string name="keyguard_missing_sim_message" product="default" msgid="6585414237800161146">"No hi ha cap targeta SIM al telèfon."</string>
+ <string name="keyguard_missing_sim_message_short" msgid="6327533369959764518">"No hi ha cap SIM"</string>
+ <string name="keyguard_missing_sim_message" product="tablet" msgid="4550152848200783542">"No hi ha cap SIM a la tauleta."</string>
+ <string name="keyguard_missing_sim_message" product="default" msgid="6585414237800161146">"No hi ha cap SIM al telèfon."</string>
<string name="keyguard_missing_sim_instructions" msgid="7350295932015220392">"Insereix una targeta SIM."</string>
<string name="keyguard_missing_sim_instructions_long" msgid="589889372883904477">"Falta la targeta SIM o no es pot llegir. Insereix-ne una."</string>
<string name="keyguard_permanent_disabled_sim_message_short" msgid="654102080186420706">"La targeta SIM no es pot fer servir."</string>
diff --git a/packages/SystemUI/res-keyguard/values-h560dp/dimens.xml b/packages/SystemUI/res-keyguard/values-h560dp/dimens.xml
index 3fb86d03a167..669f8fb642de 100644
--- a/packages/SystemUI/res-keyguard/values-h560dp/dimens.xml
+++ b/packages/SystemUI/res-keyguard/values-h560dp/dimens.xml
@@ -16,5 +16,5 @@
-->
<resources>
- <dimen name="widget_big_font_size">64dp</dimen>
-</resources> \ No newline at end of file
+ <dimen name="widget_big_font_size">54dp</dimen>
+</resources>
diff --git a/packages/SystemUI/res-keyguard/values-h650dp/dimens.xml b/packages/SystemUI/res-keyguard/values-h650dp/dimens.xml
index 3fb86d03a167..669f8fb642de 100644
--- a/packages/SystemUI/res-keyguard/values-h650dp/dimens.xml
+++ b/packages/SystemUI/res-keyguard/values-h650dp/dimens.xml
@@ -16,5 +16,5 @@
-->
<resources>
- <dimen name="widget_big_font_size">64dp</dimen>
-</resources> \ No newline at end of file
+ <dimen name="widget_big_font_size">54dp</dimen>
+</resources>
diff --git a/packages/SystemUI/res-keyguard/values-hi/strings.xml b/packages/SystemUI/res-keyguard/values-hi/strings.xml
index 65049100b55c..86e14dc8b107 100644
--- a/packages/SystemUI/res-keyguard/values-hi/strings.xml
+++ b/packages/SystemUI/res-keyguard/values-hi/strings.xml
@@ -96,10 +96,10 @@
<string name="kg_failed_attempts_almost_at_erase_user" product="default" msgid="2151286957817486128">"आपने फ़ोन का लॉक खोलने के लिए <xliff:g id="NUMBER_0">%1$d</xliff:g> बार गलत तरीके से कोशिश की है. <xliff:g id="NUMBER_1">%2$d</xliff:g> बार और गलत कोशिश करने पर, इस उपयोगकर्ता को निकाल दिया जाएगा, जिससे सभी उपयोगकर्ता डेटा मिट जाएगा."</string>
<string name="kg_failed_attempts_now_erasing_user" product="tablet" msgid="5464020754932560928">"आपने टैबलेट का लॉक खोलने के लिए <xliff:g id="NUMBER">%d</xliff:g> बार गलत तरीके से कोशिश की है. इस उपयोगकर्ता को निकाल दिया जाएगा, जिससे सभी उपयोगकर्ता डेटा हट जाएगा."</string>
<string name="kg_failed_attempts_now_erasing_user" product="default" msgid="6171564974118059">"आपने फ़ोन का लॉक खोलने के लिए <xliff:g id="NUMBER">%d</xliff:g> बार गलत तरीके से कोशिश की है. इस उपयोगकर्ता को निकाल दिया जाएगा, जिससे सभी उपयोगकर्ता डेटा हट जाएगा."</string>
- <string name="kg_failed_attempts_almost_at_erase_profile" product="tablet" msgid="9154513795928824239">"आपने टैबलेट को अनलॉक करने के लिए <xliff:g id="NUMBER_0">%1$d</xliff:g> बार गलत तरीके से कोशिश की है. <xliff:g id="NUMBER_1">%2$d</xliff:g> और असफल कोशिशों के बाद, कार्य प्रोफ़ाइल को निकाल दिया जाएगा, जिससे सभी प्रोफ़ाइल डेटा हट जाएगा."</string>
- <string name="kg_failed_attempts_almost_at_erase_profile" product="default" msgid="2162434417489128282">"आपने फ़ोन को अनलॉक करने के लिए <xliff:g id="NUMBER_0">%1$d</xliff:g> बार गलत तरीके से कोशिश की है. <xliff:g id="NUMBER_1">%2$d</xliff:g> और असफल कोशिशों के बाद, कार्य प्रोफ़ाइल को निकाल दिया जाएगा, जिससे सभी प्रोफ़ाइल डेटा हट जाएगा."</string>
- <string name="kg_failed_attempts_now_erasing_profile" product="tablet" msgid="8966727588974691544">"आपने टैबलेट को अनलॉक करने के लिए <xliff:g id="NUMBER">%d</xliff:g> बार गलत तरीके से कोशिश की है. कार्य प्रोफ़ाइल को निकाल दिया जाएगा, जिससे सभी प्रोफ़ाइल डेटा हट जाएगा."</string>
- <string name="kg_failed_attempts_now_erasing_profile" product="default" msgid="8476407539834855">"आपने फ़ोन को अनलॉक करने के लिए <xliff:g id="NUMBER">%d</xliff:g> बार गलत तरीके से कोशिश की है. कार्य प्रोफ़ाइल को निकाल दिया जाएगा, जिससे सभी प्रोफ़ाइल डेटा हट जाएगा."</string>
+ <string name="kg_failed_attempts_almost_at_erase_profile" product="tablet" msgid="9154513795928824239">"आपने टैबलेट को अनलॉक करने के लिए <xliff:g id="NUMBER_0">%1$d</xliff:g> बार गलत तरीके से कोशिश की है. <xliff:g id="NUMBER_1">%2$d</xliff:g> और असफल कोशिशों के बाद, वर्क प्रोफ़ाइल को निकाल दिया जाएगा, जिससे सभी प्रोफ़ाइल डेटा हट जाएगा."</string>
+ <string name="kg_failed_attempts_almost_at_erase_profile" product="default" msgid="2162434417489128282">"आपने फ़ोन को अनलॉक करने के लिए <xliff:g id="NUMBER_0">%1$d</xliff:g> बार गलत तरीके से कोशिश की है. <xliff:g id="NUMBER_1">%2$d</xliff:g> और असफल कोशिशों के बाद, वर्क प्रोफ़ाइल को निकाल दिया जाएगा, जिससे सभी प्रोफ़ाइल डेटा हट जाएगा."</string>
+ <string name="kg_failed_attempts_now_erasing_profile" product="tablet" msgid="8966727588974691544">"आपने टैबलेट को अनलॉक करने के लिए <xliff:g id="NUMBER">%d</xliff:g> बार गलत तरीके से कोशिश की है. वर्क प्रोफ़ाइल को निकाल दिया जाएगा, जिससे सभी प्रोफ़ाइल डेटा हट जाएगा."</string>
+ <string name="kg_failed_attempts_now_erasing_profile" product="default" msgid="8476407539834855">"आपने फ़ोन को अनलॉक करने के लिए <xliff:g id="NUMBER">%d</xliff:g> बार गलत तरीके से कोशिश की है. वर्क प्रोफ़ाइल को निकाल दिया जाएगा, जिससे सभी प्रोफ़ाइल डेटा हट जाएगा."</string>
<string name="kg_failed_attempts_almost_at_login" product="tablet" msgid="956706236554092172">"आपने अपने लॉक खोलने के पैटर्न को <xliff:g id="NUMBER_0">%1$d</xliff:g> बार गलत तरीके से ड्रॉ किया है. अगर आपने <xliff:g id="NUMBER_1">%2$d</xliff:g> बार और गलत ड्रॉ किया, तो आपसे अपने टैबलेट को किसी ईमेल खाते का इस्तेमाल करके अनलॉक करने के लिए कहा जाएगा.\n\n <xliff:g id="NUMBER_2">%3$d</xliff:g> सेकंड बाद फिर से कोशिश करें."</string>
<string name="kg_failed_attempts_almost_at_login" product="default" msgid="8364140853305528449">"आपने अपने लॉक खोलने के पैटर्न को <xliff:g id="NUMBER_0">%1$d</xliff:g> बार गलत तरीके से ड्रॉ किया है. अगर आपने <xliff:g id="NUMBER_1">%2$d</xliff:g> बार और गलत ड्रॉ किया, तो आपसे अपने फ़ोन को किसी ईमेल खाते का इस्तेमाल करके अनलॉक करने के लिए कहा जाएगा.\n\n <xliff:g id="NUMBER_2">%3$d</xliff:g> सेकंड बाद फिर से कोशिश करें."</string>
<string name="kg_password_wrong_pin_code_pukked" msgid="3389829202093674267">"गलत SIM पिन कोड, अपने डिवाइस को अनलॉक करने के लिए अब आपको अपनी मोबाइल और इंटरनेट सेवा देने वाली कंपनी से संपर्क करना होगा."</string>
diff --git a/packages/SystemUI/res-keyguard/values-sw600dp/dimens.xml b/packages/SystemUI/res-keyguard/values-sw600dp/dimens.xml
index fdca44dab019..e9bd638dfbf4 100644
--- a/packages/SystemUI/res-keyguard/values-sw600dp/dimens.xml
+++ b/packages/SystemUI/res-keyguard/values-sw600dp/dimens.xml
@@ -27,7 +27,7 @@
<!-- Overload default clock widget parameters -->
<dimen name="widget_big_font_size">100dp</dimen>
- <dimen name="widget_label_font_size">16sp</dimen>
+ <dimen name="widget_label_font_size">18sp</dimen>
<!-- EmergencyCarrierArea overlap - amount to overlap the emergency button and carrier text.
Should be 0 on devices with plenty of room (e.g. tablets) -->
diff --git a/packages/SystemUI/res-keyguard/values/dimens.xml b/packages/SystemUI/res-keyguard/values/dimens.xml
index 112dde6bfdc2..8e00efeed62c 100644
--- a/packages/SystemUI/res-keyguard/values/dimens.xml
+++ b/packages/SystemUI/res-keyguard/values/dimens.xml
@@ -42,23 +42,26 @@
<dimen name="eca_overlap">-10dip</dimen>
<!-- Slice header -->
- <dimen name="widget_title_font_size">22dp</dimen>
- <dimen name="header_subtitle_padding">4dp</dimen>
- <dimen name="header_icon_size">20dp</dimen>
+ <dimen name="widget_title_font_size">24dp</dimen>
+ <dimen name="header_subtitle_padding">12dp</dimen>
+ <dimen name="header_icon_size">16dp</dimen>
<!-- Slice subtitle -->
- <dimen name="widget_label_font_size">16dp</dimen>
+ <dimen name="widget_label_font_size">18dp</dimen>
<!-- Clock without header -->
- <dimen name="widget_big_font_size">64dp</dimen>
+ <dimen name="widget_big_font_size">54dp</dimen>
<dimen name="bottom_text_spacing_digital">0dp</dimen>
+ <dimen name="title_clock_padding">4dp</dimen>
<!-- Clock with header -->
- <dimen name="widget_small_font_size">22dp</dimen>
- <dimen name="widget_vertical_padding">32dp</dimen>
+ <dimen name="widget_small_font_size">@dimen/widget_title_font_size</dimen>
+ <dimen name="widget_vertical_padding">24dp</dimen>
+ <dimen name="widget_vertical_padding_with_header">32dp</dimen>
<dimen name="widget_vertical_padding_clock">12dp</dimen>
<!-- Subtitle paddings -->
<dimen name="widget_horizontal_padding">8dp</dimen>
- <dimen name="widget_icon_size">16dp</dimen>
+ <dimen name="widget_icon_size">20dp</dimen>
<dimen name="widget_icon_padding">8dp</dimen>
- <dimen name="subtitle_clock_padding">15dp</dimen>
+ <dimen name="subtitle_clock_padding">0dp</dimen>
+ <dimen name="header_row_font_size">14dp</dimen>
<!-- Notification shelf padding when dark -->
<dimen name="widget_bottom_separator_padding">-6dp</dimen>
diff --git a/packages/SystemUI/res-keyguard/values/styles.xml b/packages/SystemUI/res-keyguard/values/styles.xml
index 1c8e141a61f8..137c30aefd33 100644
--- a/packages/SystemUI/res-keyguard/values/styles.xml
+++ b/packages/SystemUI/res-keyguard/values/styles.xml
@@ -115,6 +115,7 @@
<item name="android:layout_height">wrap_content</item>
<item name="android:lines">1</item>
<item name="android:textSize">@dimen/widget_label_font_size</item>
+ <item name="android:letterSpacing">0.02</item>
</style>
<style name="TextAppearance.Keyguard.BottomArea">
diff --git a/packages/SystemUI/res/drawable/bubble_dismiss_circle.xml b/packages/SystemUI/res/drawable/bubble_dismiss_circle.xml
new file mode 100644
index 000000000000..1661bb22d148
--- /dev/null
+++ b/packages/SystemUI/res/drawable/bubble_dismiss_circle.xml
@@ -0,0 +1,27 @@
+<!--
+ Copyright (C) 2019 The Android Open Source Project
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+-->
+<!--
+ The transparent circle outline that encircles the bubbles when they're in the dismiss target.
+-->
+<shape
+ xmlns:android="http://schemas.android.com/apk/res/android"
+ android:shape="oval">
+
+ <stroke
+ android:width="1dp"
+ android:color="#66FFFFFF" />
+
+</shape> \ No newline at end of file
diff --git a/packages/SystemUI/res/drawable/bubble_dismiss_icon.xml b/packages/SystemUI/res/drawable/bubble_dismiss_icon.xml
new file mode 100644
index 000000000000..5c8de581f8d1
--- /dev/null
+++ b/packages/SystemUI/res/drawable/bubble_dismiss_icon.xml
@@ -0,0 +1,26 @@
+<!--
+ Copyright (C) 2019 The Android Open Source Project
+
+ Licensed under the Apache License, Version 2.0 (the "License");
+ you may not use this file except in compliance with the License.
+ You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+ Unless required by applicable law or agreed to in writing, software
+ distributed under the License is distributed on an "AS IS" BASIS,
+ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ See the License for the specific language governing permissions and
+ limitations under the License.
+-->
+<!-- The 'X' bubble dismiss icon. This is just ic_close with a stroke. -->
+<vector xmlns:android="http://schemas.android.com/apk/res/android"
+ android:width="24.0dp"
+ android:height="24.0dp"
+ android:viewportWidth="24.0"
+ android:viewportHeight="24.0">
+ <path
+ android:pathData="M19.000000,6.400000l-1.400000,-1.400000 -5.600000,5.600000 -5.600000,-5.600000 -1.400000,1.400000 5.600000,5.600000 -5.600000,5.600000 1.400000,1.400000 5.600000,-5.600000 5.600000,5.600000 1.400000,-1.400000 -5.600000,-5.600000z"
+ android:fillColor="#FFFFFFFF"
+ android:strokeColor="#FF000000"/>
+</vector>
diff --git a/packages/SystemUI/res/drawable/global_action_panel_scrim.xml b/packages/SystemUI/res/drawable/global_action_panel_scrim.xml
deleted file mode 100644
index 8b8258fc6e75..000000000000
--- a/packages/SystemUI/res/drawable/global_action_panel_scrim.xml
+++ /dev/null
@@ -1,26 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<!--
- ~ Copyright (C) 2019 The Android Open Source Project
- ~
- ~ Licensed under the Apache License, Version 2.0 (the "License");
- ~ you may not use this file except in compliance with the License.
- ~ You may obtain a copy of the License at
- ~
- ~ http://www.apache.org/licenses/LICENSE-2.0
- ~
- ~ Unless required by applicable law or agreed to in writing, software
- ~ distributed under the License is distributed on an "AS IS" BASIS,
- ~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- ~ See the License for the specific language governing permissions and
- ~ limitations under the License
- -->
-
-<shape xmlns:android="http://schemas.android.com/apk/res/android"
- android:shape="rectangle">
- <gradient
- android:centerY="0.45"
- android:startColor="#dc3c4043"
- android:centerColor="#dc3c4043"
- android:endColor="#4d3c4043"
- android:angle="270" />
-</shape> \ No newline at end of file
diff --git a/packages/SystemUI/res/layout/bubble_dismiss_target.xml b/packages/SystemUI/res/layout/bubble_dismiss_target.xml
new file mode 100644
index 000000000000..245177c8461b
--- /dev/null
+++ b/packages/SystemUI/res/layout/bubble_dismiss_target.xml
@@ -0,0 +1,66 @@
+<!--
+ ~ Copyright (C) 2019 The Android Open Source Project
+ ~
+ ~ Licensed under the Apache License, Version 2.0 (the "License");
+ ~ you may not use this file except in compliance with the License.
+ ~ You may obtain a copy of the License at
+ ~
+ ~ http://www.apache.org/licenses/LICENSE-2.0
+ ~
+ ~ Unless required by applicable law or agreed to in writing, software
+ ~ distributed under the License is distributed on an "AS IS" BASIS,
+ ~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ ~ See the License for the specific language governing permissions and
+ ~ limitations under the License
+ -->
+<!-- Bubble dismiss target consisting of an X icon and the text 'Dismiss'. -->
+<FrameLayout
+ xmlns:android="http://schemas.android.com/apk/res/android"
+ android:layout_width="wrap_content"
+ android:layout_height="@dimen/pip_dismiss_gradient_height"
+ android:layout_gravity="bottom|center_horizontal">
+
+ <LinearLayout
+ android:id="@+id/bubble_dismiss_icon_container"
+ android:layout_width="wrap_content"
+ android:layout_height="match_parent"
+ android:gravity="center"
+ android:paddingBottom="@dimen/bubble_dismiss_target_padding_y"
+ android:paddingTop="@dimen/bubble_dismiss_target_padding_y"
+ android:paddingLeft="@dimen/bubble_dismiss_target_padding_x"
+ android:paddingRight="@dimen/bubble_dismiss_target_padding_x"
+ android:clipChildren="false"
+ android:clipToPadding="false"
+ android:orientation="horizontal">
+
+ <ImageView
+ android:id="@+id/bubble_dismiss_close_icon"
+ android:layout_width="24dp"
+ android:layout_height="24dp"
+ android:src="@drawable/bubble_dismiss_icon" />
+
+ <TextView
+ android:id="@+id/bubble_dismiss_text"
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:layout_marginTop="9dp"
+ android:layout_marginBottom="9dp"
+ android:layout_marginLeft="8dp"
+ android:textAppearance="@*android:style/TextAppearance.DeviceDefault.Body1"
+ android:textColor="@android:color/white"
+ android:shadowColor="@android:color/black"
+ android:shadowDx="-1"
+ android:shadowDy="1"
+ android:shadowRadius="0.01"
+ android:text="@string/bubble_dismiss_text" />
+
+ </LinearLayout>
+
+ <FrameLayout
+ android:id="@+id/bubble_dismiss_circle"
+ android:layout_width="@dimen/bubble_dismiss_encircle_size"
+ android:layout_height="@dimen/bubble_dismiss_encircle_size"
+ android:layout_gravity="center"
+ android:alpha="0"
+ android:background="@drawable/bubble_dismiss_circle" />
+</FrameLayout> \ No newline at end of file
diff --git a/packages/SystemUI/res/layout/nav_bar_tuner_inflater.xml b/packages/SystemUI/res/layout/nav_bar_tuner_inflater.xml
deleted file mode 100644
index 133b2158c771..000000000000
--- a/packages/SystemUI/res/layout/nav_bar_tuner_inflater.xml
+++ /dev/null
@@ -1,27 +0,0 @@
-<?xml version="1.0" encoding="utf-8"?>
-<!-- Copyright (C) 2016 The Android Open Source Project
-
- Licensed under the Apache License, Version 2.0 (the "License");
- you may not use this file except in compliance with the License.
- You may obtain a copy of the License at
-
- http://www.apache.org/licenses/LICENSE-2.0
-
- Unless required by applicable law or agreed to in writing, software
- distributed under the License is distributed on an "AS IS" BASIS,
- WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- See the License for the specific language governing permissions and
- limitations under the License.
--->
-<com.android.systemui.tuner.PreviewNavInflater
- xmlns:android="http://schemas.android.com/apk/res/android"
- xmlns:systemui="http://schemas.android.com/apk/res-auto"
- android:background="@android:color/black"
- android:layout_width="match_parent"
- android:layout_height="@dimen/navigation_bar_size">
-
- <include android:id="@+id/horizontal" layout="@layout/navigation_layout" />
-
- <include android:id="@+id/vertical" layout="@layout/navigation_layout_vertical" />
-
-</com.android.systemui.tuner.PreviewNavInflater>
diff --git a/packages/SystemUI/res/layout/notif_half_shelf.xml b/packages/SystemUI/res/layout/notif_half_shelf.xml
new file mode 100644
index 000000000000..a563bb579540
--- /dev/null
+++ b/packages/SystemUI/res/layout/notif_half_shelf.xml
@@ -0,0 +1,126 @@
+<!--
+ ~ Copyright (C) 2019 The Android Open Source Project
+ ~
+ ~ Licensed under the Apache License, Version 2.0 (the "License");
+ ~ you may not use this file except in compliance with the License.
+ ~ You may obtain a copy of the License at
+ ~
+ ~ http://www.apache.org/licenses/LICENSE-2.0
+ ~
+ ~ Unless required by applicable law or agreed to in writing, software
+ ~ distributed under the License is distributed on an "AS IS" BASIS,
+ ~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ ~ See the License for the specific language governing permissions and
+ ~ limitations under the License
+ -->
+
+<FrameLayout
+ xmlns:android="http://schemas.android.com/apk/res/android"
+ android:id="@+id/half_shelf_dialog"
+ android:orientation="vertical"
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:layout_gravity="center_horizontal|bottom"
+ android:paddingStart="4dp"
+ android:paddingEnd="4dp"
+>
+
+ <LinearLayout
+ android:id="@+id/half_shelf"
+ android:layout_width="@dimen/qs_panel_width"
+ android:layout_height="wrap_content"
+ android:orientation="vertical"
+ android:gravity="bottom"
+ android:layout_gravity="center_horizontal|bottom"
+ android:background="@drawable/rounded_bg_full" >
+
+ <com.android.systemui.statusbar.notification.row.ChannelEditorListView
+ android:id="@+id/half_shelf_container"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:gravity="bottom"
+ android:orientation="vertical" >
+
+ <com.android.systemui.statusbar.notification.row.AppControlView
+ android:id="@+id/app_control"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:padding="8dp"
+ android:orientation="horizontal" >
+
+ <ImageView
+ android:id="@+id/icon"
+ android:layout_height="48dp"
+ android:layout_width="48dp"
+ android:padding="8dp" />
+
+ <TextView
+ android:id="@+id/app_name"
+ android:layout_height="wrap_content"
+ android:layout_width="0dp"
+ android:layout_weight="1"
+ android:layout_gravity="center"
+ android:padding="8dp"
+ android:gravity="center_vertical|start"
+ android:textSize="15sp"
+ android:ellipsize="end"
+ android:maxLines="1"
+ style="@style/TextAppearance.NotificationInfo.Title" />
+
+ <Switch
+ android:id="@+id/toggle"
+ android:layout_height="wrap_content"
+ android:layout_width="wrap_content"
+ android:layout_gravity="center_vertical"
+ android:padding="8dp" />
+ </com.android.systemui.statusbar.notification.row.AppControlView>
+ <!-- divider view -->
+ <View
+ android:layout_width="match_parent"
+ android:layout_height="1dp"
+ android:background="@color/notification_channel_dialog_separator"
+ />
+
+ <!-- ChannelRows get added dynamically -->
+
+ </com.android.systemui.statusbar.notification.row.ChannelEditorListView>
+ <!-- divider view -->
+ <View
+ android:layout_width="match_parent"
+ android:layout_height="1dp"
+ android:background="@color/notification_channel_dialog_separator"
+ />
+ <RelativeLayout
+ android:id="@+id/bottom_actions"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:paddingTop="@dimen/notification_guts_button_spacing"
+ android:paddingStart="20dp"
+ android:paddingEnd="20dp" >
+ <TextView
+ android:id="@+id/see_more_button"
+ android:text="@string/see_more_title"
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:layout_alignParentStart="true"
+ android:layout_centerVertical="true"
+ android:gravity="start|center_vertical"
+ android:minWidth="@dimen/notification_importance_toggle_size"
+ android:minHeight="@dimen/notification_importance_toggle_size"
+ android:maxWidth="200dp"
+ style="@style/TextAppearance.NotificationInfo.Button"/>
+ <TextView
+ android:id="@+id/done_button"
+ android:text="@string/inline_ok_button"
+ android:layout_width="wrap_content"
+ android:layout_height="wrap_content"
+ android:layout_centerVertical="true"
+ android:gravity="end|center_vertical"
+ android:maxWidth="125dp"
+ android:minWidth="@dimen/notification_importance_toggle_size"
+ android:minHeight="@dimen/notification_importance_toggle_size"
+ android:layout_alignParentEnd="true"
+ style="@style/TextAppearance.NotificationInfo.Button"/>
+ </RelativeLayout>
+ </LinearLayout>
+</FrameLayout>
diff --git a/packages/SystemUI/res/layout/notif_half_shelf_row.xml b/packages/SystemUI/res/layout/notif_half_shelf_row.xml
new file mode 100644
index 000000000000..17ea931a4f8c
--- /dev/null
+++ b/packages/SystemUI/res/layout/notif_half_shelf_row.xml
@@ -0,0 +1,78 @@
+<!--
+ ~ Copyright (C) 2019 The Android Open Source Project
+ ~
+ ~ Licensed under the Apache License, Version 2.0 (the "License");
+ ~ you may not use this file except in compliance with the License.
+ ~ You may obtain a copy of the License at
+ ~
+ ~ http://www.apache.org/licenses/LICENSE-2.0
+ ~
+ ~ Unless required by applicable law or agreed to in writing, software
+ ~ distributed under the License is distributed on an "AS IS" BASIS,
+ ~ WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ ~ See the License for the specific language governing permissions and
+ ~ limitations under the License
+ -->
+
+<com.android.systemui.statusbar.notification.row.ChannelRow
+ xmlns:android="http://schemas.android.com/apk/res/android"
+ android:id="@+id/half_shelf_row"
+ android:layout_width="match_parent"
+ android:layout_height="wrap_content"
+ android:padding="8dp"
+ android:orientation="horizontal" >
+
+ <ImageView
+ android:id="@+id/icon"
+ android:layout_height="48dp"
+ android:layout_width="48dp"
+ android:layout_gravity="center_vertical"
+ android:padding="8dp"
+ />
+
+ <RelativeLayout
+ android:id="@+id/description_container"
+ android:layout_height="wrap_content"
+ android:layout_width="0dp"
+ android:layout_weight="1"
+ android:layout_gravity="center_vertical"
+ android:gravity="left|center_vertical"
+ android:orientation="vertical"
+ >
+ <TextView
+ android:id="@+id/channel_name"
+ android:layout_height="wrap_content"
+ android:layout_width="wrap_content"
+ android:paddingBottom="0dp"
+ android:paddingStart="8dp"
+ android:paddingEnd="8dp"
+ android:gravity="center_vertical|start"
+ android:textSize="14sp"
+ android:ellipsize="end"
+ android:maxLines="1"
+ style="@style/TextAppearance.NotificationInfo.Title"
+ />
+
+ <TextView
+ android:id="@+id/channel_description"
+ android:layout_height="wrap_content"
+ android:layout_width="wrap_content"
+ android:paddingStart="8dp"
+ android:paddingEnd="8dp"
+ android:gravity="center_vertical|start"
+ android:textSize="14sp"
+ android:ellipsize="end"
+ android:maxLines="1"
+ android:layout_below="@id/channel_name"
+ style="@style/TextAppearance.NotificationInfo.Secondary"
+ />
+ </RelativeLayout>
+
+ <Switch
+ android:id="@+id/toggle"
+ android:layout_height="wrap_content"
+ android:layout_width="wrap_content"
+ android:layout_gravity="center_vertical"
+ android:padding="8dp"
+ />
+</com.android.systemui.statusbar.notification.row.ChannelRow>
diff --git a/packages/SystemUI/res/values-af/strings.xml b/packages/SystemUI/res/values-af/strings.xml
index 760e3a72fea4..895c2fed70f1 100644
--- a/packages/SystemUI/res/values-af/strings.xml
+++ b/packages/SystemUI/res/values-af/strings.xml
@@ -448,6 +448,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"Moenie weer wys nie"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"Vee alles uit"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"Bestuur"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"Kennisgewings onderbreek deur Moenie Steur Nie"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"Begin nou"</string>
<string name="empty_shade_text" msgid="708135716272867002">"Geen kennisgewings nie"</string>
@@ -527,8 +531,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"Skerm is vasgespeld"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"Dit hou dit in sig totdat jy dit ontspeld. Raak en hou Terug en Oorsig om dit te ontspeld."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"Dit hou dit in sig totdat jy dit ontspeld. Raak en hou Terug en Tuis om dit te ontspeld."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"Dit hou dit in sig totdat jy dit ontspeld. Swiep op en hou om te ontspeld."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"Dit hou dit in sig totdat jy dit ontspeld. Raak en hou Oorsig om dit te ontspeld."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"Dit hou dit in sig totdat jy dit ontspeld. Raak en hou Tuis om dit te ontspeld."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"Raak en hou die Terug- en Oorsig-knoppie om hierdie skerm te ontspeld"</string>
@@ -912,8 +915,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"Maak <xliff:g id="APP_NAME">%1$s</xliff:g> oop"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"Instellings vir <xliff:g id="APP_NAME">%1$s</xliff:g>-borrels"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"Laat borrels vanaf <xliff:g id="APP_NAME">%1$s</xliff:g> toe?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"Bestuur"</string>
<string name="no_bubbles" msgid="337101288173078247">"Weier"</string>
<string name="yes_bubbles" msgid="668809525728633841">"Laat toe"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"Vra my later"</string>
diff --git a/packages/SystemUI/res/values-am/strings.xml b/packages/SystemUI/res/values-am/strings.xml
index 327e8a9d32eb..7522c6f942fd 100644
--- a/packages/SystemUI/res/values-am/strings.xml
+++ b/packages/SystemUI/res/values-am/strings.xml
@@ -448,6 +448,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"ዳግመኛ አታሳይ"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"ሁሉንም አጽዳ"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"ያቀናብሩ"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"ማሳወቂያዎች በአትረብሽ ባሉበት ቆመዋል"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"አሁን ጀምር"</string>
<string name="empty_shade_text" msgid="708135716272867002">"ምንም ማሳወቂያ የለም"</string>
@@ -527,8 +531,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"ማያ ገጽ ተሰክቷል"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"ይሄ እስኪነቅሉት ድረስ በእይታ ውስጥ ያስቀምጠዋል። ለመንቀል ተመለስ እና አጠቃላይ ዕይታ የሚለውን ይጫኑ እና ይያዙ።"</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"ይሄ እስኪነቅሉት ድረስ በእይታ ውስጥ ያስቀምጠዋል። ለመንቀል ተመለስ እና መነሻ የሚለውን ይንኩ እና ይያዙ።"</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"እስኪነቅሉት ድረስ ይህ በእይታ ውስጥ ያቆየዋል። ለመንቀል ወደ ላይ ጠረግ አድርገው ይያዙ።"</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"ይሄ እስኪነቅሉት ድረስ በእይታ ውስጥ ያስቀምጠዋል። ለመንቀል አጠቃላይ ዕይታ ተጭነው ይያዙ።"</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"ይሄ እስኪነቅሉት ድረስ በእይታ ውስጥ ያስቀምጠዋል። ለመንቀል መነሻ የሚለውን ይንኩ እና ይያዙ።"</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"ይህን ማያ ገጽ ለመንቀል ተመለስ እና አጠቃላይ ዕይታ አዝራሮችን ይንኩ እና ይያዙ"</string>
@@ -912,8 +915,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"<xliff:g id="APP_NAME">%1$s</xliff:g> ክፈት"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"ቅንብሮች ለ <xliff:g id="APP_NAME">%1$s</xliff:g> አረፋዎች"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"ከ <xliff:g id="APP_NAME">%1$s</xliff:g> አረፋዎች ይፈቀዱ?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"ያቀናብሩ"</string>
<string name="no_bubbles" msgid="337101288173078247">"ከልክል"</string>
<string name="yes_bubbles" msgid="668809525728633841">"ፍቀድ"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"በኋላ ጠይቀኝ"</string>
diff --git a/packages/SystemUI/res/values-ar/strings.xml b/packages/SystemUI/res/values-ar/strings.xml
index 19b10c380d91..618ef0f54b9e 100644
--- a/packages/SystemUI/res/values-ar/strings.xml
+++ b/packages/SystemUI/res/values-ar/strings.xml
@@ -460,6 +460,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"عدم الإظهار مرة أخرى"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"محو الكل"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"إدارة"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"تم إيقاف الإشعارات مؤقتًا وفقًا لإعداد \"الرجاء عدم الإزعاج\""</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"البدء الآن"</string>
<string name="empty_shade_text" msgid="708135716272867002">"ليس هناك أي اشعارات"</string>
@@ -539,8 +543,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"تم تثبيت الشاشة"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"يؤدي هذا إلى استمرار عرض الشاشة المُختارة إلى أن تتم إزالة تثبيتها. المس مع الاستمرار الزرين \"رجوع\" و\"نظرة عامة\" لإزالة التثبيت."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"يؤدي هذا إلى استمرار عرض الشاشة المُختارة إلى أن تتم إزالة تثبيتها. المس مع الاستمرار الزرين \"رجوع\" و\"الشاشة الرئيسية\" لإزالة التثبيت."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"يؤدي هذا إلى استمرار عرض الشاشة المُختارة إلى أن تتم إزالة تثبيتها. مرّر الشاشة بسرعة للأعلى مع الاستمرار لإزالة تثبيت الشاشة."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"يؤدي هذا إلى استمرار عرض الشاشة المُختارة إلى أن تتم إزالة تثبيتها. المس مع الاستمرار زر \"نظرة عامة\" لإزالة التثبيت."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"يؤدي هذا إلى استمرار عرض الشاشة المُختارة إلى أن تتم إزالة تثبيتها. المس مع الاستمرار زر \"الشاشة الرئيسية\" لإزالة التثبيت."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"لإزالة تثبيت هذه الشاشة، يمكنك أن تلمس مع الاستمرار زرّي \"رجوع\" و\"نظرة عامة\"."</string>
@@ -932,8 +935,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"فتح <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"إعداد الفقاعات التفسيرية على <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"هل تريد السماح بالفقاعات التفسيرية من <xliff:g id="APP_NAME">%1$s</xliff:g>؟"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"إدارة"</string>
<string name="no_bubbles" msgid="337101288173078247">"رفض"</string>
<string name="yes_bubbles" msgid="668809525728633841">"سماح"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"اسألني لاحقًا"</string>
diff --git a/packages/SystemUI/res/values-as/strings.xml b/packages/SystemUI/res/values-as/strings.xml
index 1fc4fa445f99..813581814803 100644
--- a/packages/SystemUI/res/values-as/strings.xml
+++ b/packages/SystemUI/res/values-as/strings.xml
@@ -448,6 +448,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"পুনৰাই নেদেখুৱাব"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"সকলো মচক"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"পৰিচালনা"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"অসুবিধা নিদিব-ই জাননী পজ কৰিছে"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"এতিয়াই আৰম্ভ কৰক"</string>
<string name="empty_shade_text" msgid="708135716272867002">"কোনো জাননী নাই"</string>
@@ -527,8 +531,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"স্ক্ৰীণ পিন কৰা হ’ল"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"এই কাৰ্যই আপুনি আনপিন নকৰালৈকে ইয়াক দেখা পোৱা অৱস্থাত ৰাখে। আনপিন কৰিবলৈ \'পিছলৈ যাওক\' আৰু \'অৱলোকন\'-ত স্পৰ্শ কৰি থাকক।"</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"এই কাৰ্যই আপুনি আনপিন নকৰালৈকে ইয়াক দেখা পোৱা অৱস্থাত ৰাখে। আনপিন কৰিবলৈ পিছলৈ যাওক আৰু হ\'মত স্পৰ্শ কৰি সেঁচি ধৰক।"</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"এই কাৰ্যই আপুনি আনপিন নকৰালৈকে ইয়াক দেখা পোৱা অৱস্থাত ৰাখে। আনপিন কৰিবলৈ ওপৰলৈ ছোৱাইপ কৰি ধৰি ৰাখক।"</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"এই কাৰ্যই আপুনি আনপিন নকৰালৈকে ইয়াক দেখা পোৱা অৱস্থাত ৰাখে। আনপিন কৰিবলৈ \'অৱলোকন\'-ত স্পৰ্শ কৰি থাকক।"</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"এই কাৰ্যই আপুনি আনপিন নকৰালৈকে ইয়াক দেখা পোৱা অৱস্থাত ৰাখে। আনপিন কৰিবলৈ পিছলৈ যাওক আৰু হ\'মত স্পৰ্শ কৰি সেঁচি ধৰক।"</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"এই স্ক্ৰীণখন আনপিন কৰিবলৈ পিছলৈ যাওক আৰু অৱলোকন বুটামত স্পৰ্শ কৰি হেঁচি ধৰক।"</string>
@@ -912,8 +915,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"<xliff:g id="APP_NAME">%1$s</xliff:g> খোলক"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"<xliff:g id="APP_NAME">%1$s</xliff:g>ৰ বাবলৰ ছেটিংসমূহ"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"<xliff:g id="APP_NAME">%1$s</xliff:g>ৰ বাবলসমূহক অনুমতি দিয়ক?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"পৰিচালনা কৰক"</string>
<string name="no_bubbles" msgid="337101288173078247">"অস্বীকাৰ কৰক"</string>
<string name="yes_bubbles" msgid="668809525728633841">"অনুমতি দিয়ক"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"মোক পিছত সুধিব"</string>
diff --git a/packages/SystemUI/res/values-az/strings.xml b/packages/SystemUI/res/values-az/strings.xml
index 9fb45b67eeb5..72242f9dcc52 100644
--- a/packages/SystemUI/res/values-az/strings.xml
+++ b/packages/SystemUI/res/values-az/strings.xml
@@ -448,6 +448,8 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"Daha göstərmə"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"Hamısını silin"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"İdarə edin"</string>
+ <string name="notification_section_header_gentle" msgid="8356064473678167305">"Daha az əhəmiyyətli bildirişlər"</string>
+ <string name="accessibility_notification_section_header_gentle_clear_all" msgid="4270384919249494640">"Az əhəmiyyətli bildirişlərin hamısını silin"</string>
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"Bildirişlər \"Narahat Etməyin\" rejimi tərəfindən dayandırıldı"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"İndi başlayın"</string>
<string name="empty_shade_text" msgid="708135716272867002">"Heç bir bildiriş yoxdur"</string>
@@ -527,8 +529,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"Ekrana sancaq taxıldı"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"Sancaq götürülənə qədər bu görünəcək. Sancağı götürmək üçün Geri və İcmal düymələrinə basıb saxlayın."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"Sancaq götürülənə qədər bu görünəcək. Sancağı götürmək üçün Geri və Əsas səhifə düymələrinə basıb saxlayın."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"Bu, onu çıxarana qədər görünəcək. Çıxarmaq üçün yuxarı sürüşdürün &amp; basıb saxlayın."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"Sancaq götürülənə qədər bu görünəcək. Sancağı götürmək üçün Geri düyməsinə basıb saxlayın."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"Sancaq götürülənə qədər bu görünəcək. Sancağı götürmək üçün Əsas səhifə düyməsinə basıb saxlayın."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"Bu ekrandan sancağı götürmək üçün Geri və İcmal düymələrinə basıb saxlayın"</string>
@@ -912,8 +913,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"<xliff:g id="APP_NAME">%1$s</xliff:g> tətbiqini açın"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"<xliff:g id="APP_NAME">%1$s</xliff:g> qabarcıqları üçün ayarlar"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"<xliff:g id="APP_NAME">%1$s</xliff:g> qabarcıqlarına icazə verilsin?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"İdarə edin"</string>
<string name="no_bubbles" msgid="337101288173078247">"İmtina edin"</string>
<string name="yes_bubbles" msgid="668809525728633841">"İcazə verin"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"Sonra soruşun"</string>
diff --git a/packages/SystemUI/res/values-b+sr+Latn/strings.xml b/packages/SystemUI/res/values-b+sr+Latn/strings.xml
index 8d4cca1bf093..67a92d36ce81 100644
--- a/packages/SystemUI/res/values-b+sr+Latn/strings.xml
+++ b/packages/SystemUI/res/values-b+sr+Latn/strings.xml
@@ -208,10 +208,10 @@
<string name="accessibility_notification_dismissed" msgid="854211387186306927">"Obaveštenje je odbačeno."</string>
<string name="accessibility_desc_notification_shade" msgid="4690274844447504208">"Prozor sa obaveštenjima."</string>
<string name="accessibility_desc_quick_settings" msgid="6186378411582437046">"Brza podešavanja."</string>
- <string name="accessibility_desc_lock_screen" msgid="5625143713611759164">"Zaključani ekran."</string>
+ <string name="accessibility_desc_lock_screen" msgid="5625143713611759164">"Zaključan ekran."</string>
<string name="accessibility_desc_settings" msgid="3417884241751434521">"Podešavanja"</string>
<string name="accessibility_desc_recent_apps" msgid="4876900986661819788">"Pregled."</string>
- <string name="accessibility_desc_work_lock" msgid="4288774420752813383">"Zaključani ekran za posao"</string>
+ <string name="accessibility_desc_work_lock" msgid="4288774420752813383">"Zaključan ekran za posao"</string>
<string name="accessibility_desc_close" msgid="7479755364962766729">"Zatvori"</string>
<string name="accessibility_quick_settings_wifi" msgid="5518210213118181692">"<xliff:g id="SIGNAL">%1$s</xliff:g>."</string>
<string name="accessibility_quick_settings_wifi_changed_off" msgid="8716484460897819400">"Wi-Fi je isključen."</string>
@@ -451,6 +451,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"Ne prikazuj ponovo"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"Obriši sve"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"Upravljajte"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"Obaveštenja su pauzirana režimom Ne uznemiravaj"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"Započni odmah"</string>
<string name="empty_shade_text" msgid="708135716272867002">"Nema obaveštenja"</string>
@@ -530,8 +534,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"Ekran je zakačen"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"Na ovaj način se ovo stalno prikazuje dok ga ne otkačite. Dodirnite i zadržite Nazad i Pregled da biste ga otkačili."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"Na ovaj način se ovo stalno prikazuje dok ga ne otkačite. Dodirnite i zadržite Nazad i Početna da biste ga otkačili."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"Na ovaj način se stalno prikazuje dok ga ne otkačite. Prevucite nagore i zadržite da biste ga otkačili."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"Na ovaj način se ovo stalno prikazuje dok ga ne otkačite. Dodirnite i zadržite Pregled da biste ga otkačili."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"Na ovaj način se ovo stalno prikazuje dok ga ne otkačite. Dodirnite i zadržite Početna da biste ga otkačili."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"Da biste otkačili ovaj ekran, dodirnite i zadržite dugmad Nazad i Pregled"</string>
@@ -823,7 +826,7 @@
<string name="accessibility_quick_settings_open_settings" msgid="7806613775728380737">"Otvori podešavanja za <xliff:g id="ID_1">%s</xliff:g>."</string>
<string name="accessibility_quick_settings_edit" msgid="7839992848995240393">"Izmeni redosled podešavanja."</string>
<string name="accessibility_quick_settings_page" msgid="5032979051755200721">"<xliff:g id="ID_1">%1$d</xliff:g>. strana od <xliff:g id="ID_2">%2$d</xliff:g>"</string>
- <string name="tuner_lock_screen" msgid="5755818559638850294">"Zaključani ekran"</string>
+ <string name="tuner_lock_screen" msgid="5755818559638850294">"Zaključan ekran"</string>
<string name="pip_phone_expand" msgid="5889780005575693909">"Proširi"</string>
<string name="pip_phone_minimize" msgid="1079119422589131792">"Umanji"</string>
<string name="pip_phone_close" msgid="8416647892889710330">"Zatvori"</string>
@@ -917,8 +920,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"Otvorite <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"Podešavanja za <xliff:g id="APP_NAME">%1$s</xliff:g> oblačiće"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"Želite li da omogućite oblačiće iz aplikacije <xliff:g id="APP_NAME">%1$s</xliff:g>?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"Upravljajte"</string>
<string name="no_bubbles" msgid="337101288173078247">"Odbij"</string>
<string name="yes_bubbles" msgid="668809525728633841">"Dozvoli"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"Pitaj me kasnije"</string>
diff --git a/packages/SystemUI/res/values-be/strings.xml b/packages/SystemUI/res/values-be/strings.xml
index 4e1a24885ea9..22bdd271a3c2 100644
--- a/packages/SystemUI/res/values-be/strings.xml
+++ b/packages/SystemUI/res/values-be/strings.xml
@@ -456,6 +456,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"Не паказваць зноў"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"Ачысціць усё"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"Кіраваць"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"Паказ апавяшчэнняў прыпынены ў рэжыме \"Не турбаваць\""</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"Пачаць зараз"</string>
<string name="empty_shade_text" msgid="708135716272867002">"Апавяшчэнняў няма"</string>
@@ -535,8 +539,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"Экран замацаваны"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"Будзе паказвацца, пакуль не адмацуеце. Каб адмацаваць, краніце і ўтрымлівайце кнопкі \"Назад\" і \"Агляд\"."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"Будзе паказвацца, пакуль не адмацуеце. Каб адмацаваць, націсніце і ўтрымлівайце кнопкі \"Назад\" і \"Галоўны экран\"."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"Будзе паказвацца, пакуль не адмацуеце Каб адмацаваць, прагартайце, утрымліваючы палец на экране"</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"Будзе паказвацца, пакуль не адмацуеце. Каб адмацаваць, краніце і ўтрымлівайце кнопку \"Агляд\"."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"Будзе паказвацца, пакуль не адмацуеце. Каб адмацаваць, націсніце і ўтрымлівайце кнопку \"Галоўны экран\"."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"Каб адмацаваць гэты экран, націсніце і ўтрымлівайце кнопкі \"Назад\" і \"Агляд\""</string>
@@ -924,8 +927,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"Адкрыць праграму \"<xliff:g id="APP_NAME">%1$s</xliff:g>\""</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"Налады дыялогаў у праграме \"<xliff:g id="APP_NAME">%1$s</xliff:g>\""</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"Дазволіць дыялогі з праграмы \"<xliff:g id="APP_NAME">%1$s</xliff:g>\"?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"Кіраваць"</string>
<string name="no_bubbles" msgid="337101288173078247">"Адмовіць"</string>
<string name="yes_bubbles" msgid="668809525728633841">"Дазволіць"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"Спытаць пазней"</string>
diff --git a/packages/SystemUI/res/values-bg/strings.xml b/packages/SystemUI/res/values-bg/strings.xml
index 38321d95df3a..b905cbc50f0d 100644
--- a/packages/SystemUI/res/values-bg/strings.xml
+++ b/packages/SystemUI/res/values-bg/strings.xml
@@ -448,6 +448,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"Да не се показва отново"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"Изчистване на всички"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"Управление"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"Известията са поставени на пауза от режима „Не безпокойте“"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"Стартиране сега"</string>
<string name="empty_shade_text" msgid="708135716272867002">"Няма известия"</string>
@@ -527,8 +531,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"Екранът е фиксиран"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"Екранът ще се показва, докато не го освободите с докосване и задържане на бутона за връщане назад и този за общ преглед."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"Екранът ще се показва, докато не го освободите с докосване и задържане на бутона за връщане назад и „Начало“."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"Екранът ще остане на преден план, докато не го освободите. Прекарайте пръст нагоре и задръжте за освобождаване."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"Екранът ще се показва, докато не го освободите с докосване и задържане на бутона за общ преглед."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"Екранът ще се показва, докато не го освободите с докосване и задържане на бутона „Начало“."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"За да освободите този екран, докоснете и задръжте бутона за връщане назад и този за общ преглед"</string>
@@ -912,8 +915,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"Отваряне на „<xliff:g id="APP_NAME">%1$s</xliff:g>“"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"Настройки за балончетата за <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"Да се разрешат ли балончетата от <xliff:g id="APP_NAME">%1$s</xliff:g>?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"Управление"</string>
<string name="no_bubbles" msgid="337101288173078247">"Отказ"</string>
<string name="yes_bubbles" msgid="668809525728633841">"Разрешаване"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"Попитайте ме по-късно"</string>
diff --git a/packages/SystemUI/res/values-bn/strings.xml b/packages/SystemUI/res/values-bn/strings.xml
index 2d633698e2e9..e2f42708797b 100644
--- a/packages/SystemUI/res/values-bn/strings.xml
+++ b/packages/SystemUI/res/values-bn/strings.xml
@@ -448,6 +448,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"আর দেখাবেন না"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"সবকিছু সাফ করুন"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"পরিচালনা করুন"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"\'বিরক্ত করবেন না\' দিয়ে বিজ্ঞপ্তি পজ করা হয়েছে"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"এখন শুরু করুন"</string>
<string name="empty_shade_text" msgid="708135716272867002">"কোনো বিজ্ঞপ্তি নেই"</string>
@@ -527,8 +531,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"স্ক্রিন পিন করা হয়েছে"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"এটি আপনি আনপিন না করা পর্যন্ত এটিকে প্রদর্শিত করবে৷ আনপিন করতে ফিরুন এবং ওভারভিউ স্পর্শ করে ধরে থাকুন।"</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"এর ফলে আপনি এটি আনপিন না করা পর্যন্ত এটি দেখানো হতে থাকবে। আনপিন করতে \"ফিরে যান\" এবং \"হোম\" বোতামদুটি ট্যাপ করে ধরে রাখুন।"</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"এর ফলে আপনি আনপিন না করা পর্যন্ত এটি দেখানো হতে থাকবে। আনপিন করার জন্য উপরের দিকে সোয়াইপ করে ধরে থাকুন"</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"এটি আপনি আনপিন না করা পর্যন্ত এটিকে প্রদর্শিত করবে৷ আনপিন করতে ওভারভিউ স্পর্শ করে ধরে থাকুন৷"</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"এর ফলে আপনি এটি আনপিন না করা পর্যন্ত এটি দেখানো হতে থাকবে। আনপিন করতে \"হোম\" বোতামটি ট্যাপ করে ধরে রাখুন।"</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"এই স্ক্রিনটি আনপিন করতে \"ফিরে যান\" এবং \"এক নজরে\" বোতামদুটি ট্যাপ করে ধরে রাখুন"</string>
@@ -766,7 +769,7 @@
<string name="right_keycode" msgid="708447961000848163">"ডানদিকের কিকোড"</string>
<string name="left_icon" msgid="3096287125959387541">"বাঁ দিকের আইকন"</string>
<string name="right_icon" msgid="3952104823293824311">"ডানদিকের আইকন"</string>
- <string name="drag_to_add_tiles" msgid="230586591689084925">"টাইল যোগ করতে ট্যাপ করে টেনে আনুন"</string>
+ <string name="drag_to_add_tiles" msgid="230586591689084925">"টাইল যোগ করতে ধরে থেকে টেনে আনুন"</string>
<string name="drag_to_rearrange_tiles" msgid="4566074720193667473">"টাইলগুলি আবার সাজানোর জন্য ধরে থেকে টেনে আনুন"</string>
<string name="drag_to_remove_tiles" msgid="3361212377437088062">"সরানোর জন্য এখানে টেনে আনুন"</string>
<string name="drag_to_remove_disabled" msgid="2390968976638993382">"অন্তত ৬টি টাইল রাখতে হবে"</string>
@@ -912,8 +915,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"<xliff:g id="APP_NAME">%1$s</xliff:g> খুলুন"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"<xliff:g id="APP_NAME">%1$s</xliff:g> বাবলের জন্য সেটিংস"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"<xliff:g id="APP_NAME">%1$s</xliff:g> অ্যাপের বাবল চালু করবেন?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"ম্যানেজ করা"</string>
<string name="no_bubbles" msgid="337101288173078247">"খারিজ করুন"</string>
<string name="yes_bubbles" msgid="668809525728633841">"অনুমতি দিন"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"আমাকে পরে জিজ্ঞাসা করুন"</string>
diff --git a/packages/SystemUI/res/values-bs/strings.xml b/packages/SystemUI/res/values-bs/strings.xml
index ccd81d4cc746..c26e2a3c9f13 100644
--- a/packages/SystemUI/res/values-bs/strings.xml
+++ b/packages/SystemUI/res/values-bs/strings.xml
@@ -451,6 +451,8 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"Ne prikazuj opet"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"Očisti sve"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"Upravljaj"</string>
+ <string name="notification_section_header_gentle" msgid="8356064473678167305">"Neupadljive obavijesti"</string>
+ <string name="accessibility_notification_section_header_gentle_clear_all" msgid="4270384919249494640">"Izbrišite sve neupadljive obavijesti"</string>
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"Obavještenja su pauzirana načinom rada Ne ometaj"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"Započni odmah"</string>
<string name="empty_shade_text" msgid="708135716272867002">"Nema obavještenja"</string>
@@ -530,8 +532,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"Ekran je prikačen"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"Ekran ostaje prikazan ovako dok ga ne otkačite. Da ga otkačite, dodirnite i držite dugme Nazad."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"Na ovaj način ekran ostaje prikazan dok ga ne otkačite. Da otkačite ekran, dodirnite i držite dugme Nazad i Početna."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"Na ovaj način ekran ostaje prikazan dok ga ne otkačite. Prevucite prema gore i držite da otkačite."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"Ekran ostaje prikazan ovako dok ga ne otkačite. Da ga otkačite, dodirnite i držite dugme Pregled."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"Na ovaj način ekran ostaje prikazan dok ga ne otkačite. Da okačite ekran, dodirnite ili držite dugme Početna."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"Dodirnite i držite dugmad Nazad i Pregled da otkačite ekran"</string>
@@ -661,7 +662,7 @@
<string name="appops_mic_overlay" msgid="4835157962857919804">"Ova aplikacija prekriva druge aplikacije na ekranu i koristi mikrofon."</string>
<string name="appops_camera_mic_overlay" msgid="6718768197048030993">"Ova aplikacija prekriva druge aplikacije na ekranu i koristi mikrofon i kameru."</string>
<string name="notification_appops_settings" msgid="1028328314935908050">"Postavke"</string>
- <string name="notification_appops_ok" msgid="1156966426011011434">"UREDU"</string>
+ <string name="notification_appops_ok" msgid="1156966426011011434">"Uredu"</string>
<string name="notification_channel_controls_opened_accessibility" msgid="6553950422055908113">"Otvorene su kontrole obavještenja za aplikaciju <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="notification_channel_controls_closed_accessibility" msgid="7521619812603693144">"Zatvorene su kontrole obavještenja za aplikaciju <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="notification_channel_switch_accessibility" msgid="3420796005601900717">"Dozvoli obavještenja s ovog kanala"</string>
@@ -717,7 +718,7 @@
<string name="keyboard_key_numpad_template" msgid="8729216555174634026">"Numerička tastatura <xliff:g id="NAME">%1$s</xliff:g>"</string>
<string name="keyboard_shortcut_group_system" msgid="6472647649616541064">"Sistem"</string>
<string name="keyboard_shortcut_group_system_home" msgid="3054369431319891965">"Početak"</string>
- <string name="keyboard_shortcut_group_system_recents" msgid="3154851905021926744">"Nedavni ekrani"</string>
+ <string name="keyboard_shortcut_group_system_recents" msgid="3154851905021926744">"Nedavno"</string>
<string name="keyboard_shortcut_group_system_back" msgid="2207004531216446378">"Nazad"</string>
<string name="keyboard_shortcut_group_system_notifications" msgid="8366964080041773224">"Obavještenja"</string>
<string name="keyboard_shortcut_group_system_shortcuts_helper" msgid="4892255911160332762">"Prečice tastature"</string>
@@ -917,10 +918,9 @@
<string name="music_controls_no_title" msgid="5236895307087002011">"Bez naslova"</string>
<string name="restart_button_description" msgid="2035077840254950187">"Dodirnite da ponovo pokrenete ovu aplikaciju i aktivirate prikaz preko cijelog ekrana."</string>
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"Otvori aplikaciju <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
- <string name="bubbles_settings_button_description" msgid="2970630476657287189">"Postavke za mjehuriće aplikacije <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
- <string name="bubbles_prompt" msgid="8807968030159469710">"Dozvoliti mjehuriće iz aplikacije <xliff:g id="APP_NAME">%1$s</xliff:g>?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="bubbles_settings_button_description" msgid="2970630476657287189">"Postavke za oblačiće aplikacije <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
+ <string name="bubbles_prompt" msgid="8807968030159469710">"Dozvoliti oblačiće iz aplikacije <xliff:g id="APP_NAME">%1$s</xliff:g>?"</string>
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"Upravljaj"</string>
<string name="no_bubbles" msgid="337101288173078247">"Odbij"</string>
<string name="yes_bubbles" msgid="668809525728633841">"Dozvoli"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"Pitaj me kasnije"</string>
diff --git a/packages/SystemUI/res/values-ca/strings.xml b/packages/SystemUI/res/values-ca/strings.xml
index 62ee99cef74c..2056212cd97e 100644
--- a/packages/SystemUI/res/values-ca/strings.xml
+++ b/packages/SystemUI/res/values-ca/strings.xml
@@ -178,7 +178,7 @@
<string name="data_connection_roaming" msgid="6037232010953697354">"Itinerància"</string>
<string name="data_connection_edge" msgid="871835227939216682">"EDGE"</string>
<string name="accessibility_data_connection_wifi" msgid="2324496756590645221">"Wi-Fi"</string>
- <string name="accessibility_no_sim" msgid="8274017118472455155">"No hi ha cap targeta SIM."</string>
+ <string name="accessibility_no_sim" msgid="8274017118472455155">"No hi ha cap SIM."</string>
<string name="accessibility_cell_data" msgid="5326139158682385073">"Dades mòbils"</string>
<string name="accessibility_cell_data_on" msgid="5927098403452994422">"Dades mòbils activades"</string>
<string name="cell_data_off_content_description" msgid="4356113230238585072">"S\'han desactivat les dades mòbils"</string>
@@ -187,7 +187,7 @@
<string name="accessibility_bluetooth_tether" msgid="4102784498140271969">"Compartició de xarxa per Bluetooth"</string>
<string name="accessibility_airplane_mode" msgid="834748999790763092">"Mode d\'avió."</string>
<string name="accessibility_vpn_on" msgid="5993385083262856059">"VPN activada"</string>
- <string name="accessibility_no_sims" msgid="3957997018324995781">"No hi ha cap targeta SIM."</string>
+ <string name="accessibility_no_sims" msgid="3957997018324995781">"No hi ha cap SIM."</string>
<string name="carrier_network_change_mode" msgid="8149202439957837762">"S\'està canviant la xarxa de l\'operador de telefonia mòbil"</string>
<string name="accessibility_battery_details" msgid="7645516654955025422">"Obre els detalls de la bateria"</string>
<string name="accessibility_battery_level" msgid="7451474187113371965">"<xliff:g id="NUMBER">%d</xliff:g> per cent de bateria."</string>
@@ -448,6 +448,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"No ho tornis a mostrar"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"Esborra-ho tot"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"Gestió"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"Notificacions pausades pel mode No molestis"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"Comença ara"</string>
<string name="empty_shade_text" msgid="708135716272867002">"Cap notificació"</string>
@@ -527,8 +531,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"La pantalla està fixada"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"Aquest element es continuarà mostrant fins que deixis de fixar-lo. Per fer-ho, toca i mantén premudes els botons Enrere i Aplicacions recents."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"Aquest element es continuarà mostrant fins que deixis de fixar-lo. Per fer-ho, mantén premuts els botons Enrere i Inici."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"Aquest element es continuarà mostrant fins que deixis de fixar-lo. Llisca cap amunt i mantén premut per deixar de fixar-lo."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"Aquest element es continuarà mostrant fins que deixis de fixar-lo. Per fer-ho, toca i mantén premut el botó Aplicacions recents."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"Aquest element es continuarà mostrant fins que deixis de fixar-lo. Per fer-ho, mantén premut el botó d\'inici."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"Per deixar de fixar aquesta pantalla, mantén premuts els botons Enrere i Aplicacions recents"</string>
@@ -639,12 +642,12 @@
<string name="inline_turn_off_notifications" msgid="8635596135532202355">"Desactiva les notificacions"</string>
<string name="inline_keep_showing_app" msgid="1723113469580031041">"Vols continuar rebent notificacions d\'aquesta aplicació?"</string>
<string name="notification_silence_title" msgid="7352089096356977930">"Discreta"</string>
- <string name="notification_alert_title" msgid="3966526305405016221">"Prioritària"</string>
- <string name="notification_channel_summary_low" msgid="1065819618107531284">"T\'ajuda a centrar-te en les notificacions que es mostren a l\'àrea de notificacions. Sempre silenciosa."</string>
- <string name="notification_channel_summary_low_status" msgid="2702170424808743755">"Es mostra a sota de les notificacions prioritàries. Sempre silenciosa."</string>
- <string name="notification_channel_summary_low_lock" msgid="7966605244472624458">"Es mostra a sota de les notificacions prioritàries. Sempre silenciosa."</string>
- <string name="notification_channel_summary_low_status_lock" msgid="7012562768950012739">"Es mostra a sota de les notificacions prioritàries. Sempre silenciosa."</string>
- <string name="notification_channel_summary_default" msgid="3847289783382316019">"Emet un so i mostra una icona a la barra d\'estat. Es mostra a la pantalla de bloqueig."</string>
+ <string name="notification_alert_title" msgid="3966526305405016221">"Prioritàries"</string>
+ <string name="notification_channel_summary_low" msgid="1065819618107531284">"T\'ajuda a concentrar-te perquè les notificacions només es mostren a l\'àrea desplegable. Sempre en silenci."</string>
+ <string name="notification_channel_summary_low_status" msgid="2702170424808743755">"Es mostra a sota de les notificacions prioritàries. Sempre en silenci."</string>
+ <string name="notification_channel_summary_low_lock" msgid="7966605244472624458">"Es mostra a sota de les notificacions prioritàries. Sempre en silenci."</string>
+ <string name="notification_channel_summary_low_status_lock" msgid="7012562768950012739">"Es mostra a sota de les notificacions prioritàries. Sempre en silenci."</string>
+ <string name="notification_channel_summary_default" msgid="3847289783382316019">"Atrau la teva atenció amb un so i una icona a la barra d\'estat. Es mostra a la pantalla de bloqueig."</string>
<string name="notification_unblockable_desc" msgid="4556908766584964102">"Aquestes notificacions no es poden modificar."</string>
<string name="notification_multichannel_desc" msgid="4695920306092240550">"Aquest grup de notificacions no es pot configurar aquí"</string>
<string name="notification_delegate_header" msgid="2857691673814814270">"Notificació mitjançant aplicació intermediària"</string>
@@ -881,7 +884,7 @@
<string name="running_foreground_services_title" msgid="381024150898615683">"Aplicacions que s\'estan executant en segon pla"</string>
<string name="running_foreground_services_msg" msgid="6326247670075574355">"Toca per obtenir informació sobre l\'ús de dades i de bateria"</string>
<string name="mobile_data_disable_title" msgid="1068272097382942231">"Vols desactivar les dades mòbils?"</string>
- <string name="mobile_data_disable_message" msgid="4756541658791493506">"No tindràs accés a dades ni a Internet amb <xliff:g id="CARRIER">%s</xliff:g>. Només podràs accedir a Internet per Wi-Fi."</string>
+ <string name="mobile_data_disable_message" msgid="4756541658791493506">"No tindràs accés a dades ni a Internet mitjançant <xliff:g id="CARRIER">%s</xliff:g>. Internet només estarà disponible per Wi-Fi."</string>
<string name="mobile_data_disable_message_default_carrier" msgid="6078110473451946831">"el teu operador de telefonia mòbil"</string>
<string name="touch_filtered_warning" msgid="8671693809204767551">"Com que hi ha una aplicació que oculta una sol·licitud de permís, no es pot verificar la teva resposta des de la configuració."</string>
<string name="slice_permission_title" msgid="7465009437851044444">"Vols permetre que <xliff:g id="APP_0">%1$s</xliff:g> mostri porcions de l\'aplicació <xliff:g id="APP_2">%2$s</xliff:g>?"</string>
@@ -912,8 +915,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"Obre <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"Configuració de les bombolles: <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"Vols permetre les bombolles de l\'aplicació <xliff:g id="APP_NAME">%1$s</xliff:g>?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"Gestiona"</string>
<string name="no_bubbles" msgid="337101288173078247">"Denega"</string>
<string name="yes_bubbles" msgid="668809525728633841">"Permet"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"Pregunta-m\'ho més tard"</string>
diff --git a/packages/SystemUI/res/values-cs/strings.xml b/packages/SystemUI/res/values-cs/strings.xml
index a9687313b23d..5976839224f1 100644
--- a/packages/SystemUI/res/values-cs/strings.xml
+++ b/packages/SystemUI/res/values-cs/strings.xml
@@ -454,6 +454,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"Tuto zprávu příště nezobrazovat"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"Smazat vše"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"Spravovat"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"Oznámení jsou pozastavena režimem Nerušit"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"Spustit"</string>
<string name="empty_shade_text" msgid="708135716272867002">"Žádná oznámení"</string>
@@ -533,8 +537,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"Obrazovka je připnuta"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"Obsah bude připnut v zobrazení, dokud jej neuvolníte. Uvolníte jej stisknutím a podržením tlačítek Zpět a Přehled."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"Obsah bude připnut v zobrazení, dokud ho neuvolníte. Uvolníte ho podržením tlačítek Zpět a Plocha."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"Obsah bude připnut v zobrazení, dokud ho neuvolníte. Uvolnit ho můžete přejetím nahoru a podržením."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"Obsah bude připnut v zobrazení, dokud jej neuvolníte. Uvolníte jej stisknutím a podržením tlačítka Přehled."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"Obsah bude připnut v zobrazení, dokud ho neuvolníte. Uvolníte ho podržením tlačítka Plocha."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"Chcete-li tuto obrazovku uvolnit, podržte tlačítka Zpět a Přehled"</string>
@@ -596,7 +599,7 @@
<string name="zen_alarm_warning_indef" msgid="3482966345578319605">"Pokud tento režim nevypnete, svůj další budík <xliff:g id="WHEN">%1$s</xliff:g> neuslyšíte"</string>
<string name="zen_alarm_warning" msgid="444533119582244293">"Svůj další budík <xliff:g id="WHEN">%1$s</xliff:g> neuslyšíte"</string>
<string name="alarm_template" msgid="3980063409350522735">"v <xliff:g id="WHEN">%1$s</xliff:g>"</string>
- <string name="alarm_template_far" msgid="4242179982586714810">"dne <xliff:g id="WHEN">%1$s</xliff:g>"</string>
+ <string name="alarm_template_far" msgid="4242179982586714810">"<xliff:g id="WHEN">%1$s</xliff:g>"</string>
<string name="accessibility_quick_settings_detail" msgid="2579369091672902101">"Rychlé nastavení <xliff:g id="TITLE">%s</xliff:g>."</string>
<string name="accessibility_status_bar_hotspot" msgid="4099381329956402865">"Hotspot"</string>
<string name="accessibility_managed_profile" msgid="6613641363112584120">"Pracovní profil"</string>
@@ -922,8 +925,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"Otevřít <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"Nastavení bublin aplikace <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"Povolit bubliny z aplikace <xliff:g id="APP_NAME">%1$s</xliff:g>?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"Spravovat"</string>
<string name="no_bubbles" msgid="337101288173078247">"Zakázat"</string>
<string name="yes_bubbles" msgid="668809525728633841">"Povolit"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"Zeptat se později"</string>
diff --git a/packages/SystemUI/res/values-da/strings.xml b/packages/SystemUI/res/values-da/strings.xml
index 1aa1ab6cd2ba..7bb720fcc735 100644
--- a/packages/SystemUI/res/values-da/strings.xml
+++ b/packages/SystemUI/res/values-da/strings.xml
@@ -448,6 +448,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"Vis ikke igen"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"Ryd alt"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"Administrer"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"Notifikationer er sat på pause af Forstyr ikke"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"Start nu"</string>
<string name="empty_shade_text" msgid="708135716272867002">"Ingen notifikationer"</string>
@@ -527,8 +531,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"Skærmen er fastgjort"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"Dette fastholder skærmen i visningen, indtil du frigør den. Tryk på Tilbage og Overblik, og hold fingeren nede for at frigøre skærmen."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"Dette fastholder skærmen i visningen, indtil du frigør den. Hold Tilbage og Startskærm nede for at frigøre skærmen."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"Dette fastholder skærmen i visningen, indtil du frigør den. Stryg opad, og hold fingeren nede for at frigøre den."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"Dette fastholder skærmen i visningen, indtil du frigør den. Tryk på Tilbage, og hold fingeren nede for at frigøre skærmen."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"Dette fastholder skærmen i visningen, indtil du frigør den. Hold Startskærm nede for at frigøre skærmen."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"Hold knapperne Tilbage og Oversigt nede for at frigøre skærmen"</string>
@@ -719,7 +722,7 @@
<string name="keyboard_shortcut_group_applications_assist" msgid="9095441910537146013">"Assistance"</string>
<string name="keyboard_shortcut_group_applications_browser" msgid="6465985474000766533">"Browser"</string>
<string name="keyboard_shortcut_group_applications_contacts" msgid="2064197111278436375">"Kontakter"</string>
- <string name="keyboard_shortcut_group_applications_email" msgid="6257036897441939004">"E-mail"</string>
+ <string name="keyboard_shortcut_group_applications_email" msgid="6257036897441939004">"Mail"</string>
<string name="keyboard_shortcut_group_applications_sms" msgid="638701213803242744">"Sms"</string>
<string name="keyboard_shortcut_group_applications_music" msgid="4775559515850922780">"Musik"</string>
<string name="keyboard_shortcut_group_applications_youtube" msgid="6555453761294723317">"YouTube"</string>
@@ -912,8 +915,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"Åbn <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"Indstillinger for <xliff:g id="APP_NAME">%1$s</xliff:g>-bobler"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"Vil du tillade bobler fra <xliff:g id="APP_NAME">%1$s</xliff:g>?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"Administrer"</string>
<string name="no_bubbles" msgid="337101288173078247">"Afvis"</string>
<string name="yes_bubbles" msgid="668809525728633841">"Tillad"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"Spørg mig senere"</string>
diff --git a/packages/SystemUI/res/values-de/strings.xml b/packages/SystemUI/res/values-de/strings.xml
index 84fd4488ed44..7632c1848728 100644
--- a/packages/SystemUI/res/values-de/strings.xml
+++ b/packages/SystemUI/res/values-de/strings.xml
@@ -452,6 +452,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"Nicht mehr anzeigen"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"Alle löschen"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"Verwalten"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"Benachrichtigungen durch \"Bitte nicht stören\" pausiert"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"Jetzt starten"</string>
<string name="empty_shade_text" msgid="708135716272867002">"Keine Benachrichtigungen"</string>
@@ -531,8 +535,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"Bildschirm ist fixiert"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"Der Bildschirm bleibt so lange eingeblendet, bis du die Fixierung aufhebst. Berühre und halte dazu \"Zurück\" und \"Übersicht\"."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"Der Bildschirm wird so lange angezeigt, bis du die Fixierung aufhebst. Berühre und halte dazu \"Zurück\" und \"Startbildschirm\"."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"Der Bildschirm wird so lange angezeigt, bis du die Fixierung aufhebst. Dazu wischst du nach oben und hältst den Bildschirm gedrückt"</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"Der Bildschirm bleibt so lange eingeblendet, bis du die Fixierung aufhebst. Berühre und halte dazu \"Übersicht\"."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"Der Bildschirm wird so lange angezeigt, bis du die Fixierung aufhebst. Berühre und halte dazu \"Startbildschirm\"."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"Um die Fixierung für diesen Bildschirm aufzuheben, berühre und halte \"Zurück\" und \"Übersicht\""</string>
@@ -916,8 +919,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"<xliff:g id="APP_NAME">%1$s</xliff:g> öffnen"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"Einstellungen für <xliff:g id="APP_NAME">%1$s</xliff:g>-Bubbles"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"<xliff:g id="APP_NAME">%1$s</xliff:g>-Bubbles zulassen?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"Verwalten"</string>
<string name="no_bubbles" msgid="337101288173078247">"Ablehnen"</string>
<string name="yes_bubbles" msgid="668809525728633841">"Zulassen"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"Später fragen"</string>
diff --git a/packages/SystemUI/res/values-el/strings.xml b/packages/SystemUI/res/values-el/strings.xml
index 670a9171cbb4..308cd32c508e 100644
--- a/packages/SystemUI/res/values-el/strings.xml
+++ b/packages/SystemUI/res/values-el/strings.xml
@@ -448,6 +448,8 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"Να μην εμφανιστεί ξανά"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"Διαγραφή όλων"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"Διαχείριση"</string>
+ <string name="notification_section_header_gentle" msgid="8356064473678167305">"Διακριτικές ειδοποιήσεις"</string>
+ <string name="accessibility_notification_section_header_gentle_clear_all" msgid="4270384919249494640">"Καταργήστε όλες τις διακριτικές ειδοποιήσεις"</string>
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"Οι ειδοποιήσεις τέθηκαν σε παύση από τη λειτουργία \"Μην ενοχλείτε\""</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"Έναρξη τώρα"</string>
<string name="empty_shade_text" msgid="708135716272867002">"Δεν υπάρχουν ειδοποιήσεις"</string>
@@ -527,8 +529,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"Η οθόνη καρφιτσώθηκε"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"Με αυτόν τον τρόπο παραμένει σε προβολή μέχρι να το ξεκαρφιτσώσετε. Αγγίξτε παρατεταμένα τα στοιχεία \"Επιστροφή\" και \"Επισκόπηση\" για ξεκαρφίτσωμα."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"Με αυτόν τον τρόπο, παραμένει σε προβολή μέχρι να το ξεκαρφιτσώσετε. Αγγίξτε παρατεταμένα τα στοιχεία \"Πίσω\" και \"Αρχική οθόνη\" για ξεκαρφίτσωμα."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"Με αυτόν τον τρόπο, παραμένει σε προβολή μέχρι να το ξεκαρφιτσώσετε. Σύρετε προς τα επάνω και κρατήστε πατημένο το δάχτυλό σας για ξεκαρφίτσωμα."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"Με αυτόν τον τρόπο παραμένει σε προβολή μέχρι να το ξεκαρφιτσώσετε. Αγγίξτε παρατεταμένα την \"Επισκόπηση\" για ξεκαρφίτσωμα."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"Με αυτόν τον τρόπο, παραμένει σε προβολή μέχρι να το ξεκαρφιτσώσετε. Αγγίξτε παρατεταμένα το στοιχείο \"Αρχική οθόνη\" για ξεκαρφίτσωμα."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"Για να ξεκαρφιτσώσετε αυτήν την οθόνη, αγγίξτε παρατεταμένα τα κουμπιά \"Πίσω\" και \"Επισκόπηση\""</string>
@@ -912,8 +913,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"Άνοιγμα <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"Ρυθμίσεις για συννεφάκια <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"Να επιτρέπονται συννεφάκια από την εφαρμογή <xliff:g id="APP_NAME">%1$s</xliff:g>;"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"Διαχείριση"</string>
<string name="no_bubbles" msgid="337101288173078247">"Όχι"</string>
<string name="yes_bubbles" msgid="668809525728633841">"Να επιτρέπεται"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"Να ερωτηθώ αργότερα"</string>
diff --git a/packages/SystemUI/res/values-en-rAU/strings.xml b/packages/SystemUI/res/values-en-rAU/strings.xml
index 61b39e210e46..21c3bea81c6c 100644
--- a/packages/SystemUI/res/values-en-rAU/strings.xml
+++ b/packages/SystemUI/res/values-en-rAU/strings.xml
@@ -448,6 +448,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"Don\'t show again"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"Clear all"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"Manage"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"Notifications paused by Do Not Disturb"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"Start now"</string>
<string name="empty_shade_text" msgid="708135716272867002">"No notifications"</string>
@@ -527,8 +531,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"Screen is pinned"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"This keeps it in view until you unpin. Touch &amp; hold Back and Overview to unpin."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"This keeps it in view until you unpin. Touch &amp; hold Back and Home to unpin."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"This keeps it in view until you unpin. Swipe up &amp; hold to unpin."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"This keeps it in view until you unpin. Touch &amp; hold Overview to unpin."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"This keeps it in view until you unpin. Touch &amp; hold Home to unpin."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"To unpin this screen, touch &amp; hold Back and Overview buttons"</string>
@@ -912,8 +915,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"Open <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"Settings for <xliff:g id="APP_NAME">%1$s</xliff:g> bubbles"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"Allow bubbles from <xliff:g id="APP_NAME">%1$s</xliff:g>?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"Manage"</string>
<string name="no_bubbles" msgid="337101288173078247">"Deny"</string>
<string name="yes_bubbles" msgid="668809525728633841">"Allow"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"Ask me later"</string>
diff --git a/packages/SystemUI/res/values-en-rCA/strings.xml b/packages/SystemUI/res/values-en-rCA/strings.xml
index 0359727fff6b..b8898cf6adb9 100644
--- a/packages/SystemUI/res/values-en-rCA/strings.xml
+++ b/packages/SystemUI/res/values-en-rCA/strings.xml
@@ -448,6 +448,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"Don\'t show again"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"Clear all"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"Manage"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"Notifications paused by Do Not Disturb"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"Start now"</string>
<string name="empty_shade_text" msgid="708135716272867002">"No notifications"</string>
@@ -527,8 +531,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"Screen is pinned"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"This keeps it in view until you unpin. Touch &amp; hold Back and Overview to unpin."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"This keeps it in view until you unpin. Touch &amp; hold Back and Home to unpin."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"This keeps it in view until you unpin. Swipe up &amp; hold to unpin."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"This keeps it in view until you unpin. Touch &amp; hold Overview to unpin."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"This keeps it in view until you unpin. Touch &amp; hold Home to unpin."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"To unpin this screen, touch &amp; hold Back and Overview buttons"</string>
@@ -912,8 +915,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"Open <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"Settings for <xliff:g id="APP_NAME">%1$s</xliff:g> bubbles"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"Allow bubbles from <xliff:g id="APP_NAME">%1$s</xliff:g>?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"Manage"</string>
<string name="no_bubbles" msgid="337101288173078247">"Deny"</string>
<string name="yes_bubbles" msgid="668809525728633841">"Allow"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"Ask me later"</string>
diff --git a/packages/SystemUI/res/values-en-rGB/strings.xml b/packages/SystemUI/res/values-en-rGB/strings.xml
index 61b39e210e46..21c3bea81c6c 100644
--- a/packages/SystemUI/res/values-en-rGB/strings.xml
+++ b/packages/SystemUI/res/values-en-rGB/strings.xml
@@ -448,6 +448,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"Don\'t show again"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"Clear all"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"Manage"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"Notifications paused by Do Not Disturb"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"Start now"</string>
<string name="empty_shade_text" msgid="708135716272867002">"No notifications"</string>
@@ -527,8 +531,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"Screen is pinned"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"This keeps it in view until you unpin. Touch &amp; hold Back and Overview to unpin."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"This keeps it in view until you unpin. Touch &amp; hold Back and Home to unpin."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"This keeps it in view until you unpin. Swipe up &amp; hold to unpin."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"This keeps it in view until you unpin. Touch &amp; hold Overview to unpin."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"This keeps it in view until you unpin. Touch &amp; hold Home to unpin."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"To unpin this screen, touch &amp; hold Back and Overview buttons"</string>
@@ -912,8 +915,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"Open <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"Settings for <xliff:g id="APP_NAME">%1$s</xliff:g> bubbles"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"Allow bubbles from <xliff:g id="APP_NAME">%1$s</xliff:g>?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"Manage"</string>
<string name="no_bubbles" msgid="337101288173078247">"Deny"</string>
<string name="yes_bubbles" msgid="668809525728633841">"Allow"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"Ask me later"</string>
diff --git a/packages/SystemUI/res/values-en-rIN/strings.xml b/packages/SystemUI/res/values-en-rIN/strings.xml
index 61b39e210e46..21c3bea81c6c 100644
--- a/packages/SystemUI/res/values-en-rIN/strings.xml
+++ b/packages/SystemUI/res/values-en-rIN/strings.xml
@@ -448,6 +448,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"Don\'t show again"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"Clear all"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"Manage"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"Notifications paused by Do Not Disturb"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"Start now"</string>
<string name="empty_shade_text" msgid="708135716272867002">"No notifications"</string>
@@ -527,8 +531,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"Screen is pinned"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"This keeps it in view until you unpin. Touch &amp; hold Back and Overview to unpin."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"This keeps it in view until you unpin. Touch &amp; hold Back and Home to unpin."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"This keeps it in view until you unpin. Swipe up &amp; hold to unpin."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"This keeps it in view until you unpin. Touch &amp; hold Overview to unpin."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"This keeps it in view until you unpin. Touch &amp; hold Home to unpin."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"To unpin this screen, touch &amp; hold Back and Overview buttons"</string>
@@ -912,8 +915,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"Open <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"Settings for <xliff:g id="APP_NAME">%1$s</xliff:g> bubbles"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"Allow bubbles from <xliff:g id="APP_NAME">%1$s</xliff:g>?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"Manage"</string>
<string name="no_bubbles" msgid="337101288173078247">"Deny"</string>
<string name="yes_bubbles" msgid="668809525728633841">"Allow"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"Ask me later"</string>
diff --git a/packages/SystemUI/res/values-en-rXC/strings.xml b/packages/SystemUI/res/values-en-rXC/strings.xml
index 1ca078534331..5cdb4aedaac8 100644
--- a/packages/SystemUI/res/values-en-rXC/strings.xml
+++ b/packages/SystemUI/res/values-en-rXC/strings.xml
@@ -448,6 +448,8 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"‎‏‎‎‎‎‎‏‎‏‏‏‎‎‎‎‎‎‏‎‎‏‎‎‎‎‏‏‏‏‏‏‎‏‎‏‎‏‏‎‎‎‏‎‎‎‏‏‏‏‎‎‎‏‎‏‎‏‏‎‏‎‎‎‏‎‎‏‎‎‎‎‏‏‏‎‏‏‏‎‎‏‏‏‏‎‎‎‎‎‎‎‎‎‎‎Don\'t show again‎‏‎‎‏‎"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"‎‏‎‎‎‎‎‏‎‏‏‏‎‎‎‎‎‎‏‎‎‏‎‎‎‎‏‏‏‏‏‎‎‏‎‏‏‎‏‎‎‏‏‎‎‏‎‎‏‏‎‎‎‎‎‎‏‏‏‏‎‏‎‎‏‎‏‎‏‎‏‏‏‏‎‏‎‎‎‎‏‎‎‎‎‏‎‏‎‏‏‎‎‎Clear all‎‏‎‎‏‎"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"‎‏‎‎‎‎‎‏‎‏‏‏‎‎‎‎‎‎‏‎‎‏‎‎‎‎‏‏‏‏‏‏‎‏‎‎‎‎‏‎‎‎‏‏‏‏‏‎‏‎‏‏‏‎‎‏‎‎‏‏‎‏‎‎‏‎‏‎‏‏‎‎‏‏‏‏‎‎‎‎‏‏‏‏‏‏‏‏‎‎‏‎‎‎‏‎Manage‎‏‎‎‏‎"</string>
+ <string name="notification_section_header_gentle" msgid="8356064473678167305">"‎‏‎‎‎‎‎‏‎‏‏‏‎‎‎‎‎‎‏‎‎‏‎‎‎‎‏‏‏‏‏‏‏‏‏‏‎‎‏‏‏‏‏‏‎‏‏‎‏‎‏‏‎‏‎‎‎‏‎‏‏‏‎‏‏‏‎‏‎‎‎‏‏‏‎‏‏‎‎‏‎‎‏‏‏‏‎‏‎‎‎‎‏‎‎‏‎Gentle notifications‎‏‎‎‏‎"</string>
+ <string name="accessibility_notification_section_header_gentle_clear_all" msgid="4270384919249494640">"‎‏‎‎‎‎‎‏‎‏‏‏‎‎‎‎‎‎‏‎‎‏‎‎‎‎‏‏‏‏‏‏‎‏‏‏‎‏‏‎‏‎‎‎‎‏‏‎‏‏‏‎‏‎‎‎‏‏‏‎‏‎‏‎‏‏‎‎‏‏‎‎‎‎‎‏‏‎‏‎‎‏‎‎‎‏‎‎‏‏‏‎‎‎‎‎Clear all gentle notifications‎‏‎‎‏‎"</string>
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"‎‏‎‎‎‎‎‏‎‏‏‏‎‎‎‎‎‎‏‎‎‏‎‎‎‎‏‏‏‏‏‎‏‏‏‎‏‎‎‏‏‎‏‏‏‎‎‏‏‎‏‎‎‎‏‎‏‏‏‏‎‎‏‏‏‎‎‎‎‎‎‎‎‏‎‎‏‎‏‏‎‏‎‏‎‎‏‎‎‏‎‏‎‏‎Notifications paused by Do Not Disturb‎‏‎‎‏‎"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"‎‏‎‎‎‎‎‏‎‏‏‏‎‎‎‎‎‎‏‎‎‏‎‎‎‎‏‏‏‏‏‏‏‏‏‏‎‏‎‏‏‎‎‎‏‏‏‎‏‎‎‏‎‏‏‎‎‎‎‏‎‏‎‏‏‏‎‎‏‎‏‎‎‎‎‎‎‎‎‎‎‏‏‎‏‎‎‏‏‎‏‎‎‎‏‎‎Start now‎‏‎‎‏‎"</string>
<string name="empty_shade_text" msgid="708135716272867002">"‎‏‎‎‎‎‎‏‎‏‏‏‎‎‎‎‎‎‏‎‎‏‎‎‎‎‏‏‏‏‏‎‎‏‎‎‏‏‏‎‏‎‎‏‏‏‏‎‎‏‏‎‏‏‎‏‎‏‏‏‎‏‎‎‏‏‏‎‏‎‎‏‏‎‏‏‎‎‎‎‎‎‏‏‎‏‎‏‏‏‎‏‎‎No notifications‎‏‎‎‏‎"</string>
diff --git a/packages/SystemUI/res/values-es-rUS/strings.xml b/packages/SystemUI/res/values-es-rUS/strings.xml
index b265d2ba89ff..91d3ed45117e 100644
--- a/packages/SystemUI/res/values-es-rUS/strings.xml
+++ b/packages/SystemUI/res/values-es-rUS/strings.xml
@@ -448,6 +448,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"No volver a mostrar"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"Borrar todo"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"Administrar"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"Notificaciones pausadas por el modo \"No interrumpir\""</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"Comenzar ahora"</string>
<string name="empty_shade_text" msgid="708135716272867002">"No hay notificaciones"</string>
@@ -527,8 +531,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"Pantalla fija"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"Esta función mantiene la pantalla visible hasta que dejes de fijarla. Para ello, mantén presionados los botones Atrás y Recientes."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"Esta función mantiene la pantalla visible hasta que dejes de fijarla. Para ello, mantén presionados los botones de inicio y Atrás."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"Esta función mantiene la pantalla visible hasta que dejes de fijarla. Desliza el dedo hacia arriba y mantén presionado para dejar de fijarla."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"Esta función mantiene la pantalla visible hasta que dejes de fijarla. Para ello, mantén presionado el botón Recientes."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"Esta función mantiene la pantalla visible hasta que dejes de fijarla. Para ello, mantén presionado el botón de inicio."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"Para dejar de fijar esta pantalla, mantén presionados los botones Atrás y Recientes"</string>
@@ -912,8 +915,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"Abrir <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"Configuración para cuadros de <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"¿Quieres permitir cuadros de <xliff:g id="APP_NAME">%1$s</xliff:g>?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"Administrar"</string>
<string name="no_bubbles" msgid="337101288173078247">"Denegar"</string>
<string name="yes_bubbles" msgid="668809525728633841">"Permitir"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"Preguntarme más tarde"</string>
diff --git a/packages/SystemUI/res/values-es/strings.xml b/packages/SystemUI/res/values-es/strings.xml
index 67b4681e15f8..cae53bd1723d 100644
--- a/packages/SystemUI/res/values-es/strings.xml
+++ b/packages/SystemUI/res/values-es/strings.xml
@@ -367,7 +367,7 @@
<string name="quick_settings_night_secondary_label_on_at_sunset" msgid="8483259341596943314">"Al atardecer"</string>
<string name="quick_settings_night_secondary_label_until_sunrise" msgid="4453017157391574402">"Hasta el amanecer"</string>
<string name="quick_settings_night_secondary_label_on_at" msgid="6256314040368487637">"Hora: <xliff:g id="TIME">%s</xliff:g>"</string>
- <string name="quick_settings_secondary_label_until" msgid="2749196569462600150">"Hasta: <xliff:g id="TIME">%s</xliff:g>"</string>
+ <string name="quick_settings_secondary_label_until" msgid="2749196569462600150">"Hasta las <xliff:g id="TIME">%s</xliff:g>"</string>
<string name="quick_settings_ui_mode_night_label" msgid="512534812963862137">"Tema oscuro"</string>
<string name="quick_settings_nfc_label" msgid="9012153754816969325">"NFC"</string>
<string name="quick_settings_nfc_off" msgid="6883274004315134333">"La conexión NFC está inhabilitada"</string>
@@ -448,6 +448,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"No volver a mostrar"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"Borrar todo"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"Gestionar"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"Notificaciones pausadas por el modo No molestar"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"Iniciar ahora"</string>
<string name="empty_shade_text" msgid="708135716272867002">"No hay notificaciones"</string>
@@ -527,8 +531,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"Pantalla fijada"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"La pantalla se mantiene visible hasta que dejas de fijarla. Para ello, mantén pulsados los botones Atrás y Aplicaciones recientes."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"La pantalla se mantiene visible hasta que dejas de fijarla. Para ello, mantén pulsados los botones Atrás e Inicio."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"Se mantiene visible hasta que dejas de fijarla. Para ello, desliza el dedo hacia arriba y mantén pulsado."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"La pantalla se mantiene visible hasta que dejas de fijarla. Para ello, mantén pulsado el botón Aplicaciones recientes."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"La pantalla se mantiene visible hasta que dejas de fijarla. Para ello, mantén pulsado el botón Inicio."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"Mantén pulsado el botón Atrás y el de aplicaciones recientes para dejar de fijar esta pantalla"</string>
@@ -767,7 +770,7 @@
<string name="left_icon" msgid="3096287125959387541">"Icono a la izquierda"</string>
<string name="right_icon" msgid="3952104823293824311">"Icono a la derecha"</string>
<string name="drag_to_add_tiles" msgid="230586591689084925">"Pulsa y arrastra para añadir funciones"</string>
- <string name="drag_to_rearrange_tiles" msgid="4566074720193667473">"Mantén pulsado un icono y arrástralo para reorganizarlo"</string>
+ <string name="drag_to_rearrange_tiles" msgid="4566074720193667473">"Mantén pulsado un icono y arrástralo para reubicarlo"</string>
<string name="drag_to_remove_tiles" msgid="3361212377437088062">"Arrastra aquí para quitar una función"</string>
<string name="drag_to_remove_disabled" msgid="2390968976638993382">"Necesitas al menos 6 iconos"</string>
<string name="qs_edit" msgid="2232596095725105230">"Editar"</string>
@@ -881,7 +884,7 @@
<string name="running_foreground_services_title" msgid="381024150898615683">"Aplicaciones que se están ejecutando en segundo plano"</string>
<string name="running_foreground_services_msg" msgid="6326247670075574355">"Toca para ver información detallada sobre el uso de datos y de la batería"</string>
<string name="mobile_data_disable_title" msgid="1068272097382942231">"¿Quieres desactivar los datos móviles?"</string>
- <string name="mobile_data_disable_message" msgid="4756541658791493506">"No tienes conexión a Internet ni de datos móviles a través de <xliff:g id="CARRIER">%s</xliff:g>. Solo puedes conectarte a Internet mediante una red Wi‑Fi."</string>
+ <string name="mobile_data_disable_message" msgid="4756541658791493506">"No tendrás conexión a Internet ni de datos móviles a través de <xliff:g id="CARRIER">%s</xliff:g>. Solo podrás conectarte a Internet mediante una red Wi‑Fi."</string>
<string name="mobile_data_disable_message_default_carrier" msgid="6078110473451946831">"tu operador"</string>
<string name="touch_filtered_warning" msgid="8671693809204767551">"Una aplicación impide ver una solicitud de permiso, por lo que Ajustes no puede verificar tu respuesta."</string>
<string name="slice_permission_title" msgid="7465009437851044444">"¿Quieres permitir que <xliff:g id="APP_0">%1$s</xliff:g> muestre fragmentos de <xliff:g id="APP_2">%2$s</xliff:g>?"</string>
@@ -912,8 +915,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"Abrir <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"Ajustes de las burbujas de <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"¿Quieres permitir las burbujas de <xliff:g id="APP_NAME">%1$s</xliff:g>?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"Gestionar"</string>
<string name="no_bubbles" msgid="337101288173078247">"Denegar"</string>
<string name="yes_bubbles" msgid="668809525728633841">"Permitir"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"Preguntarme más tarde"</string>
diff --git a/packages/SystemUI/res/values-et/strings.xml b/packages/SystemUI/res/values-et/strings.xml
index 4ee9a07cc78e..7c68cce3c516 100644
--- a/packages/SystemUI/res/values-et/strings.xml
+++ b/packages/SystemUI/res/values-et/strings.xml
@@ -448,6 +448,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"Ära kuva uuesti"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"Tühjenda kõik"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"Haldamine"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"Režiim Mitte segada peatas märguanded"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"Alusta kohe"</string>
<string name="empty_shade_text" msgid="708135716272867002">"Märguandeid pole"</string>
@@ -527,8 +531,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"Ekraan on kinnitatud"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"See hoitakse kuval, kuni selle vabastate. Vabastamiseks puudutage pikalt nuppe Tagasi ja Ülevaade."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"See hoitakse kuval, kuni selle vabastate. Vabastamiseks puudutage pikalt nuppe Tagasi ja Avakuva."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"See hoitakse kuval, kuni selle vabastate. Vabastamiseks pühkige üles ja hoidke sõrme ekraanil."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"See hoitakse kuval, kuni selle vabastate. Vabastamiseks puudutage pikalt nuppu Ülevaade."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"See hoitakse kuval, kuni selle vabastate. Vabastamiseks puudutage pikalt nuppu Avakuva."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"Ekraanikuva vabastamiseks puudutage pikalt nuppe Tagasi ja Ülevaade"</string>
@@ -912,8 +915,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"Ava <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"Rakenduse <xliff:g id="APP_NAME">%1$s</xliff:g> mullide seaded"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"Kas soovite rakenduse <xliff:g id="APP_NAME">%1$s</xliff:g> mullid lubada?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"Halda"</string>
<string name="no_bubbles" msgid="337101288173078247">"Keela"</string>
<string name="yes_bubbles" msgid="668809525728633841">"Luba"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"Küsi hiljem"</string>
diff --git a/packages/SystemUI/res/values-eu/strings.xml b/packages/SystemUI/res/values-eu/strings.xml
index f1df83906eb3..1dac8adf80d9 100644
--- a/packages/SystemUI/res/values-eu/strings.xml
+++ b/packages/SystemUI/res/values-eu/strings.xml
@@ -448,6 +448,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"Ez erakutsi berriro"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"Garbitu guztiak"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"Kudeatu"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"\"Ez molestatu\" moduak pausatu egin ditu jakinarazpenak"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"Hasi"</string>
<string name="empty_shade_text" msgid="708135716272867002">"Ez dago jakinarazpenik"</string>
@@ -527,8 +531,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"Pantaila ainguratuta dago"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"Horrela, ikusgai egongo da aingura kendu arte. Aingura kentzeko, eduki sakatuta \"Atzera\" eta \"Ikuspegi orokorra\" botoiak."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"Horrela, ikusgai egongo da aingura kendu arte. Aingura kentzeko, eduki sakatuta Atzera eta Hasiera botoiak."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"Horrela, ikusgai egongo da aingura kendu arte. Aingura kentzeko, eduki sakatuta Hasiera botoia."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"Horrela, ikusgai egongo da aingura kendu arte. Aingura kentzeko, eduki sakatuta \"Ikuspegi orokorra\" botoia."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"Horrela, ikusgai egongo da aingura kendu arte. Aingura kentzeko, eduki sakatuta Hasiera botoia."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"Pantailari aingura kentzeko, eduki sakatuta Atzera eta Ikuspegi orokorra botoiak"</string>
@@ -639,8 +642,8 @@
<string name="inline_turn_off_notifications" msgid="8635596135532202355">"Desaktibatu jakinarazpenak"</string>
<string name="inline_keep_showing_app" msgid="1723113469580031041">"Aplikazio honen jakinarazpenak erakusten jarraitzea nahi duzu?"</string>
<string name="notification_silence_title" msgid="7352089096356977930">"Jakinarazi soinurik gabe"</string>
- <string name="notification_alert_title" msgid="3966526305405016221">"Lehentasunezkoa"</string>
- <string name="notification_channel_summary_low" msgid="1065819618107531284">"Pantailaren goialdeko barra lerrakorrean bakarrik erakusten ditu jakinarazpenak, arretarik gal ez dezazun. Beti isilik."</string>
+ <string name="notification_alert_title" msgid="3966526305405016221">"Lehentasunezkoak"</string>
+ <string name="notification_channel_summary_low" msgid="1065819618107531284">"Pantailaren goialdeko goitibeherako barran bakarrik erakusten ditu jakinarazpenak, arretarik gal ez dezazun. Beti isilik."</string>
<string name="notification_channel_summary_low_status" msgid="2702170424808743755">"Lehentasunik ez duten jakinarazpenak erakusten ditu. Beti isilik."</string>
<string name="notification_channel_summary_low_lock" msgid="7966605244472624458">"Lehentasunik ez duten jakinarazpenak erakusten ditu. Beti isilik."</string>
<string name="notification_channel_summary_low_status_lock" msgid="7012562768950012739">"Lehentasunik ez duten jakinarazpenak erakusten ditu. Beti isilik."</string>
@@ -766,8 +769,8 @@
<string name="right_keycode" msgid="708447961000848163">"Eskuineko teklaren kodea"</string>
<string name="left_icon" msgid="3096287125959387541">"Ezkerreko ikonoa"</string>
<string name="right_icon" msgid="3952104823293824311">"Eskuineko ikonoa"</string>
- <string name="drag_to_add_tiles" msgid="230586591689084925">"Eduki sakatuta eta arrastatu lauzak gehitzeko"</string>
- <string name="drag_to_rearrange_tiles" msgid="4566074720193667473">"Eduki sakatuta eta arrastatu, lauzak berrantolatzeko"</string>
+ <string name="drag_to_add_tiles" msgid="230586591689084925">"Lauzak gehitzeko, eduki sakatuta eta arrastatu"</string>
+ <string name="drag_to_rearrange_tiles" msgid="4566074720193667473">"Lauzak antolatzeko, eduki sakatuta eta arrastatu"</string>
<string name="drag_to_remove_tiles" msgid="3361212377437088062">"Kentzeko, arrastatu hona"</string>
<string name="drag_to_remove_disabled" msgid="2390968976638993382">"Gutxienez sei lauza behar dituzu"</string>
<string name="qs_edit" msgid="2232596095725105230">"Editatu"</string>
@@ -881,7 +884,7 @@
<string name="running_foreground_services_title" msgid="381024150898615683">"Aplikazioak exekutatzen ari dira atzeko planoan"</string>
<string name="running_foreground_services_msg" msgid="6326247670075574355">"Sakatu bateria eta datuen erabilerari buruzko xehetasunak ikusteko"</string>
<string name="mobile_data_disable_title" msgid="1068272097382942231">"Datu-konexioa desaktibatu nahi duzu?"</string>
- <string name="mobile_data_disable_message" msgid="4756541658791493506">"<xliff:g id="CARRIER">%s</xliff:g> erabilita ezingo dituzu erabili datuak edo Internet. Wi-Fi sare baten bidez soilik konektatu ahal izango zara Internetera."</string>
+ <string name="mobile_data_disable_message" msgid="4756541658791493506">"<xliff:g id="CARRIER">%s</xliff:g> erabilita ezingo dituzu erabili datuak edo Internet. Wifi-sare baten bidez soilik konektatu ahal izango zara Internetera."</string>
<string name="mobile_data_disable_message_default_carrier" msgid="6078110473451946831">"Uneko operadorea"</string>
<string name="touch_filtered_warning" msgid="8671693809204767551">"Aplikazio bat baimen-eskaera oztopatzen ari denez, ezarpenek ezin dute egiaztatu erantzuna."</string>
<string name="slice_permission_title" msgid="7465009437851044444">"<xliff:g id="APP_0">%1$s</xliff:g> aplikazioari <xliff:g id="APP_2">%2$s</xliff:g> aplikazioaren zatiak erakusteko baimena eman nahi diozu?"</string>
@@ -912,8 +915,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"Ireki <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"<xliff:g id="APP_NAME">%1$s</xliff:g> aplikazioaren ezarpenen burbuilak"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"<xliff:g id="APP_NAME">%1$s</xliff:g> aplikazioaren burbuilak erabiltzeko baimena eman nahi duzu?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"Kudeatu"</string>
<string name="no_bubbles" msgid="337101288173078247">"Ukatu"</string>
<string name="yes_bubbles" msgid="668809525728633841">"Onartu"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"Galdetu geroago"</string>
diff --git a/packages/SystemUI/res/values-fa/strings.xml b/packages/SystemUI/res/values-fa/strings.xml
index 1aba77a2f3c2..a98054fab063 100644
--- a/packages/SystemUI/res/values-fa/strings.xml
+++ b/packages/SystemUI/res/values-fa/strings.xml
@@ -208,10 +208,10 @@
<string name="accessibility_notification_dismissed" msgid="854211387186306927">"اعلان ردشد."</string>
<string name="accessibility_desc_notification_shade" msgid="4690274844447504208">"مجموعه اعلان."</string>
<string name="accessibility_desc_quick_settings" msgid="6186378411582437046">"تنظیمات سریع."</string>
- <string name="accessibility_desc_lock_screen" msgid="5625143713611759164">"قفل صفحه."</string>
+ <string name="accessibility_desc_lock_screen" msgid="5625143713611759164">"صفحه قفل."</string>
<string name="accessibility_desc_settings" msgid="3417884241751434521">"تنظیمات"</string>
<string name="accessibility_desc_recent_apps" msgid="4876900986661819788">"نمای کلی."</string>
- <string name="accessibility_desc_work_lock" msgid="4288774420752813383">"صفحه حالت قفل نمایه کاری"</string>
+ <string name="accessibility_desc_work_lock" msgid="4288774420752813383">"صفحه قفل کاری"</string>
<string name="accessibility_desc_close" msgid="7479755364962766729">"بستن"</string>
<string name="accessibility_quick_settings_wifi" msgid="5518210213118181692">"<xliff:g id="SIGNAL">%1$s</xliff:g>."</string>
<string name="accessibility_quick_settings_wifi_changed_off" msgid="8716484460897819400">"‏Wi-Fi خاموش شد."</string>
@@ -448,6 +448,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"دوباره نشان داده نشود"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"پاک کردن همه موارد"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"مدیریت"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"اعلان‌ها توسط «مزاحم نشوید» موقتاً متوقف شدند"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"اکنون شروع شود"</string>
<string name="empty_shade_text" msgid="708135716272867002">"اعلانی موجود نیست"</string>
@@ -527,8 +531,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"صفحه نمایش پین شد"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"تا زمانی که پین را بردارید، در نما نگه‌داشته می‌شود. برای برداشتن پین، «برگشت» و «نمای کلی» را لمس کنید و نگه‌دارید."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"تا برداشتن پین، در نما نگه‌داشته می‌شود. برای برداشتن پین، «برگشت» و «صفحه اصلی» را لمس کنید و نگه‌دارید."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"تا برداشتن پین، در نما نگه‌داشته می‌شود. برای برداشتن پین، از پایین صفحه تند به‌طرف بالا بکشید و نگه‌دارید."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"تا زمانی که پین را بردارید، در نما نگه‌داشته می‌شود. برای برداشتن پین، «نمای کلی» را لمس کنید و نگه‌دارید."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"تا برداشتن پین، در نما نگه‌داشته می‌شود. برای برداشتن پین، «صفحه اصلی» را لمس کنید و نگه‌دارید."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"برای برداشتن پین این صفحه، دکمه‌های «برگشت» و «نمای کلی» را لمس کنید و نگه‌دارید"</string>
@@ -617,7 +620,7 @@
<string name="tuner_full_importance_settings" msgid="3207312268609236827">"کنترل‌های قدرتمند اعلان"</string>
<string name="tuner_full_importance_settings_on" msgid="7545060756610299966">"روشن"</string>
<string name="tuner_full_importance_settings_off" msgid="8208165412614935229">"خاموش"</string>
- <string name="power_notification_controls_description" msgid="4372459941671353358">"با کنترل‌های قدرتمند اعلان می‌توانید سطح اهمیت اعلان‌های هر برنامه را از ۰ تا ۵ تعیین کنید. \n\n"<b>"سطح ۵"</b>" \n- در صدر فهرست اعلان‌ها نشان داده می‌شود \n- وقفه برای نمایش تمام‌صفحه مجاز است \n- همیشه اجمالی نشان داده می‌شود \n\n"<b>"سطح ۴"</b>" \n- وقفه برای نمایش تمام‌صفحه مجاز نیست \n- همیشه اجمالی نشان داده می‌شود \n\n"<b>"سطح ۳"</b>" \n- وقفه برای نمایش تمام‌صفحه مجاز نیست \n- هیچ‌وقت اجمالی نشان داده نمی‌شود \n\n"<b>"سطح ۲"</b>" \n- وقفه برای نمایش تمام‌صفحه مجاز نیست \n- هیچ‌وقت اجمالی نشان داده نمی‌شود \n- هیچ‌وقت صدا و لرزش ایجاد نمی‌کند \n\n"<b>"سطح ۱"</b>" \n- نمایش تمام صفحه مجاز نیست \n- هیچ‌وقت اجمالی نشان داده نمی‌شود \n- هیچ‌وقت صدا یا لرزش ایجاد نمی‌کند \n- در قفل صفحه و نوار وضعیت پنهان است \n- در پایین فهرست اعلان‌ها نشان داده می‌شود \n\n"<b>"سطح ۰"</b>" \n- همه اعلان‌های این برنامه مسدود است"</string>
+ <string name="power_notification_controls_description" msgid="4372459941671353358">"با کنترل‌های قدرتمند اعلان می‌توانید سطح اهمیت اعلان‌های هر برنامه را از ۰ تا ۵ تعیین کنید. \n\n"<b>"سطح ۵"</b>" \n- در صدر فهرست اعلان‌ها نشان داده می‌شود \n- وقفه برای نمایش تمام‌صفحه مجاز است \n- همیشه اجمالی نشان داده می‌شود \n\n"<b>"سطح ۴"</b>" \n- وقفه برای نمایش تمام‌صفحه مجاز نیست \n- همیشه اجمالی نشان داده می‌شود \n\n"<b>"سطح ۳"</b>" \n- وقفه برای نمایش تمام‌صفحه مجاز نیست \n- هیچ‌وقت اجمالی نشان داده نمی‌شود \n\n"<b>"سطح ۲"</b>" \n- وقفه برای نمایش تمام‌صفحه مجاز نیست \n- هیچ‌وقت اجمالی نشان داده نمی‌شود \n- هیچ‌وقت صدا و لرزش ایجاد نمی‌کند \n\n"<b>"سطح ۱"</b>" \n- نمایش تمام صفحه مجاز نیست \n- هیچ‌وقت اجمالی نشان داده نمی‌شود \n- هیچ‌وقت صدا یا لرزش ایجاد نمی‌کند \n- در صفحه قفل و نوار وضعیت پنهان است \n- در پایین فهرست اعلان‌ها نشان داده می‌شود \n\n"<b>"سطح ۰"</b>" \n- همه اعلان‌های این برنامه مسدود است"</string>
<string name="notification_header_default_channel" msgid="7506845022070889909">"اعلان‌ها"</string>
<string name="notification_channel_disabled" msgid="344536703863700565">"دیگر این اعلان‌ها را نخواهید دید"</string>
<string name="notification_channel_minimized" msgid="1664411570378910931">"این اعلان‌ها کوچک خواهد شد"</string>
@@ -818,7 +821,7 @@
<string name="accessibility_quick_settings_open_settings" msgid="7806613775728380737">"باز کردن تنظیمات <xliff:g id="ID_1">%s</xliff:g>."</string>
<string name="accessibility_quick_settings_edit" msgid="7839992848995240393">"ویرایش ترتیب تنظیمات."</string>
<string name="accessibility_quick_settings_page" msgid="5032979051755200721">"صفحه <xliff:g id="ID_1">%1$d</xliff:g> از <xliff:g id="ID_2">%2$d</xliff:g>"</string>
- <string name="tuner_lock_screen" msgid="5755818559638850294">"قفل صفحه"</string>
+ <string name="tuner_lock_screen" msgid="5755818559638850294">"صفحه قفل"</string>
<string name="pip_phone_expand" msgid="5889780005575693909">"بزرگ کردن"</string>
<string name="pip_phone_minimize" msgid="1079119422589131792">"کوچک کردن"</string>
<string name="pip_phone_close" msgid="8416647892889710330">"بستن"</string>
@@ -912,8 +915,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"باز کردن <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"تنظیم برای ابزارک‌های اعلان <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"برای <xliff:g id="APP_NAME">%1$s</xliff:g>، ابزارک‌های اعلان مجاز شوند؟"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"مدیریت"</string>
<string name="no_bubbles" msgid="337101288173078247">"رد کردن"</string>
<string name="yes_bubbles" msgid="668809525728633841">"اجازه دادن"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"بعداً پرسیده شود"</string>
diff --git a/packages/SystemUI/res/values-fi/strings.xml b/packages/SystemUI/res/values-fi/strings.xml
index 70d78380cf5a..84f05b75c2d5 100644
--- a/packages/SystemUI/res/values-fi/strings.xml
+++ b/packages/SystemUI/res/values-fi/strings.xml
@@ -448,6 +448,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"Älä näytä uudelleen"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"Poista kaikki"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"Muuta asetuksia"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"Älä häiritse ‑tila keskeytti ilmoitukset"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"Aloita nyt"</string>
<string name="empty_shade_text" msgid="708135716272867002">"Ei ilmoituksia"</string>
@@ -527,8 +531,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"Näyttö on kiinnitetty"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"Pysyy näkyvissä, kunnes irrotat sen. Irrota painamalla pitkään Edellinen ja Viimeisimmät."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"Pysyy näkyvissä, kunnes irrotat sen. Irrota painamalla pitkään Edellinen ja Aloitusnäyttö."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"Pysyy näkyvissä, kunnes irrotat sen. Irrota pyyhkäisemällä ylös ja painamalla pitkään."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"Pysyy näkyvissä, kunnes irrotat sen. Irrota painamalla pitkään Viimeisimmät."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"Pysyy näkyvissä, kunnes irrotat sen. Irrota painamalla pitkään Aloitusnäyttö."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"Irrota näyttö koskettamalla pitkään Takaisin- ja Viimeisimmät-painikkeita"</string>
@@ -912,8 +915,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"Avaa <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"Kuplien asetukset: <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"Sallitaanko kuplat (<xliff:g id="APP_NAME">%1$s</xliff:g>)?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"Ylläpidä"</string>
<string name="no_bubbles" msgid="337101288173078247">"Estä"</string>
<string name="yes_bubbles" msgid="668809525728633841">"Salli"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"Kysy myöhemmin"</string>
diff --git a/packages/SystemUI/res/values-fr-rCA/strings.xml b/packages/SystemUI/res/values-fr-rCA/strings.xml
index 3689f0019f21..245ee403d24f 100644
--- a/packages/SystemUI/res/values-fr-rCA/strings.xml
+++ b/packages/SystemUI/res/values-fr-rCA/strings.xml
@@ -448,6 +448,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"Ne plus afficher"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"Tout effacer"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"Gérer"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"Les notifications sont suspendues par le mode Ne pas déranger"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"Commencer"</string>
<string name="empty_shade_text" msgid="708135716272867002">"Aucune notification"</string>
@@ -527,8 +531,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"L\'écran est épinglé"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"Cet écran est épinglé jusqu\'à ce que vous annuliez l\'opération. Pour annuler l\'épinglage, maintenez le doigt sur « Retour » et « Aperçu »."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"Cet écran est épinglé jusqu\'à ce que vous annuliez l\'opération. Pour annuler l\'épinglage, maintenez le doigt sur les touches Retour et Accueil."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"Cet écran est épinglé jusqu\'à ce que vous annuliez l\'épinglage. Pour annuler l\'épinglage, balayez l\'écran vers le haut et gardez le doigt dessus."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"Cet écran est épinglé jusqu\'à ce que vous annuliez l\'opération. Pour annuler l\'épinglage, maintenez le doigt sur « Aperçu »."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"Cet écran est épinglé jusqu\'à ce que vous annuliez l\'opération. Pour annuler l\'épinglage, maintenez le doigt sur la touche Accueil."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"Pour annuler l\'épinglage de cet écran, maintenez le doigt sur les touches Retour et Aperçu."</string>
@@ -912,8 +915,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"Ouvrir <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"Paramètres pour les bulles de l\'application <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"Autoriser les bulles de l\'application <xliff:g id="APP_NAME">%1$s</xliff:g>?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"Gérer"</string>
<string name="no_bubbles" msgid="337101288173078247">"Refuser"</string>
<string name="yes_bubbles" msgid="668809525728633841">"Autoriser"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"Me demander plus tard"</string>
diff --git a/packages/SystemUI/res/values-fr/strings.xml b/packages/SystemUI/res/values-fr/strings.xml
index 80ffe9153bdf..6ccc27b08500 100644
--- a/packages/SystemUI/res/values-fr/strings.xml
+++ b/packages/SystemUI/res/values-fr/strings.xml
@@ -67,7 +67,7 @@
<string name="usb_disable_contaminant_detection" msgid="2103905315747120033">"Activer le port USB"</string>
<string name="compat_mode_on" msgid="6623839244840638213">"Zoomer pour remplir l\'écran"</string>
<string name="compat_mode_off" msgid="4434467572461327898">"Étirer pour remplir l\'écran"</string>
- <string name="global_action_screenshot" msgid="8329831278085426283">"Capture d\'écran"</string>
+ <string name="global_action_screenshot" msgid="8329831278085426283">"Capture"</string>
<string name="screenshot_saving_ticker" msgid="7403652894056693515">"Enregistrement capture écran…"</string>
<string name="screenshot_saving_title" msgid="8242282144535555697">"Enregistrement de la capture d\'écran…"</string>
<string name="screenshot_saved_title" msgid="5637073968117370753">"Capture d\'écran enregistrée"</string>
@@ -366,7 +366,7 @@
<string name="quick_settings_night_display_label" msgid="3577098011487644395">"Éclairage nocturne"</string>
<string name="quick_settings_night_secondary_label_on_at_sunset" msgid="8483259341596943314">"Activé la nuit"</string>
<string name="quick_settings_night_secondary_label_until_sunrise" msgid="4453017157391574402">"Jusqu\'à l\'aube"</string>
- <string name="quick_settings_night_secondary_label_on_at" msgid="6256314040368487637">"Activé à <xliff:g id="TIME">%s</xliff:g>"</string>
+ <string name="quick_settings_night_secondary_label_on_at" msgid="6256314040368487637">"À partir de <xliff:g id="TIME">%s</xliff:g>"</string>
<string name="quick_settings_secondary_label_until" msgid="2749196569462600150">"Jusqu\'à <xliff:g id="TIME">%s</xliff:g>"</string>
<string name="quick_settings_ui_mode_night_label" msgid="512534812963862137">"Thème foncé"</string>
<string name="quick_settings_nfc_label" msgid="9012153754816969325">"NFC"</string>
@@ -448,6 +448,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"Ne plus afficher"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"Tout effacer"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"Gérer"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"Notifications suspendues par le mode Ne pas déranger"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"Commencer"</string>
<string name="empty_shade_text" msgid="708135716272867002">"Aucune notification"</string>
@@ -527,8 +531,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"Écran épinglé"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"Cet écran est épinglé jusqu\'à l\'annulation de l\'opération. Pour annuler l\'épinglage, appuyez de manière prolongée sur les boutons Retour et Aperçu."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"Cet écran est épinglé jusqu\'à l\'annulation de l\'opération. Pour annuler l\'épinglage, appuyez de manière prolongée sur les boutons \"Retour\" et \"Accueil\"."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"Cet écran est épinglé jusqu\'à l\'annulation de l\'opération. Pour annuler l\'épinglage, balayez l\'écran vers le haut et gardez le doigt dessus."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"Cet écran est épinglé jusqu\'à l\'annulation de l\'opération. Pour annuler l\'épinglage, appuyez de manière prolongée sur le bouton Aperçu."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"Cet écran est épinglé jusqu\'à l\'annulation de l\'opération. Pour annuler l\'épinglage, appuyez de manière prolongée sur le bouton \"Accueil\"."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"Pour annuler l\'épinglage de l\'écran, appuyez de manière prolongée sur les boutons \"Retour\" et \"Aperçu\""</string>
@@ -766,8 +769,8 @@
<string name="right_keycode" msgid="708447961000848163">"Code de touche droit"</string>
<string name="left_icon" msgid="3096287125959387541">"Icône gauche"</string>
<string name="right_icon" msgid="3952104823293824311">"Icône droite"</string>
- <string name="drag_to_add_tiles" msgid="230586591689084925">"Sélectionnez et faites glisser les tuiles pour les ajouter"</string>
- <string name="drag_to_rearrange_tiles" msgid="4566074720193667473">"Sélectionnez et faites glisser les tuiles pour réorganiser"</string>
+ <string name="drag_to_add_tiles" msgid="230586591689084925">"Sélectionnez et faites glisser les icônes pour les ajouter"</string>
+ <string name="drag_to_rearrange_tiles" msgid="4566074720193667473">"Sélectionnez et faites glisser les icônes pour réorganiser"</string>
<string name="drag_to_remove_tiles" msgid="3361212377437088062">"Faites glisser les tuiles ici pour les supprimer."</string>
<string name="drag_to_remove_disabled" msgid="2390968976638993382">"Au minimum six tuiles sont nécessaires"</string>
<string name="qs_edit" msgid="2232596095725105230">"Modifier"</string>
@@ -881,7 +884,7 @@
<string name="running_foreground_services_title" msgid="381024150898615683">"Applications en cours d\'exécution en arrière-plan"</string>
<string name="running_foreground_services_msg" msgid="6326247670075574355">"Appuyer pour obtenir des informations sur l\'utilisation de la batterie et des données"</string>
<string name="mobile_data_disable_title" msgid="1068272097382942231">"Désactiver les données mobiles ?"</string>
- <string name="mobile_data_disable_message" msgid="4756541658791493506">"Vous n\'accéderez pas aux données mobiles ni à Internet via <xliff:g id="CARRIER">%s</xliff:g>. Internet ne sera disponible qu\'avec une connexion Wi-Fi."</string>
+ <string name="mobile_data_disable_message" msgid="4756541658791493506">"Vous n\'aurez pas accès aux données mobiles ni à Internet via <xliff:g id="CARRIER">%s</xliff:g>. Vous ne pourrez accéder à Internet que par Wi-Fi."</string>
<string name="mobile_data_disable_message_default_carrier" msgid="6078110473451946831">"votre opérateur"</string>
<string name="touch_filtered_warning" msgid="8671693809204767551">"L\'application Paramètres ne peut pas valider votre réponse, car une application masque la demande d\'autorisation."</string>
<string name="slice_permission_title" msgid="7465009437851044444">"Autoriser <xliff:g id="APP_0">%1$s</xliff:g> à afficher des éléments de <xliff:g id="APP_2">%2$s</xliff:g> ?"</string>
@@ -912,8 +915,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"Ouvrir <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"Paramètres des bulles de <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"Autoriser les bulles pour <xliff:g id="APP_NAME">%1$s</xliff:g> ?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"Gérer"</string>
<string name="no_bubbles" msgid="337101288173078247">"Refuser"</string>
<string name="yes_bubbles" msgid="668809525728633841">"Autoriser"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"Me demander plus tard"</string>
diff --git a/packages/SystemUI/res/values-gl/strings.xml b/packages/SystemUI/res/values-gl/strings.xml
index 4fba3a8e5489..c9386980d923 100644
--- a/packages/SystemUI/res/values-gl/strings.xml
+++ b/packages/SystemUI/res/values-gl/strings.xml
@@ -82,7 +82,7 @@
<string name="screenrecord_mic_label" msgid="4522870600914810019">"Gravar voz en off"</string>
<string name="screenrecord_taps_label" msgid="1776467076607964790">"Mostrar toques"</string>
<string name="screenrecord_stop_label" msgid="2544887572381260038">"Deter"</string>
- <string name="screenrecord_pause_label" msgid="7162476078856786227">"Poñer en pausa"</string>
+ <string name="screenrecord_pause_label" msgid="7162476078856786227">"Pór en pausa"</string>
<string name="screenrecord_resume_label" msgid="3605818317015993314">"Retomar"</string>
<string name="screenrecord_cancel_label" msgid="3385204992871088609">"Cancelar"</string>
<string name="screenrecord_share_label" msgid="4197867360204019389">"Compartir"</string>
@@ -448,6 +448,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"Non mostrar outra vez"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"Eliminar todas"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"Xestionar"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"O modo Non molestar puxo en pausa as notificacións"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"Iniciar agora"</string>
<string name="empty_shade_text" msgid="708135716272867002">"Non hai notificacións"</string>
@@ -525,18 +529,17 @@
<string name="volume_odi_captions_hint_disable" msgid="8980842810619956593">"desactiva"</string>
<string name="accessibility_output_chooser" msgid="8185317493017988680">"Cambia ao dispositivo de saída"</string>
<string name="screen_pinning_title" msgid="3273740381976175811">"A pantalla está fixada"</string>
- <string name="screen_pinning_description" msgid="8909878447196419623">"A pantalla manterase visible ata que a soltes. Para facelo, mantén premido Atrás e Visión xeral."</string>
- <string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"A pantalla manterase visible ata que a soltes. Para facelo, mantén premido Atrás e Inicio."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
- <string name="screen_pinning_description_accessible" msgid="426190689254018656">"A pantalla manterase visible ata que a soltes. Para facelo, mantén premido Visión xeral."</string>
- <string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"A pantalla manterase visible ata que a soltes. Para facelo, mantén premido Inicio."</string>
- <string name="screen_pinning_toast" msgid="2266705122951934150">"Para soltar a pantalla, mantén premidos os botóns Volver e Visión xeral"</string>
- <string name="screen_pinning_toast_recents_invisible" msgid="8252402309499161281">"Para soltar a pantalla, mantén premidos os botóns Atrás e Inicio"</string>
+ <string name="screen_pinning_description" msgid="8909878447196419623">"A pantalla manterase visible ata que deixes de fixala. Para facelo, mantén premido Atrás e Visión xeral."</string>
+ <string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"A pantalla manterase visible ata que deixes de fixala. Para facelo, mantén premido Atrás e Inicio."</string>
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"A pantalla manterase visible ata que deixes de fixala. Para facelo, pasa o dedo cara arriba e manteno premido."</string>
+ <string name="screen_pinning_description_accessible" msgid="426190689254018656">"A pantalla manterase visible ata que deixes de fixala. Para facelo, mantén premido Visión xeral."</string>
+ <string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"A pantalla manterase visible ata que deixes de fixala. Para facelo, mantén premido Inicio."</string>
+ <string name="screen_pinning_toast" msgid="2266705122951934150">"Para deixar de fixar a pantalla, mantén premidos os botóns Volver e Visión xeral"</string>
+ <string name="screen_pinning_toast_recents_invisible" msgid="8252402309499161281">"Para deixar de fixar a pantalla, mantén premidos os botóns Atrás e Inicio"</string>
<string name="screen_pinning_positive" msgid="3783985798366751226">"De acordo"</string>
<string name="screen_pinning_negative" msgid="3741602308343880268">"Non, grazas"</string>
<string name="screen_pinning_start" msgid="1022122128489278317">"Fixouse a pantalla"</string>
- <string name="screen_pinning_exit" msgid="5187339744262325372">"Soltouse a pantalla"</string>
+ <string name="screen_pinning_exit" msgid="5187339744262325372">"Deixouse de fixar a pantalla"</string>
<string name="quick_settings_reset_confirmation_title" msgid="748792586749897883">"Queres ocultar <xliff:g id="TILE_LABEL">%1$s</xliff:g>?"</string>
<string name="quick_settings_reset_confirmation_message" msgid="2235970126803317374">"Volverá aparecer a próxima vez que se active na configuración."</string>
<string name="quick_settings_reset_confirmation_button" msgid="2660339101868367515">"Ocultar"</string>
@@ -640,7 +643,7 @@
<string name="inline_keep_showing_app" msgid="1723113469580031041">"Queres seguir mostrando as notificacións desta aplicación?"</string>
<string name="notification_silence_title" msgid="7352089096356977930">"Discretas"</string>
<string name="notification_alert_title" msgid="3966526305405016221">"Prioritarias"</string>
- <string name="notification_channel_summary_low" msgid="1065819618107531284">"Permíteche centrarte con notificacións só na lista despregable. Sempre en silencio."</string>
+ <string name="notification_channel_summary_low" msgid="1065819618107531284">"Permíteche centrarte con notificacións só no panel despregable. Sempre en silencio."</string>
<string name="notification_channel_summary_low_status" msgid="2702170424808743755">"Mostra as notificacións con prioridade baixa. Sempre en silencio."</string>
<string name="notification_channel_summary_low_lock" msgid="7966605244472624458">"Mostra as notificacións con prioridade baixa. Sempre en silencio."</string>
<string name="notification_channel_summary_low_status_lock" msgid="7012562768950012739">"Mostra as notificacións con prioridade baixa. Sempre en silencio."</string>
@@ -912,8 +915,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"Abre a aplicación <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"Configuración das burbullas de <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"Queres permitir que se mostren as burbullas de <xliff:g id="APP_NAME">%1$s</xliff:g>?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"Xestionar"</string>
<string name="no_bubbles" msgid="337101288173078247">"Denegar"</string>
<string name="yes_bubbles" msgid="668809525728633841">"Permitir"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"Preguntarme máis tarde"</string>
diff --git a/packages/SystemUI/res/values-gu/strings.xml b/packages/SystemUI/res/values-gu/strings.xml
index 05333fc4c8fe..3f36a3013d43 100644
--- a/packages/SystemUI/res/values-gu/strings.xml
+++ b/packages/SystemUI/res/values-gu/strings.xml
@@ -448,6 +448,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"ફરીથી બતાવશો નહીં"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"બધુ સાફ કરો"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"મેનેજ કરો"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"ખલેલ પાડશો નહીં દ્વારા થોભાવેલ નોટિફિકેશન"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"હવે પ્રારંભ કરો"</string>
<string name="empty_shade_text" msgid="708135716272867002">"કોઈ સૂચનાઓ નથી"</string>
@@ -527,8 +531,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"સ્ક્રીન પિન કરેલ છે"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"તમે જ્યાં સુધી અનપિન કરશો નહીં ત્યાં સુધી આ તેને દૃશ્યક્ષમ રાખે છે. અનપિન કરવા માટે પાછળ અને ઝલકને સ્પર્શ કરી રાખો."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"તમે જ્યાં સુધી અનપિન કરશો નહીં ત્યાં સુધી આ તેને દૃશ્યક્ષમ રાખે છે. અનપિન કરવા માટે પાછળ અને હોમને સ્પર્શ કરી રાખો."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"તમે જ્યાં સુધી અનપિન નહીં કરો ત્યાં સુધી આ તેને દૃશ્યક્ષમ રાખે છે. ઉપરની તરફ સ્વાઇપ કરો અને અનપિન કરવા માટે દબાવી રાખો."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"તમે જ્યાં સુધી અનપિન કરશો નહીં ત્યાં સુધી આ તેને દૃશ્યક્ષમ રાખે છે. અનપિન કરવા માટે ઝલકને સ્પર્શ કરી રાખો."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"તમે જ્યાં સુધી અનપિન કરશો નહીં ત્યાં સુધી આ તેને દૃશ્યક્ષમ રાખે છે. અનપિન કરવા માટે હોમને સ્પર્શ કરી રાખો."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"આ સ્ક્રીનને અનપિન કરવા માટે, પાછળ અને ઝલક બટનને સ્પર્શ કરી રાખો"</string>
@@ -912,8 +915,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"<xliff:g id="APP_NAME">%1$s</xliff:g> ખોલો"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"<xliff:g id="APP_NAME">%1$s</xliff:g> બબલ માટેનાં સેટિંગ"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"<xliff:g id="APP_NAME">%1$s</xliff:g> પરના બબલને મંજૂરી આપીએ?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"મેનેજ કરો"</string>
<string name="no_bubbles" msgid="337101288173078247">"નકારો"</string>
<string name="yes_bubbles" msgid="668809525728633841">"મંજૂરી આપો"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"મને થોડા સમય પછી પૂછશો"</string>
diff --git a/packages/SystemUI/res/values-hi/strings.xml b/packages/SystemUI/res/values-hi/strings.xml
index a3d361121f16..4dca269c5176 100644
--- a/packages/SystemUI/res/values-hi/strings.xml
+++ b/packages/SystemUI/res/values-hi/strings.xml
@@ -252,10 +252,10 @@
<string name="accessibility_quick_settings_hotspot_changed_off" msgid="5004708003447561394">"मोबाइल हॉटस्‍पॉट को बंद किया गया."</string>
<string name="accessibility_quick_settings_hotspot_changed_on" msgid="2890951609226476206">"मोबाइल हॉटस्‍पॉट को चालू किया गया."</string>
<string name="accessibility_casting_turned_off" msgid="1430668982271976172">"स्‍क्रीन कास्‍ट करना रुक गया."</string>
- <string name="accessibility_quick_settings_work_mode_off" msgid="7045417396436552890">"कार्य मोड बंद है."</string>
- <string name="accessibility_quick_settings_work_mode_on" msgid="7650588553988014341">"कार्य मोड चालू है."</string>
- <string name="accessibility_quick_settings_work_mode_changed_off" msgid="5605534876107300711">"कार्य मोड बंद कर दिया गया."</string>
- <string name="accessibility_quick_settings_work_mode_changed_on" msgid="249840330756998612">"कार्य मोड चालू किया गया."</string>
+ <string name="accessibility_quick_settings_work_mode_off" msgid="7045417396436552890">"वर्क मोड बंद है."</string>
+ <string name="accessibility_quick_settings_work_mode_on" msgid="7650588553988014341">"वर्क मोड चालू है."</string>
+ <string name="accessibility_quick_settings_work_mode_changed_off" msgid="5605534876107300711">"वर्क मोड बंद कर दिया गया."</string>
+ <string name="accessibility_quick_settings_work_mode_changed_on" msgid="249840330756998612">"वर्क मोड चालू किया गया."</string>
<string name="accessibility_quick_settings_data_saver_changed_off" msgid="650231949881093289">"डेटा बचाने की सेटिंग बंद कर दी गई है."</string>
<string name="accessibility_quick_settings_data_saver_changed_on" msgid="4218725402373934151">"डेटा बचाने की सेटिंग चालू कर दी गई है."</string>
<string name="accessibility_quick_settings_sensor_privacy_changed_off" msgid="5152819588955163090">"सेंसर निजता को बंद कर दिया गया है."</string>
@@ -362,7 +362,7 @@
<string name="quick_settings_cellular_detail_data_used" msgid="1476810587475761478">"<xliff:g id="DATA_USED">%s</xliff:g> उपयोग किया गया"</string>
<string name="quick_settings_cellular_detail_data_limit" msgid="56011158504994128">"<xliff:g id="DATA_LIMIT">%s</xliff:g> सीमा"</string>
<string name="quick_settings_cellular_detail_data_warning" msgid="2440098045692399009">"<xliff:g id="DATA_LIMIT">%s</xliff:g> चेतावनी"</string>
- <string name="quick_settings_work_mode_label" msgid="7608026833638817218">"कार्य प्रोफ़ाइल"</string>
+ <string name="quick_settings_work_mode_label" msgid="7608026833638817218">"वर्क प्रोफ़ाइल"</string>
<string name="quick_settings_night_display_label" msgid="3577098011487644395">"नाइट लाइट"</string>
<string name="quick_settings_night_secondary_label_on_at_sunset" msgid="8483259341596943314">"शाम को चालू की जाएगी"</string>
<string name="quick_settings_night_secondary_label_until_sunrise" msgid="4453017157391574402">"सुबह तक चालू रहेगी"</string>
@@ -448,6 +448,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"फिर से न दिखाएं"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"सभी को हटाएं"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"प्रबंधित करें"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"\'परेशान न करें\' सुविधा के ज़रिए कुछ समय के लिए सूचनाएं दिखाना रोक दिया गया है"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"अब शुरू करें"</string>
<string name="empty_shade_text" msgid="708135716272867002">"कोई सूचना नहीं मिली"</string>
@@ -462,11 +466,11 @@
<string name="quick_settings_disclosure_named_management" msgid="1059403025094542908">"डिवाइस का प्रबंधन <xliff:g id="ORGANIZATION_NAME">%1$s</xliff:g> करता है"</string>
<string name="quick_settings_disclosure_management_vpns" msgid="3698767349925266482">"डिवाइस का प्रबंधन आपका संगठन करता है और वह VPNs से कनेक्ट है"</string>
<string name="quick_settings_disclosure_named_management_vpns" msgid="7777821385318891527">"डिवाइस का प्रबंधन <xliff:g id="ORGANIZATION_NAME">%1$s</xliff:g> करता है और वह VPNs से कनेक्ट है"</string>
- <string name="quick_settings_disclosure_managed_profile_monitoring" msgid="5125463987558278215">"आपका संगठन आपकी कार्य प्रोफ़ाइल में नेटवर्क ट्रैफ़िक की निगरानी कर सकता है"</string>
- <string name="quick_settings_disclosure_named_managed_profile_monitoring" msgid="8973606847896650284">"<xliff:g id="ORGANIZATION_NAME">%1$s</xliff:g> आपकी कार्य प्रोफ़ाइल में नेटवर्क ट्रैफ़िक की निगरानी कर सकता है"</string>
+ <string name="quick_settings_disclosure_managed_profile_monitoring" msgid="5125463987558278215">"आपका संगठन आपकी वर्क प्रोफ़ाइल में नेटवर्क ट्रैफ़िक की निगरानी कर सकता है"</string>
+ <string name="quick_settings_disclosure_named_managed_profile_monitoring" msgid="8973606847896650284">"<xliff:g id="ORGANIZATION_NAME">%1$s</xliff:g> आपकी वर्क प्रोफ़ाइल में नेटवर्क ट्रैफ़िक की निगरानी कर सकता है"</string>
<string name="quick_settings_disclosure_monitoring" msgid="679658227269205728">"नेटवर्क की निगरानी की जा सकती है"</string>
<string name="quick_settings_disclosure_vpns" msgid="8170318392053156330">"डिवाइस VPNs से कनेक्ट है"</string>
- <string name="quick_settings_disclosure_managed_profile_named_vpn" msgid="3494535754792751741">"कार्य प्रोफ़ाइल <xliff:g id="VPN_APP">%1$s</xliff:g> से कनेक्ट है"</string>
+ <string name="quick_settings_disclosure_managed_profile_named_vpn" msgid="3494535754792751741">"वर्क प्रोफ़ाइल <xliff:g id="VPN_APP">%1$s</xliff:g> से कनेक्ट है"</string>
<string name="quick_settings_disclosure_personal_profile_named_vpn" msgid="4467456202486569906">"व्यक्तिगत प्रोफ़ाइल <xliff:g id="VPN_APP">%1$s</xliff:g> से कनेक्ट है"</string>
<string name="quick_settings_disclosure_named_vpn" msgid="6943724064780847080">"डिवाइस <xliff:g id="VPN_APP">%1$s</xliff:g> से कनेक्ट है"</string>
<string name="monitoring_title_device_owned" msgid="1652495295941959815">"डिवाइस प्रबंधन"</string>
@@ -481,12 +485,12 @@
<string name="monitoring_description_named_management" msgid="5281789135578986303">"<xliff:g id="ORGANIZATION_NAME">%1$s</xliff:g> आपके डिवाइस का प्रबंधन करता है.\n\nआपका एडमिन सेटिंग, कॉर्पोरेट पहुंच, ऐप्लिकेशन, आपके डिवाइस से जुड़े डेटा और आपके डिवाइस की जगह की जानकारी की निगरानी कर सकता है और उन्हें प्रबंधित कर सकता है.\n\n और जानकारी के लिए, अपने एडमिन से संपर्क करें."</string>
<string name="monitoring_description_management" msgid="4573721970278370790">"आपका संगठन आपके डिवाइस का प्रबंधन करता है.\n\nआपका एडमिन सेटिंग, कॉर्पोरेट पहुंच, ऐप्लिकेशन, आपके डिवाइस से जुड़े डेटा और आपके डिवाइस की जगह की जानकारी की निगरानी कर सकता है और उन्हें प्रबंधित कर सकता है.\n\nऔर जानकारी के लिए, अपने एडमिन से संपर्क करें."</string>
<string name="monitoring_description_management_ca_certificate" msgid="5202023784131001751">"आपके संगठन ने इस डिवाइस पर एक प्रमाणपत्र अनुमति इंस्टॉल की है. आपके सुरक्षित नेटवर्क पर ट्रेफ़िक की निगरानी या उसमें बदलाव किया जा सकता है."</string>
- <string name="monitoring_description_managed_profile_ca_certificate" msgid="4683248196789897964">"आपके संगठन ने आपकी कार्य प्रोफ़ाइल में एक प्रमाणपत्र अनुमति इंस्टॉल की है. आपके सुरक्षित नेटवर्क ट्रैफ़िक की निगरानी या उसमें बदलाव किया जा सकता है."</string>
+ <string name="monitoring_description_managed_profile_ca_certificate" msgid="4683248196789897964">"आपके संगठन ने आपकी वर्क प्रोफ़ाइल में एक प्रमाणपत्र अनुमति इंस्टॉल की है. आपके सुरक्षित नेटवर्क ट्रैफ़िक की निगरानी या उसमें बदलाव किया जा सकता है."</string>
<string name="monitoring_description_ca_certificate" msgid="7886985418413598352">"इस डिवाइस पर एक प्रमाणपत्र अनुमति इंस्टॉल की है. आपके सुरक्षित नेटवर्क ट्रैफ़िक की निगरानी या उसमें बदलाव किया जा सकता है."</string>
<string name="monitoring_description_management_network_logging" msgid="7184005419733060736">"आपके व्यवस्थापक ने नेटवर्क लॉगिंग चालू किया है, जो आपके डिवाइस पर ट्रैफ़िक की निगरानी करता है."</string>
<string name="monitoring_description_named_vpn" msgid="7403457334088909254">"आप <xliff:g id="VPN_APP">%1$s</xliff:g> से कनेक्‍ट हैं, जो ईमेल, ऐप्लिकेशन और वेबसाइटों सहित आपकी नेटवर्क गतिविधि की निगरानी कर सकते हैं."</string>
<string name="monitoring_description_two_named_vpns" msgid="4198511413729213802">"आप <xliff:g id="VPN_APP_0">%1$s</xliff:g> और <xliff:g id="VPN_APP_1">%2$s</xliff:g> से कनेक्ट हैं, जो ईमेल, ऐप्लिकेशन और वेबसाइटों सहित आपकी नेटवर्क गतिविधि की निगरानी कर सकते हैं."</string>
- <string name="monitoring_description_managed_profile_named_vpn" msgid="1427905889862420559">"आपकी कार्य प्रोफ़ाइल <xliff:g id="VPN_APP">%1$s</xliff:g> से कनेक्ट है, जो ईमेल, ऐप्लिकेशन और वेबसाइटों सहित आपकी नेटवर्क गतिविधि की निगरानी कर सकता है."</string>
+ <string name="monitoring_description_managed_profile_named_vpn" msgid="1427905889862420559">"आपकी वर्क प्रोफ़ाइल <xliff:g id="VPN_APP">%1$s</xliff:g> से कनेक्ट है, जो ईमेल, ऐप्लिकेशन और वेबसाइटों सहित आपकी नेटवर्क गतिविधि की निगरानी कर सकता है."</string>
<string name="monitoring_description_personal_profile_named_vpn" msgid="3133980926929069283">"आपकी व्यक्तिगत प्रोफ़ाइल <xliff:g id="VPN_APP">%1$s</xliff:g> से कनेक्ट है, जो ईमेल, ऐप्लिकेशन और वेबसाइटों सहित आपकी नेटवर्क गतिविधि की निगरानी कर सकता है."</string>
<string name="monitoring_description_do_header_generic" msgid="96588491028288691">"<xliff:g id="DEVICE_OWNER_APP">%1$s</xliff:g> आपका डिवाइस प्रबंधित करता है."</string>
<string name="monitoring_description_do_header_with_name" msgid="5511133708978206460">"<xliff:g id="ORGANIZATION_NAME">%1$s</xliff:g> आपका डिवाइस प्रबंधित करने के लिए <xliff:g id="DEVICE_OWNER_APP">%2$s</xliff:g> का उपयोग करता है."</string>
@@ -506,11 +510,11 @@
<string name="monitoring_description_app_personal" msgid="484599052118316268">"आप <xliff:g id="APPLICATION">%1$s</xliff:g> से कनेक्‍ट हैं, जो ईमेल, ऐप्‍स और वेबसाइटों सहित आपकी व्‍यक्‍तिगत नेटवर्क गतिविधि की निगरानी कर सकता है."</string>
<string name="branded_monitoring_description_app_personal" msgid="2669518213949202599">"आप <xliff:g id="APPLICATION">%1$s</xliff:g> से कनेक्‍ट हैं, जो ईमेल, ऐप्लिकेशन और वेबसाइट सहित आपकी व्‍यक्‍तिगत नेटवर्क गतिविधि को मॉनिटर कर सकता है."</string>
<string name="monitoring_description_app_work" msgid="4612997849787922906">"आपकी वर्क प्रोफ़ाइल का प्रबंधन <xliff:g id="ORGANIZATION">%1$s</xliff:g> करता है. प्रोफ़ाइल <xliff:g id="APPLICATION">%2$s</xliff:g> से कनेक्ट है, जो ईमेल, ऐप्लिकेशन और वेबसाइटों सहित आपकी नेटवर्क गतिविधि की निगरानी कर सकता है.\n\nऔर जानकारी के लिए, अपने एडमिन से संपर्क करें."</string>
- <string name="monitoring_description_app_personal_work" msgid="5664165460056859391">"आपकी कार्य प्रोफ़ाइल का प्रबंधन <xliff:g id="ORGANIZATION">%1$s</xliff:g> करता है. प्रोफ़ाइल <xliff:g id="APPLICATION_WORK">%2$s</xliff:g> से कनेक्ट है, जो ईमेल, ऐप्लिकेशन और वेबसाइटों सहित आपकी नेटवर्क गतिविधि की निगरानी कर सकता है.\n\nआप <xliff:g id="APPLICATION_PERSONAL">%3$s</xliff:g> से भी कनेक्ट हैं, जो आपकी व्यक्तिगत नेटवर्क गतिविधि की निगरानी कर सकता है."</string>
+ <string name="monitoring_description_app_personal_work" msgid="5664165460056859391">"आपकी वर्क प्रोफ़ाइल का प्रबंधन <xliff:g id="ORGANIZATION">%1$s</xliff:g> करता है. प्रोफ़ाइल <xliff:g id="APPLICATION_WORK">%2$s</xliff:g> से कनेक्ट है, जो ईमेल, ऐप्लिकेशन और वेबसाइटों सहित आपकी नेटवर्क गतिविधि की निगरानी कर सकता है.\n\nआप <xliff:g id="APPLICATION_PERSONAL">%3$s</xliff:g> से भी कनेक्ट हैं, जो आपकी व्यक्तिगत नेटवर्क गतिविधि की निगरानी कर सकता है."</string>
<string name="keyguard_indication_trust_unlocked" msgid="2712865815371519117">"TrustAgent की वजह से अनलॉक रखा गया है"</string>
<string name="keyguard_indication_trust_disabled" msgid="7412534203633528135">"जब तक कि आप मैन्‍युअल रूप से अनलॉक नहीं करते तब तक डिवाइस लॉक रहेगा"</string>
<string name="hidden_notifications_title" msgid="7139628534207443290">"सूचनाएं ज़्यादा तेज़ी से पाएं"</string>
- <string name="hidden_notifications_text" msgid="2326409389088668981">"आपके द्वारा उन्हें अनलॉक किए जाने से पहले देखें"</string>
+ <string name="hidden_notifications_text" msgid="2326409389088668981">" उन्हें अनलॉक किए जाने से पहले देखें"</string>
<string name="hidden_notifications_cancel" msgid="3690709735122344913">"रहने दें"</string>
<string name="hidden_notifications_setup" msgid="41079514801976810">"सेट करें"</string>
<string name="zen_mode_and_condition" msgid="4462471036429759903">"<xliff:g id="ZEN_MODE">%1$s</xliff:g>. <xliff:g id="EXIT_CONDITION">%2$s</xliff:g>"</string>
@@ -527,8 +531,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"स्‍क्रीन पिन कर दी गई है"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"इससे वह तब तक दिखता रहता है जब तक कि आप उसे अनपिन नहीं कर देते. अनपिन करने के लिए, \'वापस जाएं\' और \'खास जानकारी\' को दबाकर रखें."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"इससे वह तब तक दिखाई देती है जब तक आप उसे अनपिन नहीं कर देते. अनपिन करने के लिए, होम और वापस जाएं वाले बटन को दबाकर रखें."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"इससे ऐप्लिकेशन की स्क्रीन तब तक दिखाई देती है जब तक आप उसे अनपिन नहीं करते. अनपिन करने के लिए ऊपर स्वाइप करें और स्क्रीन दबाकर रखें."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"इससे वह तब तक दिखता रहता है जब तक कि आप उसे अनपिन नहीं कर देते. अनपिन करने के लिए, \'खास जानकारी\' को दबाकर रखें."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"इससे वह तब तक दिखाई देती है जब तक आप उसे अनपिन नहीं कर देते. अनपिन करने के लिए, होम बटन को दबाकर रखें."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"इस स्क्रीन को अनपिन करने के लिए, खास जानकारी और वापस जाएं वाले बटन को दबाकर रखें"</string>
@@ -583,7 +586,7 @@
<string name="show_demo_mode" msgid="2018336697782464029">"डेमो मोड दिखाएं"</string>
<string name="status_bar_ethernet" msgid="5044290963549500128">"ईथरनेट"</string>
<string name="status_bar_alarm" msgid="8536256753575881818">"अलार्म"</string>
- <string name="status_bar_work" msgid="6022553324802866373">"कार्य प्रोफ़ाइल"</string>
+ <string name="status_bar_work" msgid="6022553324802866373">"वर्क प्रोफ़ाइल"</string>
<string name="status_bar_airplane" msgid="7057575501472249002">"हवाई जहाज़ मोड"</string>
<string name="add_tile" msgid="2995389510240786221">"टाइल जोड़ें"</string>
<string name="broadcast_tile" msgid="3894036511763289383">"टाइल प्रसारित करें"</string>
@@ -593,7 +596,7 @@
<string name="alarm_template_far" msgid="4242179982586714810">"<xliff:g id="WHEN">%1$s</xliff:g> पर"</string>
<string name="accessibility_quick_settings_detail" msgid="2579369091672902101">"तेज़ सेटिंग, <xliff:g id="TITLE">%s</xliff:g>."</string>
<string name="accessibility_status_bar_hotspot" msgid="4099381329956402865">"हॉटस्पॉट"</string>
- <string name="accessibility_managed_profile" msgid="6613641363112584120">"कार्य प्रोफ़ाइल"</string>
+ <string name="accessibility_managed_profile" msgid="6613641363112584120">"वर्क प्रोफ़ाइल"</string>
<string name="tuner_warning_title" msgid="7094689930793031682">"कुछ के लिए मज़ेदार लेकिन सबके लिए नहीं"</string>
<string name="tuner_warning" msgid="8730648121973575701">"सिस्टम यूज़र इंटरफ़ेस (यूआई) ट्यूनर, आपको Android यूज़र इंटरफ़ेस में सुधार लाने और उसे अपनी पसंद के हिसाब से बदलने के कुछ और तरीके देता है. प्रयोग के तौर पर इस्तेमाल हो रहीं ये सुविधाएं आगे चल कर रिलीज़ की जा सकती हैं, रोकी जा सकती हैं या दिखाई देना बंद हो सकती हैं. सावधानी से आगे बढ़ें."</string>
<string name="tuner_persistent_warning" msgid="8597333795565621795">"ये प्रयोगात्मक सुविधाएं आगामी रिलीज़ में बदल सकती हैं, रुक सकती हैं या दिखाई देना बंद हो सकती हैं. सावधानी से आगे बढ़ें."</string>
@@ -640,16 +643,11 @@
<string name="inline_keep_showing_app" msgid="1723113469580031041">"इस ऐप्लिकेशन से जुड़ी सूचनाएं दिखाना जारी रखें?"</string>
<string name="notification_silence_title" msgid="7352089096356977930">"बिना आवाज़ के"</string>
<string name="notification_alert_title" msgid="3966526305405016221">"ज़रूरी"</string>
- <!-- no translation found for notification_channel_summary_low (1065819618107531284) -->
- <skip />
- <!-- no translation found for notification_channel_summary_low_status (2702170424808743755) -->
- <skip />
- <!-- no translation found for notification_channel_summary_low_lock (7966605244472624458) -->
- <skip />
- <!-- no translation found for notification_channel_summary_low_status_lock (7012562768950012739) -->
- <skip />
- <!-- no translation found for notification_channel_summary_default (3847289783382316019) -->
- <skip />
+ <string name="notification_channel_summary_low" msgid="1065819618107531284">"सिर्फ़ नीचे खिंचने वाली सूची में सूचनाएं दिखती हैं ताकि आप उन पर पूरा ध्यान दे सकें. दिखते समय आवाज़ और वाइब्रेशन हमेशा बंद रहते हैं."</string>
+ <string name="notification_channel_summary_low_status" msgid="2702170424808743755">"कम ज़रूरी सूचनाएं दिखती हैं. दिखते समय आवाज़ और वाइब्रेशन हमेशा बंद रहते हैं."</string>
+ <string name="notification_channel_summary_low_lock" msgid="7966605244472624458">"कम ज़रूरी सूचनाएं दिखती हैं. दिखते समय आवाज़ और वाइब्रेशन हमेशा बंद रहते हैं."</string>
+ <string name="notification_channel_summary_low_status_lock" msgid="7012562768950012739">"कम ज़रूरी सूचनाएं दिखती हैं. दिखते समय आवाज़ और वाइब्रेशन हमेशा बंद रहते हैं."</string>
+ <string name="notification_channel_summary_default" msgid="3847289783382316019">"आवाज़ और स्टेटस बार के आइकॉन की मदद से सूचनाओं पर आपका ध्यान खिंचता है. लॉक स्क्रीन पर दिखाई देता है."</string>
<string name="notification_unblockable_desc" msgid="4556908766584964102">"ये सूचनाएं नहीं बदली जा सकती हैं."</string>
<string name="notification_multichannel_desc" msgid="4695920306092240550">"सूचनाओं के इस समूह को यहां कॉन्फ़िगर नहीं किया जा सकता"</string>
<string name="notification_delegate_header" msgid="2857691673814814270">"प्रॉक्सी सूचना"</string>
diff --git a/packages/SystemUI/res/values-hr/strings.xml b/packages/SystemUI/res/values-hr/strings.xml
index 6d078e327ada..c7b68d9f2146 100644
--- a/packages/SystemUI/res/values-hr/strings.xml
+++ b/packages/SystemUI/res/values-hr/strings.xml
@@ -307,7 +307,7 @@
<string name="quick_settings_bluetooth_secondary_label_hearing_aids" msgid="4930931771490695395">"Slušni aparati"</string>
<string name="quick_settings_bluetooth_secondary_label_transient" msgid="4551281899312150640">"Uključivanje…"</string>
<string name="quick_settings_brightness_label" msgid="6968372297018755815">"Svjetlina"</string>
- <string name="quick_settings_rotation_unlocked_label" msgid="7305323031808150099">"Automatsko izmjenjivanje"</string>
+ <string name="quick_settings_rotation_unlocked_label" msgid="7305323031808150099">"Automatsko zakretanje"</string>
<string name="accessibility_quick_settings_rotation" msgid="4231661040698488779">"Automatsko zakretanje zaslona"</string>
<string name="accessibility_quick_settings_rotation_value" msgid="8187398200140760213">"Način: <xliff:g id="ID_1">%s</xliff:g>"</string>
<string name="quick_settings_rotation_locked_label" msgid="6359205706154282377">"Izmjenjivanje je zaključano"</string>
@@ -451,6 +451,8 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"Ne prikazuj ponovo"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"Izbriši sve"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"Upravljajte"</string>
+ <string name="notification_section_header_gentle" msgid="8356064473678167305">"Neupadljive obavijesti"</string>
+ <string name="accessibility_notification_section_header_gentle_clear_all" msgid="4270384919249494640">"Izbrišite sve neupadljive obavijesti"</string>
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"Značajka Ne uznemiravaj pauzirala je Obavijesti"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"Započni sad"</string>
<string name="empty_shade_text" msgid="708135716272867002">"Nema obavijesti"</string>
@@ -530,8 +532,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"Zaslon je prikvačen"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"Zaslon će tako ostati u prvom planu dok ga ne otkvačite. Dodirnite i zadržite Natrag i Pregled da biste ga otkvačili."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"Zaslon će tako ostati u prvom planu dok ga ne otkvačite. Dodirnite gumbe Natrag i Početna i zadržite pritisak da biste ga otkvačili."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"Zaslon će tako ostati u prvom planu dok ga ne otkvačite. Prijeđite prstom prema gore i zadržite da biste ga otkvačili."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"Zaslon će tako ostati u prvom planu dok ga ne otkvačite. Dodirnite i zadržite Pregled da biste ga otkvačili."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"Zaslon će tako ostati u prvom planu dok ga ne otkvačite. Dodirnite gumb Početna i zadržite pritisak da biste ga otkvačili."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"Da biste otkvačili ovaj zaslon, dodirnite gumbe Natrag i Pregled i zadržite pritisak"</string>
@@ -917,8 +918,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"Otvorite aplikaciju <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"Postavke za oblačiće za aplikaciju <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"Želite li dopustiti oblačiće iz aplikacije <xliff:g id="APP_NAME">%1$s</xliff:g>?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"Upravljanje"</string>
<string name="no_bubbles" msgid="337101288173078247">"Odbij"</string>
<string name="yes_bubbles" msgid="668809525728633841">"Dopusti"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"Pitaj me kasnije"</string>
diff --git a/packages/SystemUI/res/values-hu/strings.xml b/packages/SystemUI/res/values-hu/strings.xml
index 7b7d6b214c0a..7b97961287d3 100644
--- a/packages/SystemUI/res/values-hu/strings.xml
+++ b/packages/SystemUI/res/values-hu/strings.xml
@@ -448,6 +448,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"Ne jelenjen meg többé"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"Az összes törlése"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"Kezelés"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"Ne zavarjanak funkcióval szüneteltetett értesítések"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"Indítás most"</string>
<string name="empty_shade_text" msgid="708135716272867002">"Nincs értesítés"</string>
@@ -527,8 +531,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"A képernyő rögzítve van"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"Megjelenítve tartja addig, amíg Ön fel nem oldja a rögzítést. A feloldáshoz tartsa lenyomva a Vissza és az Áttekintés lehetőséget."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"Megjelenítve tartja addig, amíg Ön fel nem oldja a rögzítést. A feloldáshoz tartsa lenyomva a Vissza és a Kezdőképernyő elemet."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"Megjelenítve tartja addig, amíg Ön fel nem oldja a rögzítést. A feloldáshoz csúsztasson fel, és tartsa ujját a képernyőn."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"Megjelenítve tartja addig, amíg Ön fel nem oldja a rögzítést. A feloldáshoz tartsa lenyomva az Áttekintés lehetőséget."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"Megjelenítve tartja addig, amíg Ön fel nem oldja a rögzítést. A feloldáshoz tartsa lenyomva a Kezdőképernyő elemet."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"A képernyő rögzítésének feloldásához tartsa lenyomva a Vissza és az Áttekintés gombot"</string>
@@ -912,8 +915,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"<xliff:g id="APP_NAME">%1$s</xliff:g> megnyitása"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"A(z) <xliff:g id="APP_NAME">%1$s</xliff:g>-buborékok beállításai"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"Engedélyezi a(z) <xliff:g id="APP_NAME">%1$s</xliff:g> alkalmazásból származó buborékokat?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"Kezelés"</string>
<string name="no_bubbles" msgid="337101288173078247">"Tiltás"</string>
<string name="yes_bubbles" msgid="668809525728633841">"Engedélyezés"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"Kérdezzen rá később"</string>
diff --git a/packages/SystemUI/res/values-hy/strings.xml b/packages/SystemUI/res/values-hy/strings.xml
index 8fa187dfc830..1cb5a7bb8071 100644
--- a/packages/SystemUI/res/values-hy/strings.xml
+++ b/packages/SystemUI/res/values-hy/strings.xml
@@ -448,6 +448,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"Այլևս ցույց չտալ"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"Մաքրել բոլորը"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"Կառավարել"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"Ծանուցումները չեն ցուցադրվի «Չանհանգստացնել» ռեժիմում"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"Սկսել հիմա"</string>
<string name="empty_shade_text" msgid="708135716272867002">"Ծանուցումներ չկան"</string>
@@ -527,8 +531,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"Էկրանն ամրացված է"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"Էկրանը կմնա տեսադաշտում, մինչև այն ապամրացնեք: Ապամրացնելու համար հպեք և պահեք Հետ և Համատեսք կոճակները:"</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"Էկրանը կցուցադրվի այնքան ժամանակ, մինչև որ չապամրացնեք այն: Ապամրացնելու համար հպեք և պահեք Հետ և գլխավոր էկրանի կոճակները:"</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"Էկրանը կցուցադրվի այնքան ժամանակ, մինչև որ չապամրացնեք այն: Ապամրացնելու համար մատը սահեցրեք վեր և պահեք։"</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"Էկրանը կմնա տեսադաշտում, մինչև այն ապամրացնեք: Ապամրացնելու համար հպեք և պահեք Համատեսք կոճակը:"</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"Էկրանը կցուցադրվի այնքան ժամանակ, մինչև որ չապամրացնեք այն: Ապամրացնելու համար հպեք և պահեք գլխավոր էկրանի կոճակը:"</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"Էկրանն ապամրացնելու համար հպեք և պահեք Հետ և Համատեսք կոճակները"</string>
@@ -912,8 +915,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"Բացել <xliff:g id="APP_NAME">%1$s</xliff:g> հավելվածը"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"<xliff:g id="APP_NAME">%1$s</xliff:g>-ի ամպիկների կարգավորումներ"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"Թույլատրե՞լ ամպիկներ <xliff:g id="APP_NAME">%1$s</xliff:g>-ից։"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"Կառավարել"</string>
<string name="no_bubbles" msgid="337101288173078247">"Մերժել"</string>
<string name="yes_bubbles" msgid="668809525728633841">"Թույլատրել"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"Հարցնել ավելի ուշ"</string>
diff --git a/packages/SystemUI/res/values-in/strings.xml b/packages/SystemUI/res/values-in/strings.xml
index 030825ed7838..cb1769b96b42 100644
--- a/packages/SystemUI/res/values-in/strings.xml
+++ b/packages/SystemUI/res/values-in/strings.xml
@@ -448,6 +448,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"Jangan tampilkan lagi"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"Hapus semua"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"Kelola"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"Notifikasi dijeda oleh mode Jangan Ganggu"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"Mulai sekarang"</string>
<string name="empty_shade_text" msgid="708135716272867002">"Tidak ada notifikasi"</string>
@@ -527,8 +531,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"Layar dipasangi pin"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"Ini akan terus ditampilkan sampai Anda melepas pin. Sentuh &amp; tahan tombol Kembali dan Ringkasan untuk melepas pin."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"Ini akan terus ditampilkan sampai Anda melepas pin. Sentuh &amp; tahan tombol Kembali dan Beranda untuk melepas pin."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"Ini akan terus ditampilkan sampai Anda melepas pin. Geser ke atas &amp; tahan untuk melepas pin."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"Ini akan terus ditampilkan sampai Anda melepas pin. Sentuh dan tahan tombol Ringkasan untuk melepas pin."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"Ini akan terus ditampilkan sampai Anda melepas pin. Sentuh dan tahan tombol Beranda untuk melepas pin."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"Untuk melepas pin layar ini, sentuh &amp; tahan tombol Kembali dan Ringkasan"</string>
@@ -766,8 +769,8 @@
<string name="right_keycode" msgid="708447961000848163">"Kode tombol kanan"</string>
<string name="left_icon" msgid="3096287125959387541">"Ikon kiri"</string>
<string name="right_icon" msgid="3952104823293824311">"Ikon kanan"</string>
- <string name="drag_to_add_tiles" msgid="230586591689084925">"Tahan dan tarik untuk menambahkan tile"</string>
- <string name="drag_to_rearrange_tiles" msgid="4566074720193667473">"Tahan dan tarik untuk mengatur ulang tile"</string>
+ <string name="drag_to_add_tiles" msgid="230586591689084925">"Tahan dan tarik untuk menambahkan kartu"</string>
+ <string name="drag_to_rearrange_tiles" msgid="4566074720193667473">"Tahan dan tarik untuk mengatur ulang kartu"</string>
<string name="drag_to_remove_tiles" msgid="3361212377437088062">"Tarik ke sini untuk menghapus"</string>
<string name="drag_to_remove_disabled" msgid="2390968976638993382">"Anda membutuhkan setidaknya 6 tile"</string>
<string name="qs_edit" msgid="2232596095725105230">"Edit"</string>
@@ -912,8 +915,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"Buka <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"Setelan untuk balon <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"Izinkan balon dari <xliff:g id="APP_NAME">%1$s</xliff:g>?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"Kelola"</string>
<string name="no_bubbles" msgid="337101288173078247">"Tolak"</string>
<string name="yes_bubbles" msgid="668809525728633841">"Izinkan"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"Nanti saja"</string>
diff --git a/packages/SystemUI/res/values-is/strings.xml b/packages/SystemUI/res/values-is/strings.xml
index 846eccc26fcf..31f6546f12ff 100644
--- a/packages/SystemUI/res/values-is/strings.xml
+++ b/packages/SystemUI/res/values-is/strings.xml
@@ -448,6 +448,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"Ekki sýna þetta aftur"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"Hreinsa allt"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"Stjórna"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"Hlé gert á tilkynningum þar sem stillt er á „Ónáðið ekki“"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"Byrja núna"</string>
<string name="empty_shade_text" msgid="708135716272867002">"Engar tilkynningar"</string>
@@ -527,8 +531,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"Skjárinn er festur"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"Þetta heldur þessu opnu þangað til þú losar það. Haltu fingri á „Til baka“ og „Yfirlit“ til að losa."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"Þetta heldur þessu opnu þangað til það er losað. Haltu inni bakkhnappinum og heimahnappinum til að losa."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"Þetta heldur þessu opnu þangað til það er losað. Strjúktu upp og haltu inni til að losa."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"Þetta heldur þessu opnu þangað til þú losar það. Haltu fingri á „Yfirlit“ til að losa."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"Þetta heldur þessu opnu þangað til það er losað. Haltu heimahnappinum inni til að losa."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"Til að losa þessa skjámynd skaltu halda inni bakkhnappinum og yfirlitshnappinum"</string>
@@ -912,8 +915,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"Opna <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"Stillingar fyrir blöðrur frá <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"Leyfa blöðrur frá <xliff:g id="APP_NAME">%1$s</xliff:g>?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"Stjórna"</string>
<string name="no_bubbles" msgid="337101288173078247">"Hafna"</string>
<string name="yes_bubbles" msgid="668809525728633841">"Leyfa"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"Spyrja mig síðar"</string>
diff --git a/packages/SystemUI/res/values-it/strings.xml b/packages/SystemUI/res/values-it/strings.xml
index 841e37035b73..85c2242f4c29 100644
--- a/packages/SystemUI/res/values-it/strings.xml
+++ b/packages/SystemUI/res/values-it/strings.xml
@@ -448,6 +448,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"Non mostrare più"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"Cancella tutto"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"Gestisci"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"Notifiche messe in pausa in base alla modalità Non disturbare"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"Avvia adesso"</string>
<string name="empty_shade_text" msgid="708135716272867002">"Nessuna notifica"</string>
@@ -527,8 +531,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"La schermata è fissata"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"La schermata rimane visibile finché non viene sganciata. Per sganciarla, tieni premuto Indietro e Panoramica."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"La schermata rimane visibile finché non viene disattivato il blocco su schermo. Per disattivarlo, tocca e tieni premuto Indietro e Home."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"Mantiene la visualizzazione fino allo sblocco. Scorri verso l\'alto e tieni premuto per sbloccare."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"La schermata rimane visibile finché non viene sganciata. Per sganciarla, tieni premuto Panoramica."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"La schermata rimane visibile finché non viene disattivato il blocco su schermo. Per disattivarlo, tocca e tieni premuto Home."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"Per disattivare il blocco su schermo, tocca e tieni premuti i pulsanti Indietro e Panoramica"</string>
@@ -615,7 +618,7 @@
<string name="do_not_silence" msgid="6878060322594892441">"Non silenziare"</string>
<string name="do_not_silence_block" msgid="4070647971382232311">"Non silenziare e non bloccare"</string>
<string name="tuner_full_importance_settings" msgid="3207312268609236827">"Controlli di gestione delle notifiche"</string>
- <string name="tuner_full_importance_settings_on" msgid="7545060756610299966">"Attiva"</string>
+ <string name="tuner_full_importance_settings_on" msgid="7545060756610299966">"On"</string>
<string name="tuner_full_importance_settings_off" msgid="8208165412614935229">"Off"</string>
<string name="power_notification_controls_description" msgid="4372459941671353358">"I controlli di gestione delle notifiche ti consentono di impostare un livello di importanza compreso tra 0 e 5 per le notifiche di un\'app. \n\n"<b>"Livello 5"</b>" \n- Mostra in cima all\'elenco di notifiche \n- Consenti l\'interruzione a schermo intero \n- Visualizza sempre \n\n"<b>"Livello 4"</b>" \n- Impedisci l\'interruzione a schermo intero \n- Visualizza sempre \n\n"<b>"Livello 3"</b>" \n- Impedisci l\'interruzione a schermo intero \n- Non visualizzare mai \n\n"<b>"Livello 2"</b>" \n- Impedisci l\'interruzione a schermo intero \n- Non visualizzare mai \n- Non emettere mai suoni e vibrazioni \n\n"<b>"Livello 1"</b>" \n- Impedisci l\'interruzione a schermo intero \n- Non visualizzare mai \n- Non emettere mai suoni e vibrazioni \n- Nascondi da schermata di blocco e barra di stato \n- Mostra in fondo all\'elenco di notifiche \n\n"<b>"Livello 0"</b>" \n- Blocca tutte le notifiche dell\'app"</string>
<string name="notification_header_default_channel" msgid="7506845022070889909">"Notifiche"</string>
@@ -632,7 +635,7 @@
<string name="inline_block_button" msgid="8735843688021655065">"Blocca"</string>
<string name="inline_keep_button" msgid="6665940297019018232">"Continua a mostrare"</string>
<string name="inline_minimize_button" msgid="966233327974702195">"Riduci a icona"</string>
- <string name="inline_silent_button_silent" msgid="6904727667411781466">"Modalità senza avvisi"</string>
+ <string name="inline_silent_button_silent" msgid="6904727667411781466">"Silenziose"</string>
<string name="inline_silent_button_stay_silent" msgid="6308371431217601009">"Continua con notifiche silenziose"</string>
<string name="inline_silent_button_alert" msgid="2449191160203602471">"Modalità invasiva"</string>
<string name="inline_silent_button_keep_alerting" msgid="327696842264359693">"Continua ad avvisare"</string>
@@ -640,11 +643,11 @@
<string name="inline_keep_showing_app" msgid="1723113469580031041">"Continuare a ricevere notifiche da questa app?"</string>
<string name="notification_silence_title" msgid="7352089096356977930">"Senza avvisi"</string>
<string name="notification_alert_title" msgid="3966526305405016221">"Con priorità"</string>
- <string name="notification_channel_summary_low" msgid="1065819618107531284">"Ti consente di concentrarti grazie alla visualizzazione delle notifiche soltanto nell\'area a discesa. Sempre silenziose."</string>
+ <string name="notification_channel_summary_low" msgid="1065819618107531284">"Puoi concentrarti perché le notifiche sono visualizzate solo nell\'area a discesa. Sempre silenziose."</string>
<string name="notification_channel_summary_low_status" msgid="2702170424808743755">"Vengono mostrate le notifiche con priorità bassa. Sempre silenziose."</string>
<string name="notification_channel_summary_low_lock" msgid="7966605244472624458">"Vengono mostrate le notifiche con priorità bassa. Sempre silenziose."</string>
<string name="notification_channel_summary_low_status_lock" msgid="7012562768950012739">"Vengono mostrate le notifiche con priorità bassa. Sempre silenziose."</string>
- <string name="notification_channel_summary_default" msgid="3847289783382316019">"Viene attirata la tua attenzione con un suono e un\'icona nella barra di stato. La notifica viene mostrata nella schermata di blocco."</string>
+ <string name="notification_channel_summary_default" msgid="3847289783382316019">"Attirano la tua attenzione con un suono e un\'icona nella barra di stato. Le notifiche sono mostrate nella schermata di blocco."</string>
<string name="notification_unblockable_desc" msgid="4556908766584964102">"Impossibile modificare queste notifiche."</string>
<string name="notification_multichannel_desc" msgid="4695920306092240550">"Qui non è possibile configurare questo gruppo di notifiche"</string>
<string name="notification_delegate_header" msgid="2857691673814814270">"Notifica inviata al proxy"</string>
@@ -912,8 +915,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"Apri <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"Impostazioni per fumetti <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"Consentire fumetti da <xliff:g id="APP_NAME">%1$s</xliff:g>?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"Gestisci"</string>
<string name="no_bubbles" msgid="337101288173078247">"Rifiuta"</string>
<string name="yes_bubbles" msgid="668809525728633841">"Consenti"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"Ricordamelo più tardi"</string>
diff --git a/packages/SystemUI/res/values-iw/strings.xml b/packages/SystemUI/res/values-iw/strings.xml
index 87ffbbb64e3f..c2469e634845 100644
--- a/packages/SystemUI/res/values-iw/strings.xml
+++ b/packages/SystemUI/res/values-iw/strings.xml
@@ -454,6 +454,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"אל תציג שוב"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"נקה הכל"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"ניהול"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"התראות הושהו על ידי מצב \'נא לא להפריע\'"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"התחל כעת"</string>
<string name="empty_shade_text" msgid="708135716272867002">"אין התראות"</string>
@@ -533,8 +537,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"המסך מוצמד"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"נשאר בתצוגה עד לביטול ההצמדה. יש ללחוץ לחיצה ארוכה על הלחצנים \'הקודם\' ו\'סקירה\' כדי לבטל את ההצמדה."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"נשאר בתצוגה עד לביטול ההצמדה. יש ללחוץ לחיצה ארוכה על הלחצנים \'הקודם\' ו\'דף הבית\' כדי לבטל את ההצמדה."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"נשאר בתצוגה עד לביטול ההצמדה. יש להחליק למעלה ולהחזיק כדי לבטל הצמדה."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"נשאר בתצוגה עד לביטול ההצמדה. יש ללחוץ לחיצה ארוכה על הלחצן \'סקירה\' כדי לבטל את ההצמדה."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"נשאר בתצוגה עד לביטול ההצמדה. יש ללחוץ לחיצה ארוכה על הלחצן \'דף הבית\' כדי לבטל את ההצמדה."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"כדי לבטל את ההצמדה של מסך זה, יש ללחוץ לחיצה ארוכה על הלחצנים \'הקודם\' ו\'סקירה\'"</string>
@@ -922,8 +925,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"לפתיחת <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"הגדרות בשביל בועות של <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"להתיר ל-<xliff:g id="APP_NAME">%1$s</xliff:g> להציג בועות?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"ניהול"</string>
<string name="no_bubbles" msgid="337101288173078247">"אני לא מרשה"</string>
<string name="yes_bubbles" msgid="668809525728633841">"כן, זה בסדר"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"אחליט מאוחר יותר"</string>
diff --git a/packages/SystemUI/res/values-ja/strings.xml b/packages/SystemUI/res/values-ja/strings.xml
index a34378ee1403..327bfff56532 100644
--- a/packages/SystemUI/res/values-ja/strings.xml
+++ b/packages/SystemUI/res/values-ja/strings.xml
@@ -67,7 +67,7 @@
<string name="usb_disable_contaminant_detection" msgid="2103905315747120033">"USB を有効にする"</string>
<string name="compat_mode_on" msgid="6623839244840638213">"画面サイズに合わせて拡大"</string>
<string name="compat_mode_off" msgid="4434467572461327898">"画面サイズに合わせて拡大"</string>
- <string name="global_action_screenshot" msgid="8329831278085426283">"スクリーンショット"</string>
+ <string name="global_action_screenshot" msgid="8329831278085426283">"画面の保存"</string>
<string name="screenshot_saving_ticker" msgid="7403652894056693515">"スクリーンショットを保存中..."</string>
<string name="screenshot_saving_title" msgid="8242282144535555697">"スクリーンショットを保存しています..."</string>
<string name="screenshot_saved_title" msgid="5637073968117370753">"スクリーンショットを保存しました"</string>
@@ -448,6 +448,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"次回から表示しない"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"すべて消去"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"管理"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"サイレント モードにより通知は一時停止中です"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"今すぐ開始"</string>
<string name="empty_shade_text" msgid="708135716272867002">"通知はありません"</string>
@@ -527,8 +531,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"画面が固定されました"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"固定を解除するまで画面が常に表示されるようになります。[戻る] と [最近] を同時に押し続けると固定が解除されます。"</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"固定を解除するまで画面が常に表示されるようになります。[戻る] と [ホーム] を同時に押し続けると固定が解除されます。"</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"固定を解除するまで常に表示されます。上にスワイプして長押しすると固定が解除されます。"</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"固定を解除するまで画面が常に表示されるようになります。[最近] を押し続けると固定が解除されます。"</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"固定を解除するまで画面が常に表示されるようになります。[ホーム] を押し続けると固定が解除されます。"</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"この画面の固定を解除するには [戻る] ボタンと [最近] ボタンを押し続けます"</string>
@@ -912,8 +915,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"<xliff:g id="APP_NAME">%1$s</xliff:g> を開く"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"<xliff:g id="APP_NAME">%1$s</xliff:g> のふきだしの設定"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"<xliff:g id="APP_NAME">%1$s</xliff:g> のふきだしを許可しますか?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"管理"</string>
<string name="no_bubbles" msgid="337101288173078247">"拒否"</string>
<string name="yes_bubbles" msgid="668809525728633841">"許可"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"後で確認"</string>
diff --git a/packages/SystemUI/res/values-ka/strings.xml b/packages/SystemUI/res/values-ka/strings.xml
index d3e73a06a946..e21f8e7f54c8 100644
--- a/packages/SystemUI/res/values-ka/strings.xml
+++ b/packages/SystemUI/res/values-ka/strings.xml
@@ -448,6 +448,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"აღარ მაჩვენო"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"ყველას გასუფთავება"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"მართვა"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"შეტყობინებები დაპაუზდა „არ შემაწუხოთ“ რეჟიმის მეშვეობით"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"დაწყება ახლავე"</string>
<string name="empty_shade_text" msgid="708135716272867002">"შეტყობინებები არ არის."</string>
@@ -527,8 +531,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"ეკრანი ჩამაგრებულია"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"ამით ის დარჩება ხედში ჩამაგრების მოხსნამდე. ჩამაგრების მოსახსნელად, ხანგრძლივად შეეხეთ „უკან და მიმოხილვა“-ს."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"ამით ის დარჩება ხედში ჩამაგრების მოხსნამდე. ჩამაგრების მოსახსნელად, ხანგრძლივად შეეხეთ „უკან მთავარ გვერდზე“-ს."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"ამით ის დარჩება ხედში ჩამაგრების მოხსნამდე. აუსვით ზემოთ და დააყოვნეთ ჩამაგრების მოსახსნელად."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"ამით ის დარჩება ხედში ჩამაგრების მოხსნამდე. ჩამაგრების მოსახსნელად, ხანგრძლივად შეეხეთ „მიმოხილვა“-ს."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"ამით ის დარჩება ხედში ჩამაგრების მოხსნამდე. ჩამაგრების მოსახსნელად, ხანგრძლივად შეეხეთ „მთავარ გვერდს“."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"ამ ეკრანის ჩამაგრების მოსახსნელად, ხანგრძლივად შეეხეთ ღილაკებს „უკან“ და „მიმოხილვა“"</string>
@@ -644,7 +647,7 @@
<string name="notification_channel_summary_low_status" msgid="2702170424808743755">"აჩვენებს ნაკლებად პრიორიტეტულ შეტყობინებებს. ყოველთვის ჩუმი."</string>
<string name="notification_channel_summary_low_lock" msgid="7966605244472624458">"აჩვენებს ნაკლებად პრიორიტეტულ შეტყობინებებს. ყოველთვის ჩუმი."</string>
<string name="notification_channel_summary_low_status_lock" msgid="7012562768950012739">"აჩვენებს ნაკლებად პრიორიტეტულ შეტყობინებებს. ყოველთვის ჩუმი."</string>
- <string name="notification_channel_summary_default" msgid="3847289783382316019">"იქცევს თქვენს ყურადღებას ხმით &amp; სტატუსის ზოლის ხატულა. ჩნდება ჩაკეტილ ეკრანზე."</string>
+ <string name="notification_channel_summary_default" msgid="3847289783382316019">"იქცევს თქვენს ყურადღებას ხმით &amp; სტატუსის ზოლის ხატულით. ჩნდება ჩაკეტილ ეკრანზე."</string>
<string name="notification_unblockable_desc" msgid="4556908766584964102">"ამ შეტყობინებების შეცვლა შეუძლებელია."</string>
<string name="notification_multichannel_desc" msgid="4695920306092240550">"შეტყობინებების ამ ჯგუფის კონფიგურირება აქ შეუძლებელია"</string>
<string name="notification_delegate_header" msgid="2857691673814814270">"პროქსირებული შეტყობინება"</string>
@@ -912,8 +915,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"<xliff:g id="APP_NAME">%1$s</xliff:g>-ის გახსნა"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"პარამეტრები <xliff:g id="APP_NAME">%1$s</xliff:g> ბუშტებისთვის"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"დაიშვას ბუშტები <xliff:g id="APP_NAME">%1$s</xliff:g>-დან?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"მართვა"</string>
<string name="no_bubbles" msgid="337101288173078247">"უარყოფა"</string>
<string name="yes_bubbles" msgid="668809525728633841">"დაშვება"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"მოგვიანებით მკითხეთ"</string>
diff --git a/packages/SystemUI/res/values-kk/strings.xml b/packages/SystemUI/res/values-kk/strings.xml
index 11365dd54bf5..a9bcd217483c 100644
--- a/packages/SystemUI/res/values-kk/strings.xml
+++ b/packages/SystemUI/res/values-kk/strings.xml
@@ -448,6 +448,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"Қайта көрсетпеу"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"Барлығын тазалау"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"Басқару"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"Хабарландырулар \"Мазаламау\" режимінде кідіртілді"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"Қазір бастау"</string>
<string name="empty_shade_text" msgid="708135716272867002">"Хабарландырулар жоқ"</string>
@@ -527,8 +531,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"Экран түйрелді"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"Экран босатылғанға дейін көрсетіліп тұрады. Оны босату үшін \"Артқа\" және \"Шолу\" түймелерін басып тұрыңыз."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"Экран босатылғанға дейін көрсетіліп тұрады. Оны босату үшін \"Артқа\" және \"Негізгі бет\" түймелерін түртіп, ұстап тұрыңыз"</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"Экран босатылғанға дейін көрсетіліп тұрады. Экранды босату үшін жоғары сырғытып, ұстап тұрыңыз."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"Экран босатылғанға дейін көрсетіліп тұрады. Оны босату үшін \"Кері\" түймесін басып тұрыңыз."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"Экран босатылғанға дейін көрсетіліп тұрады. Оны босату үшін \"Негізгі бет\" түймесін түртіп, ұстап тұрыңыз."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"Бұл экранды босату үшін \"Артқа\" және \"Шолу\" түймелерін түртіп, ұстап тұрыңыз"</string>
@@ -680,7 +683,7 @@
</plurals>
<string name="battery_panel_title" msgid="7944156115535366613">"Батареяны пайдалану"</string>
<string name="battery_detail_charging_summary" msgid="1279095653533044008">"Зарядтау кезінде Батарея үнемдегіш қол жетімді емес"</string>
- <string name="battery_detail_switch_title" msgid="6285872470260795421">"Батарея үнемдегіш"</string>
+ <string name="battery_detail_switch_title" msgid="6285872470260795421">"Battery Saver"</string>
<string name="battery_detail_switch_summary" msgid="9049111149407626804">"Өнімділікті және фондық деректерді азайтады"</string>
<string name="keyboard_key_button_template" msgid="6230056639734377300">"<xliff:g id="NAME">%1$s</xliff:g> түймесі"</string>
<string name="keyboard_key_home" msgid="2243500072071305073">"Home"</string>
@@ -767,7 +770,7 @@
<string name="left_icon" msgid="3096287125959387541">"Сол жақ белгіше"</string>
<string name="right_icon" msgid="3952104823293824311">"Оң жақ белгіше"</string>
<string name="drag_to_add_tiles" msgid="230586591689084925">"Қажетті элементтерді сүйреп әкеліп қойыңыз"</string>
- <string name="drag_to_rearrange_tiles" msgid="4566074720193667473">"Бөлшектердің ретін өзгерту үшін оны басып тұрып сүйреңіз"</string>
+ <string name="drag_to_rearrange_tiles" msgid="4566074720193667473">"Элементтердің ретін өзгерту үшін оларды басып тұрып сүйреңіз"</string>
<string name="drag_to_remove_tiles" msgid="3361212377437088062">"Керексіздерін осы жерге сүйреңіз"</string>
<string name="drag_to_remove_disabled" msgid="2390968976638993382">"Кемінде 6 бөлшек қажет"</string>
<string name="qs_edit" msgid="2232596095725105230">"Өңдеу"</string>
@@ -912,8 +915,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"<xliff:g id="APP_NAME">%1$s</xliff:g> қолданбасын ашу"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"<xliff:g id="APP_NAME">%1$s</xliff:g> қалқымалы анықтамаларының параметрлері"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"<xliff:g id="APP_NAME">%1$s</xliff:g> қолданбасының қалқымалы анықтамаларына рұқсат етілсін бе?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"Басқару"</string>
<string name="no_bubbles" msgid="337101288173078247">"Тыйым салу"</string>
<string name="yes_bubbles" msgid="668809525728633841">"Рұқсат беру"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"Кейінірек сұралсын"</string>
diff --git a/packages/SystemUI/res/values-km/strings.xml b/packages/SystemUI/res/values-km/strings.xml
index 1c74b4fbe55c..13f32b1ff63c 100644
--- a/packages/SystemUI/res/values-km/strings.xml
+++ b/packages/SystemUI/res/values-km/strings.xml
@@ -323,7 +323,7 @@
<string name="quick_settings_user_label" msgid="5238995632130897840">"ខ្ញុំ"</string>
<string name="quick_settings_user_title" msgid="4467690427642392403">"អ្នកប្រើ"</string>
<string name="quick_settings_user_new_user" msgid="9030521362023479778">"អ្នកប្រើ​ថ្មី"</string>
- <string name="quick_settings_wifi_label" msgid="9135344704899546041">"វ៉ាយហ្វាយ"</string>
+ <string name="quick_settings_wifi_label" msgid="9135344704899546041">"Wi-Fi"</string>
<string name="quick_settings_wifi_not_connected" msgid="7171904845345573431">"មិន​បាន​តភ្ជាប់"</string>
<string name="quick_settings_wifi_no_network" msgid="2221993077220856376">"គ្មាន​បណ្ដាញ"</string>
<string name="quick_settings_wifi_off_label" msgid="7558778100843885864">"វ៉ាយហ្វាយ​បានបិទ"</string>
@@ -448,6 +448,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"កុំ​បង្ហាញ​ម្ដងទៀត"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"សម្អាត​ទាំងអស់"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"គ្រប់គ្រង"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"ការជូនដំណឹង​បានផ្អាក​ដោយ​មុខងារកុំរំខាន"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"ចាប់ផ្ដើម​ឥឡូវ"</string>
<string name="empty_shade_text" msgid="708135716272867002">"គ្មាន​ការ​ជូនដំណឹង"</string>
@@ -527,8 +531,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"អេក្រង់​ត្រូវ​បាន​ភ្ជាប់"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"វា​នឹង​នៅតែ​បង្ហាញ រហូត​ទាល់​តែ​អ្នក​ដក​ការដៅ។ សូម​សង្កត់​ប៊ូតុង​ថយ​ក្រោយ និង​ប៊ូតុង​ទិដ្ឋភាពរួម​ឲ្យ​ជាប់ ដើម្បី​ដក​ការ​ដៅ។"</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"វា​នឹង​នៅតែ​បង្ហាញ រហូត​ទាល់​តែ​អ្នក​ដក​ការដៅ។ សូម​ចុចប៊ូតុង​ថយក្រោយ និងប៊ូតុង​ទំព័រដើម​ឱ្យ​ជាប់ ដើម្បី​ដក​ការ​ដៅ។"</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"វា​នឹង​នៅតែ​បង្ហាញ រហូតទាល់​តែអ្នក​ដកការដៅ។ អូសឡើងលើ​ឱ្យជាប់ ដើម្បី​ដក​ការដៅ។"</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"វា​នឹង​នៅតែ​បង្ហាញ រហូត​ទាល់​តែ​អ្នក​ដក​ការ​ដៅ។ សូម​សង្កត់​ប៊ូតុង​ទិដ្ឋភាពរួម​​ឲ្យ​ជាប់ ដើម្បី​ដក​ការ​ដៅ។"</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"វា​នឹង​នៅតែ​បង្ហាញ រហូត​ទាល់​តែ​អ្នក​ដក​ការដៅ។ សូម​ចុច​ប៊ូតុង​ទំព័រដើម​ឱ្យ​ជាប់ ដើម្បី​ដក​ការ​ដៅ។"</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"ដើម្បី​ដក​ការ​ដៅ​អេក្រង់​នេះ សូម​ចុច​ប៊ូតុង​ថយ​ក្រោយ និង​ប៊ូតុង​ទិដ្ឋភាពរួម​ឱ្យ​ជាប់"</string>
@@ -912,8 +915,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"បើក <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"ការកំណត់​សម្រាប់សារលេចឡើង <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"អនុញ្ញាត​សារលេចឡើង​ពី <xliff:g id="APP_NAME">%1$s</xliff:g>?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"គ្រប់គ្រង"</string>
<string name="no_bubbles" msgid="337101288173078247">"បដិសេធ"</string>
<string name="yes_bubbles" msgid="668809525728633841">"អនុញ្ញាត"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"សួរខ្ញុំនៅពេលក្រោយ"</string>
diff --git a/packages/SystemUI/res/values-kn/strings.xml b/packages/SystemUI/res/values-kn/strings.xml
index 297753878fe8..92403f15bcd8 100644
--- a/packages/SystemUI/res/values-kn/strings.xml
+++ b/packages/SystemUI/res/values-kn/strings.xml
@@ -448,6 +448,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"ಮತ್ತೊಮ್ಮೆ ತೋರಿಸದಿರು"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"ಎಲ್ಲವನ್ನೂ ತೆರವುಗೊಳಿಸು"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"ನಿರ್ವಹಿಸಿ"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"ಅಡಚಣೆ ಮಾಡಬೇಡಿ ಎನ್ನುವ ಮೂಲಕ ಅಧಿಸೂಚನೆಗಳನ್ನು ವಿರಾಮಗೊಳಿಸಲಾಗಿದೆ"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"ಈಗ ಪ್ರಾರಂಭಿಸಿ"</string>
<string name="empty_shade_text" msgid="708135716272867002">"ಯಾವುದೇ ಅಧಿಸೂಚನೆಗಳಿಲ್ಲ"</string>
@@ -527,8 +531,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"ಪರದೆಯನ್ನು ಪಿನ್ ಮಾಡಲಾಗಿದೆ"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"ನೀವು ಅನ್‌ಪಿನ್ ಮಾಡುವವರೆಗೆ ಅದನ್ನು ವೀಕ್ಷಣೆಯಲ್ಲಿಡುತ್ತದೆ. ಸ್ಪರ್ಶಿಸಿ ಮತ್ತು ಹಿಡಿದುಕೊಳ್ಳಿ ಹಾಗೂ ಅನ್‌ಪಿನ್ ಮಾಡಲು ಅವಲೋಕಿಸಿ."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"ನೀವು ಅನ್‌ಪಿನ್ ಮಾಡುವವರೆಗೆ ಅದನ್ನು ವೀಕ್ಷಣೆಯಲ್ಲಿಡುತ್ತದೆ. ಸ್ಪರ್ಶಿಸಿ ಮತ್ತು ಹಿಡಿದುಕೊಳ್ಳಿ ಹಾಗೂ ಅನ್‌ಪಿನ್ ಮಾಡಲು ಮುಖಪುಟಕ್ಕೆ ಹಿಂತಿರುಗಿ."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"ನೀವು ಅನ್‌ಪಿನ್ ಮಾಡುವವರೆಗೆ ಅದನ್ನು ವೀಕ್ಷಣೆಯಲ್ಲಿಡುತ್ತದೆ. ಮೇಲೆ ಸ್ವೈಪ್ ಮಾಡಿ ಮತ್ತು ಅನ್‌ಪಿನ್ ಮಾಡಲು ಹೋಲ್ಡ್ ಮಾಡಿ."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"ನೀವು ಅನ್‌ಪಿನ್ ಮಾಡುವವರೆಗೆ ಅದನ್ನು ವೀಕ್ಷಣೆಯಲ್ಲಿಡುತ್ತದೆ. ಅನ್‌ಪಿನ್ ಮಾಡಲು ಅವಲೋಕನವನ್ನು ಸ್ಪರ್ಶಿಸಿ ಮತ್ತು ಹೋಲ್ಡ್ ಮಾಡಿ."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"ನೀವು ಅನ್‌ಪಿನ್ ಮಾಡುವವರೆಗೆ ಅದನ್ನು ವೀಕ್ಷಣೆಯಲ್ಲಿಡುತ್ತದೆ. ಅನ್‌ಪಿನ್ ಮಾಡಲು ಮುಖಪುಟವನ್ನು ಸ್ಪರ್ಶಿಸಿ ಮತ್ತು ಒತ್ತಿಹಿಡಿಯಿರಿ."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"ಈ ಪರದೆಯನ್ನು ಅನ್‌ಪಿನ್ ಮಾಡಲು, ಹಿಂದಕ್ಕೆ ಮತ್ತು ಸಮಗ್ರ ನೋಟ ಬಟನ್‌ಗಳನ್ನು ಸ್ಪರ್ಶಿಸಿ ಒತ್ತಿಹಿಡಿಯಿರಿ"</string>
@@ -912,8 +915,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"<xliff:g id="APP_NAME">%1$s</xliff:g> ಅನ್ನು ತೆರೆಯಿರಿ"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"<xliff:g id="APP_NAME">%1$s</xliff:g> ಬಬಲ್‌ಗಳಿಗಾಗಿ ಸೆಟ್ಟಿಂಗ್‌ಗಳು"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"<xliff:g id="APP_NAME">%1$s</xliff:g> ಆ್ಯಪ್‌ನ ಬಬಲ್‌ಗಳನ್ನು ಅನುಮತಿಸುವುದೇ?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"ನಿರ್ವಹಿಸಿ"</string>
<string name="no_bubbles" msgid="337101288173078247">"ನಿರಾಕರಿಸಿ"</string>
<string name="yes_bubbles" msgid="668809525728633841">"ಅನುಮತಿಸಿ"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"ನನ್ನನ್ನು ಆನಂತರ ಕೇಳಿ"</string>
diff --git a/packages/SystemUI/res/values-ko/strings.xml b/packages/SystemUI/res/values-ko/strings.xml
index 12fcc2b3aedc..79ca42ebe4b1 100644
--- a/packages/SystemUI/res/values-ko/strings.xml
+++ b/packages/SystemUI/res/values-ko/strings.xml
@@ -223,7 +223,7 @@
<string name="accessibility_quick_settings_airplane_changed_off" msgid="66846307818850664">"비행기 모드가 사용 중지되었습니다."</string>
<string name="accessibility_quick_settings_airplane_changed_on" msgid="8983005603505087728">"비행기 모드를 사용합니다."</string>
<string name="accessibility_quick_settings_dnd_none_on" msgid="2960643943620637020">"모두 음소거"</string>
- <string name="accessibility_quick_settings_dnd_alarms_on" msgid="3357131899365865386">"알람만"</string>
+ <string name="accessibility_quick_settings_dnd_alarms_on" msgid="3357131899365865386">"알람만 허용"</string>
<string name="accessibility_quick_settings_dnd" msgid="5555155552520665891">"방해 금지 모드"</string>
<string name="accessibility_quick_settings_dnd_changed_off" msgid="2757071272328547807">"방해 금지 모드가 사용 중지되었습니다."</string>
<string name="accessibility_quick_settings_dnd_changed_on" msgid="6808220653747701059">"방해 금지 모드가 사용 설정되었습니다."</string>
@@ -292,8 +292,8 @@
<string name="ethernet_label" msgid="7967563676324087464">"이더넷"</string>
<string name="quick_settings_header_onboarding_text" msgid="8030309023792936283">"추가 옵션을 보려면 아이콘을 길게 터치하세요."</string>
<string name="quick_settings_dnd_label" msgid="7112342227663678739">"방해 금지 모드"</string>
- <string name="quick_settings_dnd_priority_label" msgid="483232950670692036">"중요 알림만"</string>
- <string name="quick_settings_dnd_alarms_label" msgid="2559229444312445858">"알람만"</string>
+ <string name="quick_settings_dnd_priority_label" msgid="483232950670692036">"중요 알림만 허용"</string>
+ <string name="quick_settings_dnd_alarms_label" msgid="2559229444312445858">"알람만 허용"</string>
<string name="quick_settings_dnd_none_label" msgid="5025477807123029478">"모두 차단"</string>
<string name="quick_settings_bluetooth_label" msgid="6304190285170721401">"블루투스"</string>
<string name="quick_settings_bluetooth_multiple_devices_label" msgid="3912245565613684735">"블루투스(<xliff:g id="NUMBER">%d</xliff:g>개의 기기)"</string>
@@ -399,8 +399,8 @@
<string name="camera_hint" msgid="7939688436797157483">"카메라를 사용하려면 아이콘에서 스와이프하세요."</string>
<string name="interruption_level_none_with_warning" msgid="5114872171614161084">"전체 무음입니다. 이렇게 하면 스크린 리더도 무음으로 설정됩니다."</string>
<string name="interruption_level_none" msgid="6000083681244492992">"모두 차단"</string>
- <string name="interruption_level_priority" msgid="6426766465363855505">"중요 알림만"</string>
- <string name="interruption_level_alarms" msgid="5226306993448328896">"알람만"</string>
+ <string name="interruption_level_priority" msgid="6426766465363855505">"중요 알림만 허용"</string>
+ <string name="interruption_level_alarms" msgid="5226306993448328896">"알람만 허용"</string>
<string name="interruption_level_none_twoline" msgid="3957581548190765889">"모두\n차단"</string>
<string name="interruption_level_priority_twoline" msgid="1564715335217164124">"중요 알림만\n허용"</string>
<string name="interruption_level_alarms_twoline" msgid="3266909566410106146">"알람만\n"</string>
@@ -448,6 +448,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"다시 표시 안함"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"모두 지우기"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"관리"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"방해 금지 모드로 일시중지된 알림"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"시작하기"</string>
<string name="empty_shade_text" msgid="708135716272867002">"알림 없음"</string>
@@ -527,8 +531,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"화면 고정됨"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"고정 해제할 때까지 계속 표시됩니다. 고정 해제하려면 뒤로 및 최근 사용을 길게 터치하세요."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"고정 해제할 때까지 계속 표시됩니다. 고정 해제하려면 뒤로 및 홈을 길게 터치하세요."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"고정 해제할 때까지 계속 표시됩니다. 고정 해제하려면 위로 스와이프한 다음 탭한 상태를 유지하세요."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"고정 해제할 때까지 계속 표시됩니다. 고정 해제하려면 최근 사용을 길게 터치하세요."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"고정 해제할 때까지 계속 표시됩니다. 고정 해제하려면 홈을 길게 터치하세요."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"이 화면을 고정 해제하려면 뒤로 및 최근 사용 버튼을 길게 터치하세요."</string>
@@ -912,8 +915,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"<xliff:g id="APP_NAME">%1$s</xliff:g> 열기"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"<xliff:g id="APP_NAME">%1$s</xliff:g> 알림 풍선 설정"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"<xliff:g id="APP_NAME">%1$s</xliff:g>의 알림 풍선을 허용하시겠습니까?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"관리"</string>
<string name="no_bubbles" msgid="337101288173078247">"거부"</string>
<string name="yes_bubbles" msgid="668809525728633841">"허용"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"나중에 알림"</string>
diff --git a/packages/SystemUI/res/values-ky/strings.xml b/packages/SystemUI/res/values-ky/strings.xml
index 48ae1226c5a1..2b589e202522 100644
--- a/packages/SystemUI/res/values-ky/strings.xml
+++ b/packages/SystemUI/res/values-ky/strings.xml
@@ -448,6 +448,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"Экинчи көрсөтүлбөсүн"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"Бардыгын тазалап салуу"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"Башкаруу"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"\"Тынчымды алба\" режиминде билдирмелер тындырылды"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"Азыр баштоо"</string>
<string name="empty_shade_text" msgid="708135716272867002">"Билдирме жок"</string>
@@ -527,8 +531,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"Экран кадалган"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"Ал бошотулмайынча көрүнө берет. Бошотуу үчүн, \"Артка\" жана \"Карап чыгуу\" баскычтарын басып, кармап туруңуз."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"Ал бошотулмайынча көрүнө берет. Бошотуу үчүн, \"Артка\" жана \"Башкы бет\" баскычтарын басып, кармап туруңуз."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"Ал бошотулмайынча көрүнө берет. Бошотуу үчүн өйдө сүрүп, коё бербей басып туруңуз."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"Ал бошотулмайынча көрүнө берет. Бошотуу үчүн, \"Карап чыгуу\" баскычын басып, кармап туруңуз."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"Ал бошотулмайынча көрүнө берет. Бошотуу үчүн, \"Башкы бет\" баскычын басып, кармап туруңуз."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"Бул экранды бошотуу үчүн \"Артка\" жана \"Сереп салуу\" баскычтарын басып, кармап туруңуз"</string>
@@ -622,7 +625,7 @@
<string name="notification_channel_disabled" msgid="344536703863700565">"Мындан ары бул эскертмелер сизге көрсөтүлбөйт"</string>
<string name="notification_channel_minimized" msgid="1664411570378910931">"Бул эскертмелер кичирейтилет"</string>
<string name="notification_channel_silenced" msgid="2877199534497961942">"Бул билдирмелер үнсүз көрсөтүлөт"</string>
- <string name="notification_channel_unsilenced" msgid="4790904571552394137">"Бул билдирмелер үн менен эскертилет"</string>
+ <string name="notification_channel_unsilenced" msgid="4790904571552394137">"Бул билдирмелер тууралуу кабарлап турабыз"</string>
<string name="inline_blocking_helper" msgid="3055064577771478591">"Адатта мындай эскертмелерди өткөрүп жибересиз. \nАлар көрсөтүлө берсинби?"</string>
<string name="inline_done_button" msgid="492513001558716452">"Бүттү"</string>
<string name="inline_ok_button" msgid="975600017662930615">"Колдонуу"</string>
@@ -764,8 +767,8 @@
<string name="accessibility_key" msgid="5701989859305675896">"Ыңгайлаштырылган чабыттоо баскычы"</string>
<string name="left_keycode" msgid="2010948862498918135">"Сол жактагы баскыч коду"</string>
<string name="right_keycode" msgid="708447961000848163">"Оң жактагы баскыч коду"</string>
- <string name="left_icon" msgid="3096287125959387541">"Сол жактагы сүрөтчө"</string>
- <string name="right_icon" msgid="3952104823293824311">"Оң жактагы сүрөтчө"</string>
+ <string name="left_icon" msgid="3096287125959387541">"¨Солго¨ сүрөтчөсү"</string>
+ <string name="right_icon" msgid="3952104823293824311">"¨Оңго¨ сүрөтчөсү"</string>
<string name="drag_to_add_tiles" msgid="230586591689084925">"Керектүү элементтерди сүйрөп келиңиз"</string>
<string name="drag_to_rearrange_tiles" msgid="4566074720193667473">"Элементтердин иретин өзгөртүү үчүн кармап туруп, сүйрөңүз"</string>
<string name="drag_to_remove_tiles" msgid="3361212377437088062">"Алып салуу үчүн бул жерге сүйрөңүз"</string>
@@ -775,12 +778,12 @@
<string-array name="clock_options">
<item msgid="5965318737560463480">"Сааттар, мүнөттөр жана секунддар"</item>
<item msgid="1427801730816895300">"Сааттар жана мүнөттөр (демейки шартта)"</item>
- <item msgid="3830170141562534721">"Бул сөлөкөт көрсөтүлбөсүн"</item>
+ <item msgid="3830170141562534721">"Бул сүрөтчө көрсөтүлбөсүн"</item>
</string-array>
<string-array name="battery_options">
<item msgid="3160236755818672034">"Ар дайым пайызы көрсөтүлсүн"</item>
<item msgid="2139628951880142927">"Кубаттоо учурунда пайызы көрсөтүлсүн (демейки)"</item>
- <item msgid="3327323682209964956">"Бул сөлөкөт көрсөтүлбөсүн"</item>
+ <item msgid="3327323682209964956">"Бул сүрөтчө көрсөтүлбөсүн"</item>
</string-array>
<string name="tuner_low_priority" msgid="1325884786608312358">"Анча маанилүү эмес билдирменин сүрөтчөлөрүн көрсөтүү"</string>
<string name="other" msgid="4060683095962566764">"Башка"</string>
@@ -854,7 +857,7 @@
<string name="tuner_right" msgid="6222734772467850156">"Оңго"</string>
<string name="tuner_menu" msgid="191640047241552081">"Меню"</string>
<string name="tuner_app" msgid="3507057938640108777">"<xliff:g id="APP">%1$s</xliff:g> колдонмосу"</string>
- <string name="notification_channel_alerts" msgid="4496839309318519037">"Эскертүүлөр"</string>
+ <string name="notification_channel_alerts" msgid="4496839309318519037">"Шашылыш билдирүүлөр"</string>
<string name="notification_channel_battery" msgid="5786118169182888462">"Батарея"</string>
<string name="notification_channel_screenshot" msgid="6314080179230000938">"Скриншоттор"</string>
<string name="notification_channel_general" msgid="4525309436693914482">"Жалпы билдирүүлөр"</string>
@@ -880,8 +883,8 @@
<string name="qs_dnd_replace" msgid="8019520786644276623">"Алмаштыруу"</string>
<string name="running_foreground_services_title" msgid="381024150898615683">"Фондо иштеп жаткан колдонмолор"</string>
<string name="running_foreground_services_msg" msgid="6326247670075574355">"Батареянын кубаты жана трафиктин көлөмү жөнүндө билүү үчүн таптап коюңуз"</string>
- <string name="mobile_data_disable_title" msgid="1068272097382942231">"Мобилдик Интернет өчүрүлсүнбү?"</string>
- <string name="mobile_data_disable_message" msgid="4756541658791493506">"<xliff:g id="CARRIER">%s</xliff:g> байланыш оператору аркылуу дайындарга же Интернетке кирүү мүмкүнчүлүгүңүз болбойт. Интернетке Wi-Fi аркылуу гана кирүү мүмкүн."</string>
+ <string name="mobile_data_disable_title" msgid="1068272097382942231">"Мобилдик Интернетти өчүрөсүзбү?"</string>
+ <string name="mobile_data_disable_message" msgid="4756541658791493506">"<xliff:g id="CARRIER">%s</xliff:g> байланыш оператору аркылуу дайындарга же Интернетке кирүү мүмкүнчүлүгүңүз болбойт. Интернетке Wi-Fi аркылуу гана кире аласыз."</string>
<string name="mobile_data_disable_message_default_carrier" msgid="6078110473451946831">"байланыш операторуңуз"</string>
<string name="touch_filtered_warning" msgid="8671693809204767551">"Уруксат берүү сурамыңыз көрүнбөй калгандыктан, Жөндөөлөр жообуңузду ырастай албай жатат."</string>
<string name="slice_permission_title" msgid="7465009437851044444">"<xliff:g id="APP_0">%1$s</xliff:g> колдонмосуна <xliff:g id="APP_2">%2$s</xliff:g> үлгүлөрүн көрсөтүүгө уруксат берилсинби?"</string>
@@ -911,9 +914,8 @@
<string name="restart_button_description" msgid="2035077840254950187">"Бул колдонмону өчүрүп күйгүзүп, толук экранга өтүү үчүн таптап коюңуз."</string>
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"<xliff:g id="APP_NAME">%1$s</xliff:g> колдонмосун ачуу"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"<xliff:g id="APP_NAME">%1$s</xliff:g> көбүктөрүнүн жөндөөлөрү"</string>
- <string name="bubbles_prompt" msgid="8807968030159469710">"<xliff:g id="APP_NAME">%1$s</xliff:g> колдонмосунун көбүктөрүнө уруксат берилсинби?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="bubbles_prompt" msgid="8807968030159469710">"<xliff:g id="APP_NAME">%1$s</xliff:g> колдонмосунун калкып чыкма билдирмелерине уруксат бересизби?"</string>
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"Башкаруу"</string>
<string name="no_bubbles" msgid="337101288173078247">"Жок"</string>
<string name="yes_bubbles" msgid="668809525728633841">"Уруксат берүү"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"Кийинчерээк суралсын"</string>
diff --git a/packages/SystemUI/res/values-lo/strings.xml b/packages/SystemUI/res/values-lo/strings.xml
index a3a458a2bf6d..999472910b9e 100644
--- a/packages/SystemUI/res/values-lo/strings.xml
+++ b/packages/SystemUI/res/values-lo/strings.xml
@@ -448,6 +448,8 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"ບໍ່​ຕ້ອງ​ສະ​ແດງ​ອີກ"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"ລຶບລ້າງທັງໝົດ"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"ຈັດການ"</string>
+ <string name="notification_section_header_gentle" msgid="8356064473678167305">"ການແຈ້ງເຕືອນສຸພາບ"</string>
+ <string name="accessibility_notification_section_header_gentle_clear_all" msgid="4270384919249494640">"ລຶບລ້າງການແຈ້ງເຕືອນແບບສຸພາບ"</string>
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"ຢຸດການແຈ້ງເຕືອນໂດຍໂໝດຫ້າມລົບກວນແລ້ວ"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"ເລີ່ມດຽວນີ້"</string>
<string name="empty_shade_text" msgid="708135716272867002">"ບໍ່ມີການແຈ້ງເຕືອນ"</string>
@@ -527,8 +529,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"ປັກ​ໝຸດໜ້າ​ຈໍ​ແລ້ວ"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"ນີ້ຈະສະແດງມັນໃນໜ້າຈໍຈົນກວ່າທ່ານຈະເຊົາປັກມຸດ. ໃຫ້ແຕະປຸ່ມກັບຄືນ ແລະ ປຸ່ມພາບຮວມຄ້າງໄວ້ເພື່ອຍົກເລີກການປັກມຸດ."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"ນີ້ຈະສະແດງມັນໃນໜ້າຈໍຈົນກວ່າທ່ານຈະເຊົາປັກໝຸດ. ໃຫ້ແຕະປຸ່ມກັບຄືນ ແລະ ປຸ່ມພາບຮວມຄ້າງໄວ້ເພື່ອຍົກເລີກການປັກໝຸດ."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"ນີ້ຈະເຮັດໃຫ້ມັນຢູ່ໃນມຸມມອງຈົນກວ່າທ່ານຈະເຊົາປັກໝຸດ. ປັດຂຶ້ນຄ້າງໄວ້ເພື່ອເຊົາປັກໝຸດ."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"ນີ້ຈະສະແດງມັນໃນໜ້າຈໍຈົນກວ່າທ່ານຈະເຊົາປັກມຸດ. ໃຫ້ແຕະປຸ່ມພາບຮວມຄ້າງໄວ້ເພື່ອຍົກເລີກການປັກມຸດ."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"ນີ້ຈະສະແດງມັນໃນໜ້າຈໍຈົນກວ່າທ່ານຈະເຊົາປັກໝຸດ. ໃຫ້ແຕະປຸ່ມພາບຮວມຄ້າງໄວ້ເພື່ອຍົກເລີກການປັກໝຸດ."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"ເພື່ອຍົກເລີກການປັກໝຸດໜ້າຈໍນີ້, ໃຫ້ແຕະປຸ່ມກັບຄືນ ແລະ ປຸ່ມພາບຮວມຄ້າງໄວ້"</string>
@@ -912,8 +913,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"ເປີດ <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"ການຕັ້ງຄ່າສຳລັບ bubble <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"ອະນຸຍາດໃຫ້ມີ bubbles ຈາກ <xliff:g id="APP_NAME">%1$s</xliff:g> ບໍ?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"ຈັດການ"</string>
<string name="no_bubbles" msgid="337101288173078247">"ປະຕິເສດ"</string>
<string name="yes_bubbles" msgid="668809525728633841">"ອະນຸຍາດ"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"ຖາມຂ້ອຍໃນພາຍຫຼັງ"</string>
diff --git a/packages/SystemUI/res/values-lt/strings.xml b/packages/SystemUI/res/values-lt/strings.xml
index 5f846231ca49..e8cda2a21c53 100644
--- a/packages/SystemUI/res/values-lt/strings.xml
+++ b/packages/SystemUI/res/values-lt/strings.xml
@@ -454,6 +454,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"Daugiau neberodyti"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"Viską išvalyti"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"Tvarkyti"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"Pranešimai pristabdyti naudojant netrukdymo režimą"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"Pradėti dabar"</string>
<string name="empty_shade_text" msgid="708135716272867002">"Nėra įspėjimų"</string>
@@ -922,8 +926,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"Atidaryti „<xliff:g id="APP_NAME">%1$s</xliff:g>“"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"„<xliff:g id="APP_NAME">%1$s</xliff:g>“ debesėlių nustatymai"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"Leisti programos „<xliff:g id="APP_NAME">%1$s</xliff:g>“ debesėlius?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"Tvarkyti"</string>
<string name="no_bubbles" msgid="337101288173078247">"Atmesti"</string>
<string name="yes_bubbles" msgid="668809525728633841">"Leisti"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"Paklausti vėliau"</string>
diff --git a/packages/SystemUI/res/values-lv/strings.xml b/packages/SystemUI/res/values-lv/strings.xml
index 72e22e25031d..b2bcbb09a6e7 100644
--- a/packages/SystemUI/res/values-lv/strings.xml
+++ b/packages/SystemUI/res/values-lv/strings.xml
@@ -451,6 +451,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"Vairs nerādīt"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"Dzēst visu"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"Pārvaldīt"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"Paziņojumi pārtraukti, izmantojot iestatījumu “Netraucēt”"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"Sākt tūlīt"</string>
<string name="empty_shade_text" msgid="708135716272867002">"Nav paziņojumu"</string>
@@ -530,8 +534,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"Ekrāns ir piesprausts"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"Šādi tas būs redzams līdz brīdim, kad to atspraudīsiet. Lai atspraustu, pieskarieties pogām Atpakaļ un Pārskats un turiet tās."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"Šādi tas būs redzams līdz brīdim, kad to atspraudīsiet. Lai atspraustu, pieskarieties pogām “Atpakaļ” un “Sākums” un turiet tās."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"Šādi tas būs redzams līdz brīdim, kad to atspraudīsiet. Velciet augšup un turiet to, lai atspraustu."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"Šādi tas būs redzams līdz brīdim, kad to atspraudīsiet. Lai atspraustu, pieskarieties pogai Pārskats un turiet to."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"Šādi tas būs redzams līdz brīdim, kad to atspraudīsiet. Lai atspraustu, pieskarieties pogai “Sākums” un turiet to."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"Lai atspraustu šo ekrānu, pieskarieties pogām “Atpakaļ” un “Pārskats” un turiet tās."</string>
@@ -917,8 +920,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"Atvērt lietotni <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"Lietotnes <xliff:g id="APP_NAME">%1$s</xliff:g> burbuļu iestatījumi"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"Vai atļaut burbuļus no lietotnes <xliff:g id="APP_NAME">%1$s</xliff:g>?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"Pārvaldīt"</string>
<string name="no_bubbles" msgid="337101288173078247">"Neatļaut"</string>
<string name="yes_bubbles" msgid="668809525728633841">"Atļaut"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"Pajautāt vēlāk"</string>
diff --git a/packages/SystemUI/res/values-mk/strings.xml b/packages/SystemUI/res/values-mk/strings.xml
index e916a6a8b16b..bfeaf3d3925e 100644
--- a/packages/SystemUI/res/values-mk/strings.xml
+++ b/packages/SystemUI/res/values-mk/strings.xml
@@ -448,6 +448,8 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"Не покажувај повторно"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"Исчисти сè"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"Управувајте"</string>
+ <string name="notification_section_header_gentle" msgid="8356064473678167305">"Нежни известувања"</string>
+ <string name="accessibility_notification_section_header_gentle_clear_all" msgid="4270384919249494640">"Исчисти ги сите тивки известувања"</string>
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"Известувањата се паузирани од „Не вознемирувај“"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"Започни сега"</string>
<string name="empty_shade_text" msgid="708135716272867002">"Нема известувања"</string>
@@ -527,8 +529,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"Екранот е прикачен"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"Ќе се гледа сѐ додека не го откачите. Допрете и држете „Назад“ и „Краток преглед“ за откачување."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"Ќе се гледа сѐ додека не го откачите. Допрете и задржете „Назад“ и „Почетен екран“ за откачување."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"Ќе се гледа сѐ додека не го откачите. Лизгајте нагоре и задржете за откачување."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"Ќе се гледа сѐ додека не го откачите. Допрете и држете „Краток преглед“ за откачување."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"Ќе се гледа сѐ додека не го откачите. Допрете и задржете „Почетен екран“ за откачување."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"За откачување на екранов, допрете и задржете ги копчињата „Назад“ и „Краток преглед“"</string>
@@ -912,8 +913,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"Отворете ја <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"Поставки за баланчињата на <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"Да се дозволат балончиња од <xliff:g id="APP_NAME">%1$s</xliff:g>?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"Управување"</string>
<string name="no_bubbles" msgid="337101288173078247">"Одбиј"</string>
<string name="yes_bubbles" msgid="668809525728633841">"Дозволи"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"Прашај ме подоцна"</string>
diff --git a/packages/SystemUI/res/values-ml/strings.xml b/packages/SystemUI/res/values-ml/strings.xml
index d23a973c47c2..be7ae17c8daa 100644
--- a/packages/SystemUI/res/values-ml/strings.xml
+++ b/packages/SystemUI/res/values-ml/strings.xml
@@ -307,7 +307,7 @@
<string name="quick_settings_bluetooth_secondary_label_transient" msgid="4551281899312150640">"ഓണാക്കുന്നു…"</string>
<string name="quick_settings_brightness_label" msgid="6968372297018755815">"തെളിച്ചം"</string>
<string name="quick_settings_rotation_unlocked_label" msgid="7305323031808150099">"സ്‌ക്രീൻ സ്വയമേവ തിരിയുക"</string>
- <string name="accessibility_quick_settings_rotation" msgid="4231661040698488779">"സ്‌ക്രീൻ സ്വയമേ തിരിക്കുക"</string>
+ <string name="accessibility_quick_settings_rotation" msgid="4231661040698488779">"സ്‌ക്രീൻ സ്വയമേവ തിരിക്കുക"</string>
<string name="accessibility_quick_settings_rotation_value" msgid="8187398200140760213">"<xliff:g id="ID_1">%s</xliff:g> മോഡ്"</string>
<string name="quick_settings_rotation_locked_label" msgid="6359205706154282377">"റൊട്ടേഷൻ ലോക്കുചെയ്‌തു"</string>
<string name="quick_settings_rotation_locked_portrait_label" msgid="5102691921442135053">"പോർട്രെയ്‌റ്റ്"</string>
@@ -448,6 +448,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"വീണ്ടും കാണിക്കരുത്"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"എല്ലാം മായ്‌ക്കുക"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"മാനേജ് ചെയ്യുക"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"\'ശല്യപ്പെടുത്തരുത്\' വഴി അറിയിപ്പുകൾ താൽക്കാലികമായി നിർത്തി"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"ഇപ്പോൾ ആരംഭിക്കുക"</string>
<string name="empty_shade_text" msgid="708135716272867002">"അറിയിപ്പുകൾ ഒന്നുമില്ല"</string>
@@ -527,8 +531,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"സ്‌ക്രീൻ പിൻ ചെയ്‌തു"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"നിങ്ങൾ അൺപിൻ ചെയ്യുന്നതുവരെ ഇത് കാണുന്ന വിധത്തിൽ നിലനിർത്തും. അൺപിൻ ചെയ്യാൻ \'തിരികെ\', \'ചുരുക്കവിവരണം\' എന്നിവ സ്‌പർശിച്ച് പിടിക്കുക."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"നിങ്ങൾ അൺപിൻ ചെയ്യുന്നതുവരെ ഇത് കാണുന്ന വിധത്തിൽ നിലനിർത്തും. അൺപിൻ ചെയ്യാൻ \'തിരികെ പോവുക\', \'ഹോം\' ബട്ടണുകൾ സ്‌പർശിച്ച് പിടിക്കുക."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"നിങ്ങൾ അൺപിൻ ചെയ്യുന്നതുവരെ ഇത് കാണുന്ന വിധത്തിൽ നിലനിർത്തും. അൺപിൻ ചെയ്യാൻ മുകളിലേക്ക് സ്വൈപ്പ് ചെയ്‌ത് പിടിക്കുക."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"നിങ്ങൾ അൺപിൻ ചെയ്യുന്നതുവരെ ഇത് കാണുന്ന വിധത്തിൽ നിലനിർത്തും. അൺപിൻ ചെയ്യാൻ \'ചുരുക്കവിവരണം\' സ്‌പർശിച്ച് പിടിക്കുക."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"നിങ്ങൾ അൺപിൻ ചെയ്യുന്നതുവരെ ഇത് കാണുന്ന വിധത്തിൽ നിലനിർത്തും. അൺപിൻ ചെയ്യാൻ \'ഹോം\' ബട്ടൺ സ്‌പർശിച്ച് പിടിക്കുക."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"ഈ സ്‌ക്രീൻ അൺപിൻ ചെയ്യാൻ, \'തിരികെ പോവുക\', \'അവലോകനം\' ബട്ടണുകൾ സ്‌പർശിച്ച് പിടിക്കുക"</string>
@@ -713,7 +716,7 @@
<string name="keyboard_shortcut_group_system_recents" msgid="3154851905021926744">"പുതിയവ"</string>
<string name="keyboard_shortcut_group_system_back" msgid="2207004531216446378">"മടങ്ങുക"</string>
<string name="keyboard_shortcut_group_system_notifications" msgid="8366964080041773224">"അറിയിപ്പുകൾ"</string>
- <string name="keyboard_shortcut_group_system_shortcuts_helper" msgid="4892255911160332762">"കീബോഡ് കുറുക്കുവഴികൾ"</string>
+ <string name="keyboard_shortcut_group_system_shortcuts_helper" msgid="4892255911160332762">"കീബോർഡ് കുറുക്കുവഴികൾ"</string>
<string name="keyboard_shortcut_group_system_switch_input" msgid="8413348767825486492">"കീബോർഡ് ലേഔട്ട് മാറുക"</string>
<string name="keyboard_shortcut_group_applications" msgid="9129465955073449206">"അപ്ലിക്കേഷനുകൾ"</string>
<string name="keyboard_shortcut_group_applications_assist" msgid="9095441910537146013">"അസിസ്റ്റ്"</string>
@@ -912,8 +915,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"<xliff:g id="APP_NAME">%1$s</xliff:g> തുറക്കുക"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"<xliff:g id="APP_NAME">%1$s</xliff:g> എന്നതിനുള്ള ബബിളുകളുടെ ക്രമീകരണം"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"<xliff:g id="APP_NAME">%1$s</xliff:g>-ൽ നിന്നും ബബിളുകളെ അനുവദിക്കണോ?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"മാനേജ് ചെയ്യുക"</string>
<string name="no_bubbles" msgid="337101288173078247">"നിരസിക്കുക"</string>
<string name="yes_bubbles" msgid="668809525728633841">"അനുവദിക്കുക"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"എന്നോട് പിന്നീട് ചോദിക്കുക"</string>
diff --git a/packages/SystemUI/res/values-mn/strings.xml b/packages/SystemUI/res/values-mn/strings.xml
index cb743d46dafa..3a6943aa46bf 100644
--- a/packages/SystemUI/res/values-mn/strings.xml
+++ b/packages/SystemUI/res/values-mn/strings.xml
@@ -448,6 +448,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"Дахиж үл харуулах"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"Бүгдийг арилгах"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"Удирдах"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"Бүү саад бол горимын түр зогсоосон мэдэгдэл"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"Одоо эхлүүлэх"</string>
<string name="empty_shade_text" msgid="708135716272867002">"Мэдэгдэл байхгүй"</string>
@@ -527,8 +531,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"Дэлгэц эхэнд байрлуулагдсан"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"Таныг тогтоосныг болиулах хүртэл үүнийг харуулна. Тогтоосныг болиулахын тулд Буцах, Тоймыг дараад хүлээнэ үү."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"Таныг тогтоосныг болиулах хүртэл үүнийг харуулсан хэвээр байна. Тогтоосныг болиулахын тулд Буцах, Нүүр хуудас товчлуурыг дараад хүлээнэ үү."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"Та тогтоосныг болиулах хүртэл үүнийг харуулсан хэвээр байна. Тогтоосныг болиулахын тулд дээш удаан шударна уу."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"Таныг тогтоосныг болиулах хүртэл харагдах болно. Тогтоосныг болиулахын тулд Буцах товчлуурыг дараад, хүлээнэ үү."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"Таныг тогтоосныг болиулах хүртэл үүнийг харуулсан хэвээр байна. Тогтоосныг болиулахын тулд Нүүр хуудас товчлуурыг дараад хүлээнэ үү."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"Энэ дэлгэцийг тогтоосныг болиулахын тулд Буцах, Тойм товчлуурыг дараад хүлээнэ үү"</string>
@@ -639,7 +642,7 @@
<string name="inline_turn_off_notifications" msgid="8635596135532202355">"Мэдэгдлийг унтраах"</string>
<string name="inline_keep_showing_app" msgid="1723113469580031041">"Энэ аппаас мэдэгдэл харуулсан хэвээр байх уу?"</string>
<string name="notification_silence_title" msgid="7352089096356977930">"Бага ач холбогдолтой"</string>
- <string name="notification_alert_title" msgid="3966526305405016221">"Дунд зэргийн ач холбогдолтой"</string>
+ <string name="notification_alert_title" msgid="3966526305405016221">"Чухал ач холбогдолтой"</string>
<string name="notification_channel_summary_low" msgid="1065819618107531284">"Танд зөвхөн доош татдаг сүүдрийн мэдэгдлээр төвлөрөхөд тусалдаг. Үргэлж чимээгүй байна."</string>
<string name="notification_channel_summary_low_status" msgid="2702170424808743755">"Доорх ач холбогдолтой мэдэгдлийг харуулдаг. Үргэлж чимээгүй байна."</string>
<string name="notification_channel_summary_low_lock" msgid="7966605244472624458">"Доорх ач холбогдолтой мэдэгдлийг харуулдаг. Үргэлж чимээгүй байна."</string>
@@ -912,8 +915,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"<xliff:g id="APP_NAME">%1$s</xliff:g>-г нээх"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"<xliff:g id="APP_NAME">%1$s</xliff:g>-н хөөсний тохиргоо"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"<xliff:g id="APP_NAME">%1$s</xliff:g>-н хөөсийг зөвшөөрөх үү?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"Удирдах"</string>
<string name="no_bubbles" msgid="337101288173078247">"Татгалзах"</string>
<string name="yes_bubbles" msgid="668809525728633841">"Зөвшөөрөх"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"Надаас дараа асуу"</string>
diff --git a/packages/SystemUI/res/values-mr/strings.xml b/packages/SystemUI/res/values-mr/strings.xml
index 22db427502d6..84d701b5e06c 100644
--- a/packages/SystemUI/res/values-mr/strings.xml
+++ b/packages/SystemUI/res/values-mr/strings.xml
@@ -338,7 +338,7 @@
<string name="quick_settings_cast_no_wifi" msgid="2696477881905521882">"वाय-फाय कनेक्ट केलेले नाही"</string>
<string name="quick_settings_brightness_dialog_title" msgid="8599674057673605368">"चमक"</string>
<string name="quick_settings_brightness_dialog_auto_brightness_label" msgid="5064982743784071218">"स्वयंचलित"</string>
- <string name="quick_settings_inversion_label" msgid="8790919884718619648">"रंगांचा क्रम उलटा लावा"</string>
+ <string name="quick_settings_inversion_label" msgid="8790919884718619648">"रंग उलटे लावा"</string>
<string name="quick_settings_color_space_label" msgid="853443689745584770">"रंग सुधारणा मोड"</string>
<string name="quick_settings_more_settings" msgid="326112621462813682">"अधिक सेटिंग्ज"</string>
<string name="quick_settings_done" msgid="3402999958839153376">"पूर्ण झाले"</string>
@@ -448,6 +448,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"पुन्हा दर्शवू नका"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"सर्व साफ करा"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"व्यवस्थापित करा"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"व्यत्यय आणून नकाद्वारे सूचना थांबवल्या"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"आता सुरू करा"</string>
<string name="empty_shade_text" msgid="708135716272867002">"सूचना नाहीत"</string>
@@ -527,8 +531,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"स्क्रीन पिन केलेली आहे"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"तुम्ही अनपिन करेर्यंत हे यास दृश्यामध्ये ठेवते. अनपिन करण्‍यासाठी परत आणि विहंगावलोकनास स्पर्श करा आणि धरून ठेवा."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"तुम्ही अनपिन करेर्यंत हे त्याला दृश्यामध्ये ठेवते. अनपिन करण्‍यासाठी मागे आणि होम वर स्पर्श करा आणि धरून ठेवा."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"हे तुम्ही अनपिन करेपर्यंत दृश्यमान ठेवते. वरती स्‍वाइप करा आणि अनपिन करण्यासाठी धरून ठेवा."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"तुम्ही अनपिन करेर्यंत हे यास दृश्यामध्ये ठेवते. अनपिन करण्‍यासाठी विहंगावलोकनास स्पर्श करा आणि धरून ठेवा."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"तुम्ही अनपिन करेपर्यंत हे त्यास दृश्यामध्ये ठेवते. अनपिन करण्यासाठी होमला स्पर्श करा आणि धरून ठेवा."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"हा स्क्रीन अनपिन करण्यासाठी, मागे आणि अवलोकन बटणांना स्पर्श करून धरून ठेवा"</string>
@@ -734,9 +737,9 @@
<string name="accessibility_long_click_tile" msgid="6687350750091842525">"सेटिंग्ज उघडा"</string>
<string name="accessibility_status_bar_headphones" msgid="9156307120060559989">"हेडफोन कनेक्ट केले"</string>
<string name="accessibility_status_bar_headset" msgid="8666419213072449202">"हेडसेट कनेक्ट केला"</string>
- <string name="data_saver" msgid="5037565123367048522">"डेटा बचतकर्ता"</string>
- <string name="accessibility_data_saver_on" msgid="8454111686783887148">"डेटा बचतकर्ता चालू आहे"</string>
- <string name="accessibility_data_saver_off" msgid="8841582529453005337">"डेटा बचतकर्ता बंद आहे"</string>
+ <string name="data_saver" msgid="5037565123367048522">"डेटा सेव्हर"</string>
+ <string name="accessibility_data_saver_on" msgid="8454111686783887148">"डेटा सेव्हर चालू आहे"</string>
+ <string name="accessibility_data_saver_off" msgid="8841582529453005337">"डेटा सेव्हर बंद आहे"</string>
<string name="switch_bar_on" msgid="1142437840752794229">"चालू"</string>
<string name="switch_bar_off" msgid="8803270596930432874">"बंद"</string>
<string name="nav_bar" msgid="1993221402773877607">"नॅव्हिगेशन बार"</string>
@@ -912,8 +915,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"<xliff:g id="APP_NAME">%1$s</xliff:g> उघडा"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"<xliff:g id="APP_NAME">%1$s</xliff:g> बबलसाठी सेटिंग्ज"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"<xliff:g id="APP_NAME">%1$s</xliff:g> वरील बबलना अनुमती द्यायची?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"व्यवस्थापित करा"</string>
<string name="no_bubbles" msgid="337101288173078247">"नाकारा"</string>
<string name="yes_bubbles" msgid="668809525728633841">"अनुमती द्या"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"मला नंतर विचारा"</string>
diff --git a/packages/SystemUI/res/values-ms/strings.xml b/packages/SystemUI/res/values-ms/strings.xml
index 267cd89edd69..c95310033250 100644
--- a/packages/SystemUI/res/values-ms/strings.xml
+++ b/packages/SystemUI/res/values-ms/strings.xml
@@ -448,6 +448,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"Jangan tunjukkan lagi"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"Kosongkan semua"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"Urus"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"Pemberitahuan dijeda oleh Jangan Ganggu"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"Mulakan sekarang"</string>
<string name="empty_shade_text" msgid="708135716272867002">"Tiada pemberitahuan"</string>
@@ -527,8 +531,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"Skrin telah disemat"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"Tindakan ini memastikan skrin kelihatan sehingga anda menyahsemat. Sentuh &amp; tahan Kembali dan Ikhtisar untuk menyahsemat."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"Tindakan ini memastikan skrin kelihatan sehingga anda menyahsemat. Sentuh &amp; tahan Kembali dan Skrin Utama untuk menyahsemat."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"Tindakan ini memastikan skrin kelihatan sehingga anda menyahsemat. Leret ke atas &amp; tahan untuk menyahsemat."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"Tindakan ini memastikan skrin kelihatan sehingga anda menyahsemat. Sentuh &amp; tahan Ikhtisar untuk menyahsemat."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"Tindakan ini memastikan skrin kelihatan sehingga anda menyahsemat. Sentuh &amp; tahan Skrin Utama untuk menyahsemat."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"Untuk menyahsemat skrin ini, sentuh &amp; tahan butang Kembali dan Ikhtisar"</string>
@@ -912,8 +915,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"Buka <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"Tetapan untuk gelembung <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"Benarkan gelembung daripada <xliff:g id="APP_NAME">%1$s</xliff:g>?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"Urus"</string>
<string name="no_bubbles" msgid="337101288173078247">"Tolak"</string>
<string name="yes_bubbles" msgid="668809525728633841">"Benarkan"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"Tanya saya kemudian"</string>
diff --git a/packages/SystemUI/res/values-my/strings.xml b/packages/SystemUI/res/values-my/strings.xml
index 27c1d68871b8..4c1b8b18b3ba 100644
--- a/packages/SystemUI/res/values-my/strings.xml
+++ b/packages/SystemUI/res/values-my/strings.xml
@@ -448,6 +448,8 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"နောက်ထပ် မပြပါနှင့်"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"အားလုံး ဖယ်ရှားရန်"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"စီမံရန်"</string>
+ <string name="notification_section_header_gentle" msgid="8356064473678167305">"မသိမသာ အကြောင်းကြားချက်များ"</string>
+ <string name="accessibility_notification_section_header_gentle_clear_all" msgid="4270384919249494640">"မသိမသာ အကြောင်းကြားချက်အားလုံး ရှင်းပါ"</string>
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"အကြောင်းကြားချက်များကို \'မနှောင့်ယှက်ရ\' က ခေတ္တရပ်ထားသည်"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"ယခု စတင်ပါ"</string>
<string name="empty_shade_text" msgid="708135716272867002">"အကြောင်းကြားချက်များ မရှိ"</string>
@@ -527,8 +529,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"မျက်နှာပြင် ပင်ထိုးပြီးပါပြီ"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"သင်ပင်မဖြုတ်မခြင်း ၎င်းကို ပြသထားပါမည်။ ပင်ဖြုတ်ရန် Back နှင့် Overview ကို ထိ၍ဖိထားပါ။"</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"သင်က ပင်မဖြုတ်မခြင်း ၎င်းကို ပြသထားပါမည်။ ပင်ဖြုတ်ရန် \'နောက်သို့\' နှင့် \'ပင်မ\' ခလုတ်တို့ကို တို့၍ဖိထားပါ။"</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"သင်က ပင်မဖြုတ်မချင်း ၎င်းကို ပြသထားပါမည်။ ပင်ဖြုတ်ရန် အပေါ်သို့ပွတ်ဆွဲပြီး ဖိထားပါ။"</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"သင်ပင်မဖြုတ်မချင်း ၎င်းကိုပြသထားပါမည်။ ပင်ဖြုတ်ရန် Overview ကိုထိပြီး ဖိထားပါ။"</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"သင်က ပင်မဖြုတ်မချင်း ၎င်းကိုပြသထားပါမည်။ ပင်ဖြုတ်ရန် \'ပင်မ\' ခလုတ်ကို တို့၍ဖိထားပါ။"</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"ဤမျက်နှာပြင်ကို ပင်ဖြုတ်ရန်အတွက် \'နောက်သို့\' နှင့် \'အနှစ်ချုပ်\' ခလုတ်တို့ကို တို့၍ဖိထားပါ"</string>
@@ -881,7 +882,7 @@
<string name="running_foreground_services_title" msgid="381024150898615683">"နောက်ခံတွင် ပွင့်နေသော အက်ပ်များ"</string>
<string name="running_foreground_services_msg" msgid="6326247670075574355">"ဘက်ထရီနှင့် ဒေတာအသုံးပြုမှု အသေးစိတ်ကို ကြည့်ရန် တို့ပါ"</string>
<string name="mobile_data_disable_title" msgid="1068272097382942231">"မိုဘိုင်းဒေတာ ပိတ်လိုပါသလား။"</string>
- <string name="mobile_data_disable_message" msgid="4756541658791493506">"<xliff:g id="CARRIER">%s</xliff:g> မှ ဒေတာ သို့မဟုတ် အင်တာနက်ကို သုံးစွဲ၍ မရနိုင်ပါ။ Wi-Fi အသုံးပြု၍သာ အင်တာနက် သုံးစွဲနိုင်ပါသည်။"</string>
+ <string name="mobile_data_disable_message" msgid="4756541658791493506">"<xliff:g id="CARRIER">%s</xliff:g> မှတစ်ဆင့် ဒေတာ သို့မဟုတ် အင်တာနက်ကို သုံးစွဲ၍ မရနိုင်ပါ။ Wi-Fi အသုံးပြု၍သာ အင်တာနက် သုံးစွဲနိုင်ပါသည်။"</string>
<string name="mobile_data_disable_message_default_carrier" msgid="6078110473451946831">"သင်၏ ဝန်ဆောင်မှုပေးသူ"</string>
<string name="touch_filtered_warning" msgid="8671693809204767551">"အပလီကေးရှင်းတစ်ခုက ခွင့်ပြုချက်တောင်းခံမှုကို ပိတ်ထားသောကြောင့် ဆက်တင်များသည် သင်၏ လုပ်ဆောင်ကို တုံ့ပြန်နိုင်ခြင်းမရှိပါ။"</string>
<string name="slice_permission_title" msgid="7465009437851044444">"<xliff:g id="APP_0">%1$s</xliff:g> အား <xliff:g id="APP_2">%2$s</xliff:g> ၏အချပ်များ ပြသခွင့်ပြုပါသလား။"</string>
@@ -912,8 +913,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"<xliff:g id="APP_NAME">%1$s</xliff:g> ကိုဖွင့်ရန်"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"<xliff:g id="APP_NAME">%1$s</xliff:g> ပူဖောင်းကွက်များအတွက် ဆက်တင်များ"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"<xliff:g id="APP_NAME">%1$s</xliff:g> မှ ပူဖောင်းကွက်များကို ခွင့်ပြုလိုပါသလား။"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"စီမံရန်"</string>
<string name="no_bubbles" msgid="337101288173078247">"ငြင်းပယ်ရန်"</string>
<string name="yes_bubbles" msgid="668809525728633841">"ခွင့်ပြုရန်"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"နောက်မှ မေးရန်"</string>
diff --git a/packages/SystemUI/res/values-nb/strings.xml b/packages/SystemUI/res/values-nb/strings.xml
index a0c65523d0d6..2b84fa812b95 100644
--- a/packages/SystemUI/res/values-nb/strings.xml
+++ b/packages/SystemUI/res/values-nb/strings.xml
@@ -448,6 +448,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"Ikke vis igjen"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"Fjern alt"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"Administrer"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"Varsler er satt på pause av «Ikke forstyrr»"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"Start nå"</string>
<string name="empty_shade_text" msgid="708135716272867002">"Ingen varsler"</string>
@@ -527,8 +531,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"Skjermen er låst"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"På denne måten blir skjermen synlig frem til du løsner den. Trykk og hold inne Tilbake og Oversikt for å løsne den."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"På denne måten blir skjermen synlig frem til du løsner den. Trykk og hold inne Tilbake og Startside for å løsne den."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"På denne måten blir skjermen synlig frem til du løsner den. Sveip opp og hold for å løsne."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"På denne måten blir skjermen synlig frem til du løsner den. Trykk og hold inne Oversikt for å løsne den."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"På denne måten blir skjermen synlig frem til du løsner den. Trykk og hold inne Startside for å løsne den."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"For å løsne denne skjermen, trykk på og hold inne Tilbake- og Oversikt-knappene"</string>
@@ -912,8 +915,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"Åpne <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"Innstillinger for <xliff:g id="APP_NAME">%1$s</xliff:g>-bobler"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"Vil du tillate bobler fra <xliff:g id="APP_NAME">%1$s</xliff:g>?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"Administrer"</string>
<string name="no_bubbles" msgid="337101288173078247">"Avvis"</string>
<string name="yes_bubbles" msgid="668809525728633841">"Tillat"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"Spør meg senere"</string>
diff --git a/packages/SystemUI/res/values-ne/strings.xml b/packages/SystemUI/res/values-ne/strings.xml
index b3dedc58e286..89037ee84523 100644
--- a/packages/SystemUI/res/values-ne/strings.xml
+++ b/packages/SystemUI/res/values-ne/strings.xml
@@ -448,6 +448,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"फेरि नदेखाउनुहोस्"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"सबै हटाउनुहोस्"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"व्यवस्थित गर्नुहोस्"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"बाधा नपुऱ्याउनुहोस् नामक मोडमार्फत पज पारिएका सूचनाहरू"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"अहिले सुरु गर्नुहोस्"</string>
<string name="empty_shade_text" msgid="708135716272867002">"कुनै सूचनाहरू छैनन्"</string>
@@ -527,8 +531,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"पर्दा राखेका छ"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"तपाईंले अनपिन नगरेसम्म यसले त्यसलाई दृश्यमा कायम राख्छ। अनपिन गर्न पछाडि र परिदृश्य बटनलाई छोइराख्नुहोस्।"</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"तपाईंले अनपिन नगरेसम्म यसले त्यसलाई दृश्यमा कायम राख्छ। अनपिन गर्न पछाडि र गृह नामक बटनहरूलाई छोइराख्नुहोस्।"</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"तपाईंले अनपिन नगरेसम्म यस कार्यले यसलाई दृश्यमा राख्छ। अनपिन गर्न माथितिर स्वाइप गरी होल्ड गर्नुहोस्।"</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"तपाईंले अनपिन नगरेसम्म यसले त्यसलाई दृश्यमा कायम राख्छ। अनपिन गर्न परिदृश्य बटनलाई छोइराख्नुहोस्।"</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"तपाईंले अनपिन नगरेसम्म यसले त्यसलाई दृश्यमा कायम राख्छ। अनपिन गर्न गृह नामक बटनलाई छोइराख्नुहोस्।"</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"यस स्क्रिनलाई अनपनि गर्न पछाडि र परिदृश्य नामक बटनहरूलाई छोइराख्नुहोस्"</string>
@@ -912,8 +915,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"<xliff:g id="APP_NAME">%1$s</xliff:g> खोल्नुहोस्"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"<xliff:g id="APP_NAME">%1$s</xliff:g> का बबलसम्बन्धी सेटिङहरू"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"<xliff:g id="APP_NAME">%1$s</xliff:g> का बबलहरूलाई अनुमति दिने हो?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"व्यवस्थापन गर्नुहोस्"</string>
<string name="no_bubbles" msgid="337101288173078247">"अस्वीकार गर्नुहोस्"</string>
<string name="yes_bubbles" msgid="668809525728633841">"अनुमति दिनुहोस्"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"मलाई पछि सोध्नुहोस्"</string>
diff --git a/packages/SystemUI/res/values-night/colors.xml b/packages/SystemUI/res/values-night/colors.xml
index a53855825105..e25faa28d658 100644
--- a/packages/SystemUI/res/values-night/colors.xml
+++ b/packages/SystemUI/res/values-night/colors.xml
@@ -50,6 +50,7 @@
<color name="notification_guts_button_color">@color/GM2_blue_200</color>
<color name="notification_section_header_label_color">@color/GM2_grey_200</color>
+ <color name="notification_channel_dialog_separator">@color/GM2_grey_700</color>
<!-- The color of the background in the top part of QSCustomizer -->
<color name="qs_customize_background">@color/GM2_grey_900</color>
@@ -74,4 +75,4 @@
<color name="biometric_dialog_accent">#ff80cbc4</color> <!-- light teal -->
<color name="biometric_dialog_error">#fff28b82</color> <!-- red 300 -->
-</resources> \ No newline at end of file
+</resources>
diff --git a/packages/SystemUI/res/values-nl/strings.xml b/packages/SystemUI/res/values-nl/strings.xml
index 7b0cb055abb5..d07562c2f204 100644
--- a/packages/SystemUI/res/values-nl/strings.xml
+++ b/packages/SystemUI/res/values-nl/strings.xml
@@ -294,7 +294,7 @@
<string name="quick_settings_dnd_label" msgid="7112342227663678739">"Niet storen"</string>
<string name="quick_settings_dnd_priority_label" msgid="483232950670692036">"Alleen prioriteit"</string>
<string name="quick_settings_dnd_alarms_label" msgid="2559229444312445858">"Alleen wekkers"</string>
- <string name="quick_settings_dnd_none_label" msgid="5025477807123029478">"Totale stilte"</string>
+ <string name="quick_settings_dnd_none_label" msgid="5025477807123029478">"Helemaal stil"</string>
<string name="quick_settings_bluetooth_label" msgid="6304190285170721401">"Bluetooth"</string>
<string name="quick_settings_bluetooth_multiple_devices_label" msgid="3912245565613684735">"Bluetooth (<xliff:g id="NUMBER">%d</xliff:g> apparaten)"</string>
<string name="quick_settings_bluetooth_off_label" msgid="8159652146149219937">"Bluetooth uit"</string>
@@ -397,8 +397,8 @@
<string name="phone_hint" msgid="4872890986869209950">"Vegen voor telefoon"</string>
<string name="voice_hint" msgid="8939888732119726665">"Vegen vanaf pictogram voor spraakassistent"</string>
<string name="camera_hint" msgid="7939688436797157483">"Vegen voor camera"</string>
- <string name="interruption_level_none_with_warning" msgid="5114872171614161084">"Totale stilte. Hiermee worden schermlezers ook op stil gezet."</string>
- <string name="interruption_level_none" msgid="6000083681244492992">"Totale stilte"</string>
+ <string name="interruption_level_none_with_warning" msgid="5114872171614161084">"Helemaal stil. Hiermee worden schermlezers ook op stil gezet."</string>
+ <string name="interruption_level_none" msgid="6000083681244492992">"Helemaal stil"</string>
<string name="interruption_level_priority" msgid="6426766465363855505">"Alleen prioriteit"</string>
<string name="interruption_level_alarms" msgid="5226306993448328896">"Alleen wekkers"</string>
<string name="interruption_level_none_twoline" msgid="3957581548190765889">"Totale\nstilte"</string>
@@ -448,6 +448,8 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"Niet opnieuw weergeven"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"Alles wissen"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"Beheren"</string>
+ <string name="notification_section_header_gentle" msgid="8356064473678167305">"Vriendelijke meldingen"</string>
+ <string name="accessibility_notification_section_header_gentle_clear_all" msgid="4270384919249494640">"Alle vriendelijke meldingen wissen"</string>
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"Meldingen onderbroken door \'Niet storen\'"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"Nu starten"</string>
<string name="empty_shade_text" msgid="708135716272867002">"Geen meldingen"</string>
@@ -527,8 +529,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"Scherm is vastgezet"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"Het scherm blijft zichtbaar totdat je het losmaakt. Tik op Terug en Overzicht en houd deze vast om het scherm los te maken."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"Het scherm blijft zichtbaar totdat je het losmaakt. Tik op Terug en Home en houd deze vast om het scherm los te maken."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"Zo blijft het scherm zichtbaar totdat je dit losmaakt. Veeg omhoog en houd vast om los te maken."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"Het scherm blijft zichtbaar totdat je het losmaakt. Tik op Overzicht en houd dit vast om het scherm los te maken."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"Het scherm blijft zichtbaar totdat je het losmaakt. Tik op Home en houd dit vast om het scherm los te maken."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"Tik op Terug en Overzicht en houd deze knoppen vast om dit scherm los te maken"</string>
@@ -881,7 +882,7 @@
<string name="running_foreground_services_title" msgid="381024150898615683">"Apps uitgevoerd op achtergrond"</string>
<string name="running_foreground_services_msg" msgid="6326247670075574355">"Tik voor batterij- en datagebruik"</string>
<string name="mobile_data_disable_title" msgid="1068272097382942231">"Mobiele data uitschakelen?"</string>
- <string name="mobile_data_disable_message" msgid="4756541658791493506">"Je hebt geen toegang tot gegevens of internet via <xliff:g id="CARRIER">%s</xliff:g>. Internet is alleen beschikbaar via wifi."</string>
+ <string name="mobile_data_disable_message" msgid="4756541658791493506">"Je hebt geen toegang tot data of internet via <xliff:g id="CARRIER">%s</xliff:g>. Internet is alleen beschikbaar via wifi."</string>
<string name="mobile_data_disable_message_default_carrier" msgid="6078110473451946831">"je provider"</string>
<string name="touch_filtered_warning" msgid="8671693809204767551">"Aangezien een app een toestemmingsverzoek afdekt, kan Instellingen je reactie niet verifiëren."</string>
<string name="slice_permission_title" msgid="7465009437851044444">"<xliff:g id="APP_0">%1$s</xliff:g> toestaan om segmenten van <xliff:g id="APP_2">%2$s</xliff:g> weer te geven?"</string>
@@ -912,8 +913,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"<xliff:g id="APP_NAME">%1$s</xliff:g> openen"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"Instellingen voor <xliff:g id="APP_NAME">%1$s</xliff:g>-ballonnen"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"Ballonnen van <xliff:g id="APP_NAME">%1$s</xliff:g> toestaan?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"Beheren"</string>
<string name="no_bubbles" msgid="337101288173078247">"Weigeren"</string>
<string name="yes_bubbles" msgid="668809525728633841">"Toestaan"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"Later vragen"</string>
diff --git a/packages/SystemUI/res/values-or/strings.xml b/packages/SystemUI/res/values-or/strings.xml
index 715228365043..0fa40431d725 100644
--- a/packages/SystemUI/res/values-or/strings.xml
+++ b/packages/SystemUI/res/values-or/strings.xml
@@ -324,7 +324,7 @@
<string name="quick_settings_user_title" msgid="4467690427642392403">"ୟୁଜର୍‌"</string>
<string name="quick_settings_user_new_user" msgid="9030521362023479778">"ନୂଆ ୟୁଜର୍‌"</string>
<string name="quick_settings_wifi_label" msgid="9135344704899546041">"ୱାଇ-ଫାଇ"</string>
- <string name="quick_settings_wifi_not_connected" msgid="7171904845345573431">"କନେକ୍ଟ ହୋଇନାହିଁ"</string>
+ <string name="quick_settings_wifi_not_connected" msgid="7171904845345573431">"ସଂଯୁକ୍ତ ହୋଇନାହିଁ"</string>
<string name="quick_settings_wifi_no_network" msgid="2221993077220856376">"ନେଟ୍‌ୱର୍କ ନାହିଁ"</string>
<string name="quick_settings_wifi_off_label" msgid="7558778100843885864">"ୱାଇ-ଫାଇ ଅଫ୍‍"</string>
<string name="quick_settings_wifi_on_label" msgid="7607810331387031235">"ୱାଇ-ଫାଇ ଅନ୍‍ ଅଛି"</string>
@@ -448,6 +448,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"ପୁଣି ଦେଖାନ୍ତୁ ନାହିଁ"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"ସମସ୍ତ ଖାଲି କରନ୍ତୁ"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"ପରିଚାଳନା କରନ୍ତୁ"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"\"ବିରକ୍ତ କରନ୍ତୁ ନାହିଁ\" ବିକଳ୍ପ ଦ୍ୱାରା ବିଜ୍ଞପ୍ତି ପଜ୍‍ ହୋଇଛି"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"ବର୍ତ୍ତମାନ ଆରମ୍ଭ କରନ୍ତୁ"</string>
<string name="empty_shade_text" msgid="708135716272867002">"କୌଣସି ବିଜ୍ଞପ୍ତି ନାହିଁ"</string>
@@ -527,8 +531,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"ସ୍କ୍ରିନକୁ ପିନ୍‌ କରାଯାଇଛି"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"ଆପଣ ଅନପିନ୍‍ ନକରିବା ପର୍ଯ୍ୟନ୍ତ ଏହା ଦେଖାଉଥିବ। ଅନପିନ୍‍ କରିବାକୁ ସ୍ପର୍ଶ କରି ଧରିରଖନ୍ତୁ ଓ ଦେଖନ୍ତୁ।"</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"ଆପଣ ଅନପିନ୍‍ ନକରିବା ପର୍ଯ୍ୟନ୍ତ ଏହା ଦେଖାଉଥିବ। ଅନପିନ୍‍ କରିବା ପାଇଁ ହୋମ୍ ଓ ବ୍ୟାକ୍ ବଟନ୍‌କୁ ଧରିରଖନ୍ତୁ।"</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"ଆପଣ ଅନ୍‌ପିନ୍ ନକରିବା ପର୍ଯ୍ୟନ୍ତ ଏହା ଦେଖାଯାଉଥିବ। ଅନ୍‌ପିନ୍ କରିବା ପାଇଁ ଉପରକୁ ସ୍ୱାଇପ୍‌ କରି ଧରି ରଖନ୍ତୁ"</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"ଆପଣ ଅନପିନ୍‍ ନକରିବା ପର୍ଯ୍ୟନ୍ତ ଏହା ଦେଖାଉଥିବ। ଅନପିନ୍‍ କରିବାକୁ ସ୍ପର୍ଶ କରନ୍ତୁ ଏବଂ ଓଭରଭ୍ୟୁକୁ ଧରିରଖନ୍ତୁ।"</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"ଆପଣ ଅନପିନ୍‍ ନକରିବା ପର୍ଯ୍ୟନ୍ତ ଏହା ଦେଖାଉଥିବ। ଅନପିନ୍‍ କରିବା ପର୍ଯ୍ୟନ୍ତ ହୋମ୍‌କୁ ଦାବିଧରନ୍ତୁ।"</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"ଏହି ସ୍କ୍ରୀନ୍‍‍କୁ ଅନପିନ୍‍ କରିବା ପାଇଁ, ବ୍ୟାକ୍ ଏବଂ ଓଭରଭ୍ୟୁ ବଟନ୍‍‌କୁ ଦାବିଧରନ୍ତୁ"</string>
@@ -640,11 +643,11 @@
<string name="inline_keep_showing_app" msgid="1723113469580031041">"ଏହି ଆପ୍‌ରୁ ବିଜ୍ଞପ୍ତିଗୁଡ଼ିକୁ ଦେଖାଇବା ଜାରି ରଖିବେ?"</string>
<string name="notification_silence_title" msgid="7352089096356977930">"ଧିରେ"</string>
<string name="notification_alert_title" msgid="3966526305405016221">"ପ୍ରାଥମିକତା ଭିତ୍ତିକ"</string>
- <string name="notification_channel_summary_low" msgid="1065819618107531284">"କେବଳ ପୁଲ୍-ଡାଉନ୍ ସେଡ୍‌ରେ ବିଜ୍ଞପ୍ତିଗୁଡ଼ିକ ଉପରେ ଫୋକସ୍ ରହିବା ପାଇଁ ଆପଣଙ୍କୁ ସାହାଯ୍ୟ କରିଥାଏ। ସର୍ବଦା ନିରବ।"</string>
+ <string name="notification_channel_summary_low" msgid="1065819618107531284">"କେବଳ ପୁଲ୍-ଡାଉନ୍ ସେଡ୍‌ରେ ବିଜ୍ଞପ୍ତିଗୁଡ଼ିକ ଉପରେ ଫୋକସ୍ ରହିବା ପାଇଁ ଆପଣଙ୍କୁ ସାହାଯ୍ୟ କରିଥାଏ। ସର୍ବଦା ନୀରବ।"</string>
<string name="notification_channel_summary_low_status" msgid="2702170424808743755">"ପ୍ରାଥମିକତା ବିଜ୍ଞପ୍ତିଗୁଡ଼ିକର ତଳେ ଡିସ୍‌ପ୍ଲେ ହୁଏ। ସର୍ବଦା ନିରବ।"</string>
<string name="notification_channel_summary_low_lock" msgid="7966605244472624458">"ପ୍ରାଥମିକତା ବିଜ୍ଞପ୍ତିଗୁଡ଼ିକର ତଳେ ଡିସ୍‌ପ୍ଲେ ହୁଏ। ସର୍ବଦା ନିରବ।"</string>
<string name="notification_channel_summary_low_status_lock" msgid="7012562768950012739">"ପ୍ରାଥମିକତା ବିଜ୍ଞପ୍ତିଗୁଡ଼ିକର ତଳେ ଡିସ୍‌ପ୍ଲେ ହୁଏ। ସର୍ବଦା ନିରବ।"</string>
- <string name="notification_channel_summary_default" msgid="3847289783382316019">"ସାଉଣ୍ଡ ଏବଂ ଏକ ଷ୍ଟାଟସ୍ ବାର୍ ଆଇକନ୍ ମାଧ୍ୟମରେ ଆପଣଙ୍କର ଧ୍ୟାନ ଆକର୍ଷିତ କରିଥାଏ। ଲକ୍ ସ୍କ୍ରିନ୍‌ରେ ଦେଖାଯାଇଥାଏ।"</string>
+ <string name="notification_channel_summary_default" msgid="3847289783382316019">"ସାଉଣ୍ଡ୍ ଏବଂ ଏକ ଷ୍ଟାଟସ୍ ବାର୍ ଆଇକନ୍ ମାଧ୍ୟମରେ ଆପଣଙ୍କର ଧ୍ୟାନ ଆକର୍ଷିତ କରିଥାଏ। ଲକ୍ ସ୍କ୍ରିନ୍‌ରେ ଦେଖାଯାଇଥାଏ।"</string>
<string name="notification_unblockable_desc" msgid="4556908766584964102">"ଏହି ବିଜ୍ଞପ୍ତିଗୁଡ଼ିକ ପରିବର୍ତ୍ତନ କରିହେବ ନାହିଁ।"</string>
<string name="notification_multichannel_desc" msgid="4695920306092240550">"ଏଠାରେ ଏହି ବିଜ୍ଞପ୍ତିଗୁଡ଼ିକର ଗ୍ରୁପ୍ କନଫ୍ୟୁଗର୍ କରାଯାଇପାରିବ ନାହିଁ"</string>
<string name="notification_delegate_header" msgid="2857691673814814270">"ବିଜ୍ଞପ୍ତି ପ୍ରକ୍ସୀ ହୋଇଛି"</string>
@@ -715,7 +718,7 @@
<string name="keyboard_shortcut_group_system_notifications" msgid="8366964080041773224">"ବିଜ୍ଞପ୍ତି"</string>
<string name="keyboard_shortcut_group_system_shortcuts_helper" msgid="4892255911160332762">"କୀ\'ବୋର୍ଡ ସର୍ଟକଟ୍"</string>
<string name="keyboard_shortcut_group_system_switch_input" msgid="8413348767825486492">"କୀ\'ବୋର୍ଡ୍‍ର ଲେଆଉଟ୍‍କୁ ବଦଳାନ୍ତୁ"</string>
- <string name="keyboard_shortcut_group_applications" msgid="9129465955073449206">"ଆପ୍ଲିକେଶନ୍‌"</string>
+ <string name="keyboard_shortcut_group_applications" msgid="9129465955073449206">"ଆପ୍ଲିକେସନ୍‌"</string>
<string name="keyboard_shortcut_group_applications_assist" msgid="9095441910537146013">"ସହାୟତା"</string>
<string name="keyboard_shortcut_group_applications_browser" msgid="6465985474000766533">"ବ୍ରାଉଜର୍"</string>
<string name="keyboard_shortcut_group_applications_contacts" msgid="2064197111278436375">"ଯୋଗାଯୋଗ"</string>
@@ -912,8 +915,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"<xliff:g id="APP_NAME">%1$s</xliff:g> ଖୋଲନ୍ତୁ"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"<xliff:g id="APP_NAME">%1$s</xliff:g> ବବଲ୍‌ଗୁଡ଼ିକ ପାଇଁ ସେଟିଂସ୍"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"<xliff:g id="APP_NAME">%1$s</xliff:g>ରୁ ବବ୍‌ଲ୍‌ଗୁଡ଼ିକୁ ଅନୁମତି ଦିଅନ୍ତୁ?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"ପରିଚାଳନା କରନ୍ତୁ"</string>
<string name="no_bubbles" msgid="337101288173078247">"ପ୍ରତ୍ୟାଖ୍ୟାନ କରନ୍ତୁ"</string>
<string name="yes_bubbles" msgid="668809525728633841">"ଅନୁମତି ଦିଅନ୍ତୁ"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"ମୋତେ ପରେ ପଚାରନ୍ତୁ"</string>
diff --git a/packages/SystemUI/res/values-pa/strings.xml b/packages/SystemUI/res/values-pa/strings.xml
index 2e50bc93d049..78ff73c1d306 100644
--- a/packages/SystemUI/res/values-pa/strings.xml
+++ b/packages/SystemUI/res/values-pa/strings.xml
@@ -448,6 +448,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"ਦੁਬਾਰਾ ਨਾ ਦਿਖਾਓ"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"ਸਭ ਕਲੀਅਰ ਕਰੋ"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"ਪ੍ਰਬੰਧਨ ਕਰੋ"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"\'ਪਰੇਸ਼ਾਨ ਨਾ ਕਰੋ\' ਵੱਲੋਂ ਸੂਚਨਾਵਾਂ ਨੂੰ ਰੋਕਿਆ ਗਿਆ"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"ਹੁਣ ਚਾਲੂ ਕਰੋ"</string>
<string name="empty_shade_text" msgid="708135716272867002">"ਕੋਈ ਸੂਚਨਾਵਾਂ ਨਹੀਂ"</string>
@@ -527,8 +531,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"ਸਕ੍ਰੀਨ ਪਿੰਨ ਕੀਤੀ"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"ਇਹ ਇਸ ਨੂੰ ਤਦ ਤੱਕ ਦ੍ਰਿਸ਼ ਵਿੱਚ ਰੱਖਦਾ ਹੈ ਜਦ ਤੱਕ ਤੁਸੀਂ ਅਨਪਿੰਨ ਨਹੀਂ ਕਰਦੇ। ਅਨਪਿੰਨ ਕਰਨ ਲਈ \'ਪਿੱਛੇ\' ਅਤੇ \'ਰੂਪ-ਰੇਖਾ\' ਨੂੰ ਸਪੱਰਸ਼ ਕਰੋ ਅਤੇ ਦਬਾ ਕੇ ਰੱਖੋ।"</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"ਤੁਹਾਡੇ ਵੱਲੋਂ ਅਨਪਿੰਨ ਨਾ ਕੀਤੇ ਜਾਣ ਤੱਕ ਇਸਨੂੰ ਦਿਖਾਇਆ ਜਾਂਦਾ ਹੈ। ਅਨਪਿੰਨ ਕਰਨ ਲਈ \'ਪਿੱਛੇ\' ਅਤੇ \'ਹੋਮ\' ਨੂੰ ਸਪੱਰਸ਼ ਕਰਕੇ ਦਬਾਈ ਰੱਖੋ।"</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"ਤੁਹਾਡੇ ਵੱਲੋਂ ਅਨਪਿੰਨ ਨਾ ਕੀਤੇ ਜਾਣ ਤੱਕ ਇਸਨੂੰ ਦਿਖਾਇਆ ਜਾਂਦਾ ਹੈ। ਅਨਪਿੰਨ ਕਰਨ ਲਈ ਉੱਪਰ ਵੱਲ ਸਵਾਈਪ ਕਰੋ ਅਤੇ ਫੜ ਕੇ ਰੱਖੋ।"</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"ਇਹ ਇਸ ਨੂੰ ਤਦ ਤੱਕ ਦ੍ਰਿਸ਼ ਵਿੱਚ ਰੱਖਦਾ ਹੈ ਜਦ ਤੱਕ ਤੁਸੀਂ ਅਨਪਿੰਨ ਨਹੀਂ ਕਰਦੇ। ਅਨਪਿੰਨ ਕਰਨ ਲਈ \'ਰੂਪ-ਰੇਖਾ\' ਨੂੰ ਸਪੱਰਸ਼ ਕਰੋ ਅਤੇ ਦਬਾ ਕੇ ਰੱਖੋ।"</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"ਤੁਹਾਡੇ ਵੱਲੋਂ ਅਨਪਿੰਨ ਨਾ ਕੀਤੇ ਜਾਣ ਤੱਕ ਇਸਨੂੰ ਦਿਖਾਇਆ ਜਾਂਦਾ ਹੈ। ਅਨਪਿੰਨ ਕਰਨ ਲਈ \'ਹੋਮ\' ਨੂੰ ਸਪੱਰਸ਼ ਕਰਕੇ ਦਬਾਈ ਰੱਖੋ।"</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"ਇਸ ਸਕ੍ਰੀਨ ਨੂੰ ਅਨਪਿੰਨ ਕਰਨ ਲਈ, \'ਪਿੱਛੇ\' ਅਤੇ \'ਰੂਪ-ਰੇਖਾ\' ਬਟਨਾਂ ਨੂੰ ਸਪੱਰਸ਼ ਕਰਕੇ ਦਬਾਈ ਰੱਖੋ"</string>
@@ -912,8 +915,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"<xliff:g id="APP_NAME">%1$s</xliff:g> ਖੋਲ੍ਹੋ"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"<xliff:g id="APP_NAME">%1$s</xliff:g> ਬੁਲਬੁਲਿਆਂ ਲਈ ਸੈਟਿੰਗਾਂ"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"<xliff:g id="APP_NAME">%1$s</xliff:g> ਤੋਂ ਬੁਲਬੁਲੇ ਆਉਣ ਦਿਓ?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"ਪ੍ਰਬੰਧਨ ਕਰੋ"</string>
<string name="no_bubbles" msgid="337101288173078247">"ਮਨ੍ਹਾ ਕਰੋ"</string>
<string name="yes_bubbles" msgid="668809525728633841">"ਕਰਨ ਦਿਓ"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"ਮੈਨੂੰ ਬਾਅਦ ਵਿੱਚ ਪੁੱਛੋ"</string>
diff --git a/packages/SystemUI/res/values-pl/strings.xml b/packages/SystemUI/res/values-pl/strings.xml
index 0aa7ff6bda02..9fc1c4a5acf7 100644
--- a/packages/SystemUI/res/values-pl/strings.xml
+++ b/packages/SystemUI/res/values-pl/strings.xml
@@ -456,6 +456,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"Nie pokazuj ponownie"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"Ukryj wszystkie"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"Zarządzaj"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"Powiadomienia wstrzymane przez tryb Nie przeszkadzać"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"Rozpocznij teraz"</string>
<string name="empty_shade_text" msgid="708135716272867002">"Brak powiadomień"</string>
@@ -535,8 +539,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"Ekran jest przypięty"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"Ekran będzie widoczny, dopóki go nie odepniesz. Aby to zrobić, kliknij i przytrzymaj Wstecz oraz Przegląd."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"Ekran będzie widoczny, dopóki go nie odepniesz. Aby to zrobić, naciśnij i przytrzymaj Wstecz oraz Ekran główny."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"Ekran będzie widoczny, dopóki go nie odepniesz. Przesuń palcem w górę i przytrzymaj, by odpiąć."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"Ekran będzie widoczny, dopóki go nie odepniesz. Aby to zrobić, kliknij i przytrzymaj Przegląd."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"Ekran będzie widoczny, dopóki go nie odepniesz. Aby to zrobić, naciśnij i przytrzymaj Ekran główny."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"Aby odpiąć ten ekran, naciśnij i przytrzymaj przyciski Wstecz oraz Przegląd"</string>
@@ -878,7 +881,7 @@
<string name="instant_apps_message_with_help" msgid="6179830437630729747">"Aplikacja została otwarta bez zainstalowania. Kliknij, by dowiedzieć się więcej."</string>
<string name="app_info" msgid="6856026610594615344">"O aplikacji"</string>
<string name="go_to_web" msgid="2650669128861626071">"Otwórz przeglądarkę"</string>
- <string name="mobile_data" msgid="7094582042819250762">"Komórkowa transmisja danych"</string>
+ <string name="mobile_data" msgid="7094582042819250762">"Dane mobilne"</string>
<string name="mobile_data_text_format" msgid="3526214522670876454">"<xliff:g id="ID_1">%1$s</xliff:g> – <xliff:g id="ID_2">%2$s</xliff:g>"</string>
<string name="mobile_carrier_text_format" msgid="3241721038678469804">"<xliff:g id="CARRIER_NAME">%1$s</xliff:g>, <xliff:g id="MOBILE_DATA_TYPE">%2$s</xliff:g>"</string>
<string name="wifi_is_off" msgid="1838559392210456893">"Wi-Fi jest wyłączone"</string>
@@ -924,8 +927,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"Otwórz: <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"Ustawienia dymków aplikacji <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"Zezwolić na dymki z aplikacji <xliff:g id="APP_NAME">%1$s</xliff:g>?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"Zarządzaj"</string>
<string name="no_bubbles" msgid="337101288173078247">"Odmów"</string>
<string name="yes_bubbles" msgid="668809525728633841">"Zezwól"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"Zapytaj później"</string>
diff --git a/packages/SystemUI/res/values-pt-rBR/strings.xml b/packages/SystemUI/res/values-pt-rBR/strings.xml
index 3feb5c6340be..a2441768477e 100644
--- a/packages/SystemUI/res/values-pt-rBR/strings.xml
+++ b/packages/SystemUI/res/values-pt-rBR/strings.xml
@@ -448,6 +448,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"Não mostrar novamente"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"Limpar tudo"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"Gerenciar"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"Notificações pausadas pelo modo \"Não perturbe\""</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"Iniciar agora"</string>
<string name="empty_shade_text" msgid="708135716272867002">"Sem notificações"</string>
@@ -527,8 +531,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"A tela está fixada"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"Ela é mantida à vista até que seja liberada. Toque em Voltar e em Visão geral e mantenha essas opções pressionadas para liberar."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"Ela é mantida à vista até que seja liberada. Toque em Voltar e em Início e mantenha essas opções pressionadas para liberar."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"Ela é mantida à vista até que seja liberada. Deslize para cima e a mantenha pressionada para liberar."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"Ela é mantida à vista até que seja liberada. Toque em Visão geral e mantenha essa opção pressionada para liberar."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"Ela é mantida à vista até que seja liberada. Toque em Início e mantenha essa opção pressionada para liberar."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"Para liberar esta tela, mantenha os botões Voltar e Visão geral pressionados"</string>
@@ -912,8 +915,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"Abrir <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"Configurações de balões do <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"Permitir balões de <xliff:g id="APP_NAME">%1$s</xliff:g>?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"Gerenciar"</string>
<string name="no_bubbles" msgid="337101288173078247">"Negar"</string>
<string name="yes_bubbles" msgid="668809525728633841">"Permitir"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"Perguntar depois"</string>
diff --git a/packages/SystemUI/res/values-pt-rPT/strings.xml b/packages/SystemUI/res/values-pt-rPT/strings.xml
index a526ca06d5f6..557760f94199 100644
--- a/packages/SystemUI/res/values-pt-rPT/strings.xml
+++ b/packages/SystemUI/res/values-pt-rPT/strings.xml
@@ -448,6 +448,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"Não mostrar de novo"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"Limpar tudo"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"Gerir"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"Notificações colocadas em pausa pelo modo Não incomodar."</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"Começar agora"</string>
<string name="empty_shade_text" msgid="708135716272867002">"Sem notificações"</string>
@@ -527,8 +531,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"O ecrã está fixado"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"Esta opção mantém o item visível até o soltar. Toque sem soltar em Anterior e em Vista geral para soltar."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"Esta opção mantém o item visível até o soltar. Toque sem soltar em Anterior e em Página inicial para soltar."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"Esta opção mantém o item visível até o soltar. Deslize rapidamente para cima e mantenha o gesto para soltar."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"Esta opção mantém o item visível até o soltar. Toque sem soltar em Vista geral para soltar."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"Esta opção mantém o item visível até o soltar. Toque sem soltar em Página inicial para soltar."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"Para soltar este ecrã, toque sem soltar nos botões Anterior e Vista geral."</string>
@@ -912,8 +915,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"Abrir a aplicação <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"Definições dos balões da aplicação <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"Pretende permitir balões da aplicação <xliff:g id="APP_NAME">%1$s</xliff:g>?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"Gerir"</string>
<string name="no_bubbles" msgid="337101288173078247">"Recusar"</string>
<string name="yes_bubbles" msgid="668809525728633841">"Permitir"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"Perguntar depois"</string>
diff --git a/packages/SystemUI/res/values-pt/strings.xml b/packages/SystemUI/res/values-pt/strings.xml
index 3feb5c6340be..a2441768477e 100644
--- a/packages/SystemUI/res/values-pt/strings.xml
+++ b/packages/SystemUI/res/values-pt/strings.xml
@@ -448,6 +448,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"Não mostrar novamente"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"Limpar tudo"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"Gerenciar"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"Notificações pausadas pelo modo \"Não perturbe\""</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"Iniciar agora"</string>
<string name="empty_shade_text" msgid="708135716272867002">"Sem notificações"</string>
@@ -527,8 +531,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"A tela está fixada"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"Ela é mantida à vista até que seja liberada. Toque em Voltar e em Visão geral e mantenha essas opções pressionadas para liberar."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"Ela é mantida à vista até que seja liberada. Toque em Voltar e em Início e mantenha essas opções pressionadas para liberar."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"Ela é mantida à vista até que seja liberada. Deslize para cima e a mantenha pressionada para liberar."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"Ela é mantida à vista até que seja liberada. Toque em Visão geral e mantenha essa opção pressionada para liberar."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"Ela é mantida à vista até que seja liberada. Toque em Início e mantenha essa opção pressionada para liberar."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"Para liberar esta tela, mantenha os botões Voltar e Visão geral pressionados"</string>
@@ -912,8 +915,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"Abrir <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"Configurações de balões do <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"Permitir balões de <xliff:g id="APP_NAME">%1$s</xliff:g>?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"Gerenciar"</string>
<string name="no_bubbles" msgid="337101288173078247">"Negar"</string>
<string name="yes_bubbles" msgid="668809525728633841">"Permitir"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"Perguntar depois"</string>
diff --git a/packages/SystemUI/res/values-ro/strings.xml b/packages/SystemUI/res/values-ro/strings.xml
index 5baf1afe5753..4979069d9164 100644
--- a/packages/SystemUI/res/values-ro/strings.xml
+++ b/packages/SystemUI/res/values-ro/strings.xml
@@ -451,6 +451,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"Nu se mai afișează"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"Ștergeți toate notificările"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"Gestionați"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"Notificări întrerupte prin „Nu deranja”"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"Începeți acum"</string>
<string name="empty_shade_text" msgid="708135716272867002">"Nicio notificare"</string>
@@ -530,8 +534,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"Ecranul este fixat"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"Astfel rămâne afișat până anulați fixarea. Atingeți lung opțiunile Înapoi și Recente pentru a anula fixarea."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"Astfel rămâne afișat până anulați fixarea. Atingeți lung opțiunile Înapoi și Acasă pentru a anula fixarea."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"Astfel rămâne afișat până anulați fixarea. Glisați în sus și țineți apăsat pentru a anula fixarea."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"Astfel rămâne afișat până anulați fixarea. Atingeți lung opțiunea Recente pentru a anula fixarea."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"Astfel rămâne afișat până anulați fixarea. Atingeți lung opțiunea Acasă pentru a anula fixarea."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"Pentru a anula fixarea acestui ecran, atingeți lung butoanele Înapoi și Recente"</string>
@@ -917,8 +920,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"Accesați <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"Setări pentru baloanele <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"Permiteți baloanele de la <xliff:g id="APP_NAME">%1$s</xliff:g>?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"Gestionați"</string>
<string name="no_bubbles" msgid="337101288173078247">"Refuzați"</string>
<string name="yes_bubbles" msgid="668809525728633841">"Permiteți"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"Întreabă-mă mai târziu"</string>
diff --git a/packages/SystemUI/res/values-ru/strings.xml b/packages/SystemUI/res/values-ru/strings.xml
index fc11173a7722..5a799686bc3c 100644
--- a/packages/SystemUI/res/values-ru/strings.xml
+++ b/packages/SystemUI/res/values-ru/strings.xml
@@ -454,6 +454,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"Больше не показывать"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"Очистить все"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"Настроить"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"В режиме \"Не беспокоить\" уведомления заблокированы"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"Начать"</string>
<string name="empty_shade_text" msgid="708135716272867002">"Нет уведомлений"</string>
@@ -533,8 +537,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"Блокировка в приложении включена"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"Приложение останется активным, пока вы не отмените блокировку, нажав и удерживая кнопки \"Назад\" и \"Обзор\"."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"Приложение останется активным, пока вы не отмените блокировку, нажав и удерживая кнопки \"Назад\" и \"Главный экран\"."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"Экран будет зафиксирован, пока вы не отмените блокировку (для этого нужно провести вверх и удерживать)."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"Приложение останется активным, пока вы не отмените блокировку, нажав и удерживая кнопку \"Обзор\"."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"Приложение останется активным, пока вы не отмените блокировку, нажав и удерживая кнопку \"Главный экран\"."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"Чтобы отменить блокировку, нажмите и удерживайте кнопки \"Назад\" и \"Обзор\""</string>
@@ -920,10 +923,9 @@
<string name="music_controls_no_title" msgid="5236895307087002011">"Без названия"</string>
<string name="restart_button_description" msgid="2035077840254950187">"Нажмите, чтобы перезапустить приложение и перейти в полноэкранный режим."</string>
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"Открыть приложение \"<xliff:g id="APP_NAME">%1$s</xliff:g>\"."</string>
- <string name="bubbles_settings_button_description" msgid="2970630476657287189">"Настройки всплывающих подсказок от приложения \"<xliff:g id="APP_NAME">%1$s</xliff:g>\"."</string>
- <string name="bubbles_prompt" msgid="8807968030159469710">"Разрешить всплывающие подсказки от приложения \"<xliff:g id="APP_NAME">%1$s</xliff:g>\"?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="bubbles_settings_button_description" msgid="2970630476657287189">"Настройки всплывающих уведомлений от приложения \"<xliff:g id="APP_NAME">%1$s</xliff:g>\"."</string>
+ <string name="bubbles_prompt" msgid="8807968030159469710">"Разрешить всплывающие уведомления от приложения \"<xliff:g id="APP_NAME">%1$s</xliff:g>\"?"</string>
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"Настроить"</string>
<string name="no_bubbles" msgid="337101288173078247">"Запретить"</string>
<string name="yes_bubbles" msgid="668809525728633841">"Разрешить"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"Напомнить позже"</string>
diff --git a/packages/SystemUI/res/values-si/strings.xml b/packages/SystemUI/res/values-si/strings.xml
index 3ae5f6ca3bac..09755bbfe522 100644
--- a/packages/SystemUI/res/values-si/strings.xml
+++ b/packages/SystemUI/res/values-si/strings.xml
@@ -448,6 +448,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"නැවත නොපෙන්වන්න"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"සියල්ල හිස් කරන්න"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"කළමනාකරණය කරන්න"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"බාධා නොකරන්න මගින් විරාම කරන ලද දැනුම්දීම්"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"දැන් අරඹන්න"</string>
<string name="empty_shade_text" msgid="708135716272867002">"දැනුම්දීම් නැත"</string>
@@ -527,8 +531,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"තීරය අමුණන ලදි"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"මෙය ඔබ ගලවන තෙක් එය දසුන තුළ තබයි. ගැලවීමට දළ විශ්ලේෂණය ස්පර්ශ කර ආපසු අල්ලාගෙන සිටින්න."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"මෙය ඔබ ගලවන තෙක් එය දසුන තුළ තබයි. ගැලවීමට මුල් පිටුව ස්පර්ශ කර අල්ලාගෙන සිටින්න."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"මෙය ඔබ ගලවන තෙක් එය දසුන තුළ තබයි. ගැලවීමට ඉහළට ස්වයිප් කර අල්ලා සිටින්න."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"මෙය ඔබ ගලවන තෙක් එය දසුන තුළ තබයි. ගැලවීමට දළ විශ්ලේෂණය ස්පර්ශ කර අල්ලාගෙන සිටින්න."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"මෙය ඔබ ගලවන තෙක් එය දසුන තුළ තබයි. ගැලවීමට මුල් පිටුව ස්පර්ශ කර අල්ලාගෙන සිටින්න."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"මෙම තිර ඇමුණුම ගැලවීමට, දළ විශ්ලේෂණය බොත්තම් ස්පර්ශ කර අල්ලා ගෙන සිටින්න"</string>
@@ -912,8 +915,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"<xliff:g id="APP_NAME">%1$s</xliff:g> විවෘත කරන්න"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"<xliff:g id="APP_NAME">%1$s</xliff:g> බුබුළු සඳහා සැකසීම්"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"<xliff:g id="APP_NAME">%1$s</xliff:g> වෙතින් බුබුළුවලට ඉඩ දෙන්නේද?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"කළමනා කරන්න"</string>
<string name="no_bubbles" msgid="337101288173078247">"ප්‍රතික්‍ෂේප කරන්න"</string>
<string name="yes_bubbles" msgid="668809525728633841">"ඉඩ දෙන්න"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"පසුව මගෙන් අසන්න"</string>
diff --git a/packages/SystemUI/res/values-sk/strings.xml b/packages/SystemUI/res/values-sk/strings.xml
index 5fcc605c331d..ae8e0220201d 100644
--- a/packages/SystemUI/res/values-sk/strings.xml
+++ b/packages/SystemUI/res/values-sk/strings.xml
@@ -370,7 +370,7 @@
<string name="quick_settings_night_display_label" msgid="3577098011487644395">"Nočný režim"</string>
<string name="quick_settings_night_secondary_label_on_at_sunset" msgid="8483259341596943314">"Zapne sa pri západe slnka"</string>
<string name="quick_settings_night_secondary_label_until_sunrise" msgid="4453017157391574402">"Do východu slnka"</string>
- <string name="quick_settings_night_secondary_label_on_at" msgid="6256314040368487637">"Zapne sa o <xliff:g id="TIME">%s</xliff:g>"</string>
+ <string name="quick_settings_night_secondary_label_on_at" msgid="6256314040368487637">"Od <xliff:g id="TIME">%s</xliff:g>"</string>
<string name="quick_settings_secondary_label_until" msgid="2749196569462600150">"Do <xliff:g id="TIME">%s</xliff:g>"</string>
<string name="quick_settings_ui_mode_night_label" msgid="512534812963862137">"Tmavý motív"</string>
<string name="quick_settings_nfc_label" msgid="9012153754816969325">"NFC"</string>
@@ -454,6 +454,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"Nabudúce nezobrazovať"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"Vymazať všetko"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"Spravovať"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"Upozornenia sú pozastavené režimom bez vyrušení"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"Spustiť"</string>
<string name="empty_shade_text" msgid="708135716272867002">"Žiadne upozornenia"</string>
@@ -533,8 +537,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"Obrazovka je pripnutá"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"Obsah bude pripnutý v zobrazení, dokým ho neuvoľníte. Uvoľníte ho stlačením a podržaním tlačidiel Späť a Prehľad."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"Obsah bude pripnutý v zobrazení, dokým ho neuvoľníte. Uvoľníte ho pridržaním tlačidiel Späť a Domov."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"Táto možnosť ponechá položku v zobrazení, dokým ju neodopnete. Odpojíte potiahnutím a pridržaním."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"Obsah bude pripnutý v zobrazení, dokým ho neuvoľníte. Uvoľníte ho stlačením a podržaním tlačidla Prehľad."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"Obsah bude pripnutý v zobrazení, dokým ho neuvoľníte. Uvoľníte ho pridržaním tlačidla Domov."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"Ak chcete odopnúť túto obrazovku, pridržte tlačidlá Späť a Prehľad"</string>
@@ -891,7 +894,7 @@
<string name="running_foreground_services_title" msgid="381024150898615683">"Aplikácie sú spustené na pozadí"</string>
<string name="running_foreground_services_msg" msgid="6326247670075574355">"Klepnutím zobrazíte podrobnosti o batérii a spotrebe dát"</string>
<string name="mobile_data_disable_title" msgid="1068272097382942231">"Chcete vypnúť mobilné dáta?"</string>
- <string name="mobile_data_disable_message" msgid="4756541658791493506">"Prostredníctvom operátora <xliff:g id="CARRIER">%s</xliff:g> nebudete mať prístup k dátam ani internetu. Internet bude k dispozícii iba cez Wi-Fi."</string>
+ <string name="mobile_data_disable_message" msgid="4756541658791493506">"Nebudete mať prístup k dátam ani internetu prostredníctvom operátora <xliff:g id="CARRIER">%s</xliff:g>. Internet bude k dispozícii iba cez Wi‑Fi."</string>
<string name="mobile_data_disable_message_default_carrier" msgid="6078110473451946831">"váš operátor"</string>
<string name="touch_filtered_warning" msgid="8671693809204767551">"Nastavenia nemôžu overiť vašu odpoveď, pretože určitá aplikácia blokuje žiadosť o povolenie."</string>
<string name="slice_permission_title" msgid="7465009437851044444">"Povoliť aplikácii <xliff:g id="APP_0">%1$s</xliff:g> zobrazovať rezy z aplikácie <xliff:g id="APP_2">%2$s</xliff:g>?"</string>
@@ -922,8 +925,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"Otvoriť <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"Nastavenia bublín aplikácie <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"Povoliť bubliny z aplikácie <xliff:g id="APP_NAME">%1$s</xliff:g>?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"Spravovať"</string>
<string name="no_bubbles" msgid="337101288173078247">"Zamietnuť"</string>
<string name="yes_bubbles" msgid="668809525728633841">"Povoliť"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"Spýtať sa neskôr"</string>
diff --git a/packages/SystemUI/res/values-sl/strings.xml b/packages/SystemUI/res/values-sl/strings.xml
index e7eeae58079a..584e4c83906c 100644
--- a/packages/SystemUI/res/values-sl/strings.xml
+++ b/packages/SystemUI/res/values-sl/strings.xml
@@ -67,7 +67,7 @@
<string name="usb_disable_contaminant_detection" msgid="2103905315747120033">"Omogoči USB"</string>
<string name="compat_mode_on" msgid="6623839244840638213">"Povečava čez cel zaslon"</string>
<string name="compat_mode_off" msgid="4434467572461327898">"Raztegnitev čez zaslon"</string>
- <string name="global_action_screenshot" msgid="8329831278085426283">"Posnetek zaslona"</string>
+ <string name="global_action_screenshot" msgid="8329831278085426283">"Posnetek"</string>
<string name="screenshot_saving_ticker" msgid="7403652894056693515">"Shranjev. posnetka zaslona ..."</string>
<string name="screenshot_saving_title" msgid="8242282144535555697">"Shranjevanje posnetka zaslona ..."</string>
<string name="screenshot_saved_title" msgid="5637073968117370753">"Posnetek zaslona je shranjen"</string>
@@ -454,6 +454,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"Tega ne prikaži več"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"Izbriši vse"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"Upravljanje"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"Prikazovanje obvestil je začasno zaustavljeno z načinom »ne moti«"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"Začni zdaj"</string>
<string name="empty_shade_text" msgid="708135716272867002">"Ni obvestil"</string>
@@ -533,8 +537,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"Zaslon je pripet"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"S tem ostane zaslon viden, dokler ga ne odpnete. Če ga želite odpeti, hkrati pridržite gumba za nazaj in pregled."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"S tem ostane zaslon viden, dokler ga ne odpnete. Če ga želite odpeti, hkrati pridržite gumba za nazaj in za začetni zaslon."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"S tem ostane zaslon viden, dokler ga ne odpnete. Če ga želite odpeti, povlecite navzgor in pridržite."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"S tem ostane zaslon viden, dokler ga ne odpnete. Če ga želite odpeti, pridržite gumb za pregled."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"S tem ostane zaslon viden, dokler ga ne odpnete. Če ga želite odpeti, pridržite gumb za začetni zaslon."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"Če želite odpeti ta zaslon, hkrati pridržite gumba za nazaj in za pregled."</string>
@@ -638,13 +641,13 @@
<string name="inline_block_button" msgid="8735843688021655065">"Blokiraj"</string>
<string name="inline_keep_button" msgid="6665940297019018232">"Prikazuj še naprej"</string>
<string name="inline_minimize_button" msgid="966233327974702195">"Minimiraj"</string>
- <string name="inline_silent_button_silent" msgid="6904727667411781466">"Brez zvočnega opozorila"</string>
+ <string name="inline_silent_button_silent" msgid="6904727667411781466">"Diskretno"</string>
<string name="inline_silent_button_stay_silent" msgid="6308371431217601009">"Še naprej prikazuj brez zvoka"</string>
<string name="inline_silent_button_alert" msgid="2449191160203602471">"Z zvočnim opozorilom"</string>
<string name="inline_silent_button_keep_alerting" msgid="327696842264359693">"Še naprej opozarjaj"</string>
<string name="inline_turn_off_notifications" msgid="8635596135532202355">"Izklopi obvestila"</string>
<string name="inline_keep_showing_app" msgid="1723113469580031041">"Želite, da so obvestila te aplikacije še naprej prikazana?"</string>
- <string name="notification_silence_title" msgid="7352089096356977930">"Brez zvočnega opozorila"</string>
+ <string name="notification_silence_title" msgid="7352089096356977930">"Diskretno"</string>
<string name="notification_alert_title" msgid="3966526305405016221">"Prednostno"</string>
<string name="notification_channel_summary_low" msgid="1065819618107531284">"Nemoteč prikaz samo na poteznem zaslonu z obvestili. Vedno tiho."</string>
<string name="notification_channel_summary_low_status" msgid="2702170424808743755">"Prikaz pod prednostnimi obvestili. Vedno tiho."</string>
@@ -891,7 +894,7 @@
<string name="running_foreground_services_title" msgid="381024150898615683">"Aplikacije, ki se izvajajo v ozadju"</string>
<string name="running_foreground_services_msg" msgid="6326247670075574355">"Dotaknite se za prikaz podrobnosti porabe akumulatorja in prenosa podatkov"</string>
<string name="mobile_data_disable_title" msgid="1068272097382942231">"Želite izklopiti prenos podatkov v mobilnih omrežjih?"</string>
- <string name="mobile_data_disable_message" msgid="4756541658791493506">"Dostopa do podatkov ali interneta ne boste imeli prek <xliff:g id="CARRIER">%s</xliff:g>. Internet bo na voljo samo prek povezave Wi-Fi."</string>
+ <string name="mobile_data_disable_message" msgid="4756541658791493506">"Prek operaterja <xliff:g id="CARRIER">%s</xliff:g> ne boste imeli dostopa do podatkovne povezave ali interneta. Internet bo na voljo samo prek povezave Wi-Fi."</string>
<string name="mobile_data_disable_message_default_carrier" msgid="6078110473451946831">"svojega operaterja"</string>
<string name="touch_filtered_warning" msgid="8671693809204767551">"Ker aplikacija zakriva zahtevo za dovoljenje, z nastavitvami ni mogoče preveriti vašega odziva."</string>
<string name="slice_permission_title" msgid="7465009437851044444">"Želite dovoliti, da aplikacija <xliff:g id="APP_0">%1$s</xliff:g> prikaže izreze aplikacije <xliff:g id="APP_2">%2$s</xliff:g>?"</string>
@@ -922,8 +925,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"Odpri aplikacijo <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"Nastavitve za oblačke aplikacije <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"Želite dovoliti oblačke iz aplikacije <xliff:g id="APP_NAME">%1$s</xliff:g>?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"Upravljanje"</string>
<string name="no_bubbles" msgid="337101288173078247">"Zavrni"</string>
<string name="yes_bubbles" msgid="668809525728633841">"Dovoli"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"Vprašaj me pozneje"</string>
diff --git a/packages/SystemUI/res/values-sq/strings.xml b/packages/SystemUI/res/values-sq/strings.xml
index 001af8d0703b..dae69b2c866d 100644
--- a/packages/SystemUI/res/values-sq/strings.xml
+++ b/packages/SystemUI/res/values-sq/strings.xml
@@ -448,6 +448,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"Mos e shfaq sërish"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"Pastroji të gjitha"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"Menaxho"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"Njoftimet janë vendosur në pauzë nga modaliteti \"Mos shqetëso\""</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"Fillo tani"</string>
<string name="empty_shade_text" msgid="708135716272867002">"Asnjë njoftim"</string>
@@ -527,8 +531,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"Ekrani u gozhdua"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"Kjo e ruan në pamje deri sa ta heqësh nga gozhdimi. Prek dhe mbaj të shtypur \"Prapa\" dhe \"Përmbledhje\" për ta hequr nga gozhdimi."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"Kjo e ruan në pamje deri sa ta heqësh nga gozhdimi. Prek dhe mbaj të shtypur \"Prapa\" dhe \"Kreu\" për ta hequr nga gozhdimi."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"Kjo e ruan në pamje deri sa ta zhgozhdosh. Rrëshqit shpejt lart dhe mbaje të shtypur për ta hequr zhgozhduar."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"Kjo e ruan në pamje deri sa ta heqësh nga gozhdimi. Prek dhe mbaj të shtypur \"Përmbledhje\" për ta hequr nga gozhdimi."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"Kjo e ruan në pamje deri sa ta heqësh nga gozhdimi. Prek dhe mbaj të shtypur \"Kreu\" për ta hequr nga gozhdimi."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"Për të hequr gozhdimin e këtij ekrani, prek dhe mbaj butonat \"Prapa\" dhe \"Përmbledhja\"."</string>
@@ -912,8 +915,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"Hap <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"Cilësimet për flluskat e <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"Të lejohen flluskat nga <xliff:g id="APP_NAME">%1$s</xliff:g>?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"Menaxho"</string>
<string name="no_bubbles" msgid="337101288173078247">"Refuzo"</string>
<string name="yes_bubbles" msgid="668809525728633841">"Lejo"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"Më pyet më vonë"</string>
diff --git a/packages/SystemUI/res/values-sr/strings.xml b/packages/SystemUI/res/values-sr/strings.xml
index a0a0cbfc92a9..39e3677267f2 100644
--- a/packages/SystemUI/res/values-sr/strings.xml
+++ b/packages/SystemUI/res/values-sr/strings.xml
@@ -208,10 +208,10 @@
<string name="accessibility_notification_dismissed" msgid="854211387186306927">"Обавештење је одбачено."</string>
<string name="accessibility_desc_notification_shade" msgid="4690274844447504208">"Прозор са обавештењима."</string>
<string name="accessibility_desc_quick_settings" msgid="6186378411582437046">"Брза подешавања."</string>
- <string name="accessibility_desc_lock_screen" msgid="5625143713611759164">"Закључани екран."</string>
+ <string name="accessibility_desc_lock_screen" msgid="5625143713611759164">"Закључан екран."</string>
<string name="accessibility_desc_settings" msgid="3417884241751434521">"Подешавања"</string>
<string name="accessibility_desc_recent_apps" msgid="4876900986661819788">"Преглед."</string>
- <string name="accessibility_desc_work_lock" msgid="4288774420752813383">"Закључани екран за посао"</string>
+ <string name="accessibility_desc_work_lock" msgid="4288774420752813383">"Закључан екран за посао"</string>
<string name="accessibility_desc_close" msgid="7479755364962766729">"Затвори"</string>
<string name="accessibility_quick_settings_wifi" msgid="5518210213118181692">"<xliff:g id="SIGNAL">%1$s</xliff:g>."</string>
<string name="accessibility_quick_settings_wifi_changed_off" msgid="8716484460897819400">"Wi-Fi је искључен."</string>
@@ -451,6 +451,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"Не приказуј поново"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"Обриши све"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"Управљајте"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"Обавештења су паузирана режимом Не узнемиравај"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"Започни одмах"</string>
<string name="empty_shade_text" msgid="708135716272867002">"Нема обавештења"</string>
@@ -530,8 +534,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"Екран је закачен"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"На овај начин се ово стално приказује док га не откачите. Додирните и задржите Назад и Преглед да бисте га откачили."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"На овај начин се ово стално приказује док га не откачите. Додирните и задржите Назад и Почетна да бисте га откачили."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"На овај начин се стално приказује док га не откачите. Превуците нагоре и задржите да бисте га откачили."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"На овај начин се ово стално приказује док га не откачите. Додирните и задржите Преглед да бисте га откачили."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"На овај начин се ово стално приказује док га не откачите. Додирните и задржите Почетна да бисте га откачили."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"Да бисте откачили овај екран, додирните и задржите дугмад Назад и Преглед"</string>
@@ -823,7 +826,7 @@
<string name="accessibility_quick_settings_open_settings" msgid="7806613775728380737">"Отвори подешавања за <xliff:g id="ID_1">%s</xliff:g>."</string>
<string name="accessibility_quick_settings_edit" msgid="7839992848995240393">"Измени редослед подешавања."</string>
<string name="accessibility_quick_settings_page" msgid="5032979051755200721">"<xliff:g id="ID_1">%1$d</xliff:g>. страна од <xliff:g id="ID_2">%2$d</xliff:g>"</string>
- <string name="tuner_lock_screen" msgid="5755818559638850294">"Закључани екран"</string>
+ <string name="tuner_lock_screen" msgid="5755818559638850294">"Закључан екран"</string>
<string name="pip_phone_expand" msgid="5889780005575693909">"Прошири"</string>
<string name="pip_phone_minimize" msgid="1079119422589131792">"Умањи"</string>
<string name="pip_phone_close" msgid="8416647892889710330">"Затвори"</string>
@@ -917,8 +920,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"Отворите <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"Подешавања за <xliff:g id="APP_NAME">%1$s</xliff:g> облачиће"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"Желите ли да омогућите облачиће из апликације <xliff:g id="APP_NAME">%1$s</xliff:g>?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"Управљајте"</string>
<string name="no_bubbles" msgid="337101288173078247">"Одбиј"</string>
<string name="yes_bubbles" msgid="668809525728633841">"Дозволи"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"Питај ме касније"</string>
diff --git a/packages/SystemUI/res/values-sv/strings.xml b/packages/SystemUI/res/values-sv/strings.xml
index 084a38879587..83ec18fabaaf 100644
--- a/packages/SystemUI/res/values-sv/strings.xml
+++ b/packages/SystemUI/res/values-sv/strings.xml
@@ -448,6 +448,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"Visa inte igen"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"Rensa alla"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"Hantera"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"Aviseringar har pausats via Stör ej"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"Starta nu"</string>
<string name="empty_shade_text" msgid="708135716272867002">"Inga aviseringar"</string>
@@ -527,8 +531,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"Skärmen har fästs"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"Skärmen visas tills du lossar den. Tryck länge på Tillbaka och Översikt om du vill lossa skärmen."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"Skärmen visas tills du lossar den. Tryck länge på Tillbaka och Startsida om du vill lossa skärmen."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"Skärmen visas tills du lossar den. Svep uppåt och håll kvar fingret om du vill lossa skärmen."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"Skärmen visas tills du lossar den. Tryck länge på Översikt om du vill lossa skärmen."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"Skärmen visas tills du lossar den. Tryck länge på Startsida om du vill lossa skärmen."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"Om du vill lossa skärmen trycker du länge på knapparna Tillbaka och Översikt"</string>
@@ -912,8 +915,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"Öppna <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"Inställningar för <xliff:g id="APP_NAME">%1$s</xliff:g>-bubblor"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"Vill du tillåta bubblor från <xliff:g id="APP_NAME">%1$s</xliff:g>?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"Hantera"</string>
<string name="no_bubbles" msgid="337101288173078247">"Neka"</string>
<string name="yes_bubbles" msgid="668809525728633841">"Tillåt"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"Fråga senare"</string>
diff --git a/packages/SystemUI/res/values-sw/strings.xml b/packages/SystemUI/res/values-sw/strings.xml
index 0191319f1560..4652dc7d8557 100644
--- a/packages/SystemUI/res/values-sw/strings.xml
+++ b/packages/SystemUI/res/values-sw/strings.xml
@@ -448,6 +448,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"Usionyeshe tena"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"Futa zote"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"Dhibiti"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"Kipengele cha Usinisumbue kimesitisha arifa"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"Anza sasa"</string>
<string name="empty_shade_text" msgid="708135716272867002">"Hakuna arifa"</string>
@@ -527,8 +531,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"Skrini imebandikwa"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"Hali hii huifanya ionekane hadi utakapoibandua. Gusa na ushikilie kipengele cha Nyuma na Muhtasari ili ubandue."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"Hali hii huifanya ionekane hadi utakapoibandua. Gusa na ushikilie kitufe cha kurudisha Nyuma na cha Mwanzo kwa pamoja ili ubandue."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"Hali hii huifanya ionekane hadi utakapoibandua. Telezesha kidole juu na ushikilie ili uibandue."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"Hali hii huifanya ionekane hadi utakapoibandua. Gusa na ushikilie kipengele cha Muhtasari ili ubandue."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"Hali hii huifanya ionekane hadi utakapoibandua. Gusa na ushikilie kitufe cha Mwanzo ili ubandue."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"Ili ubandue skrini hii, gusa na ushikilie kitufe cha Nyuma na Muhtasari"</string>
@@ -912,8 +915,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"Fungua <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"Mipangilio ya viputo vya <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"Je, ungependa kuruhusu viputo kutoka <xliff:g id="APP_NAME">%1$s</xliff:g>?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"Dhibiti"</string>
<string name="no_bubbles" msgid="337101288173078247">"Kataa"</string>
<string name="yes_bubbles" msgid="668809525728633841">"Ruhusu"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"Niulize baadaye"</string>
diff --git a/packages/SystemUI/res/values-ta/strings.xml b/packages/SystemUI/res/values-ta/strings.xml
index 6c849f360b55..6088b52974cf 100644
--- a/packages/SystemUI/res/values-ta/strings.xml
+++ b/packages/SystemUI/res/values-ta/strings.xml
@@ -50,7 +50,7 @@
<string name="usb_accessory_permission_prompt" msgid="2465531696941369047">"<xliff:g id="USB_ACCESSORY">%2$s</xliff:g>ஐ அணுக, <xliff:g id="APPLICATION">%1$s</xliff:g> ஆப்ஸை அனுமதிக்கவா?"</string>
<string name="usb_device_confirm_prompt" msgid="7440562274256843905">"<xliff:g id="USB_DEVICE">%2$s</xliff:g>ஐக் கையாள, <xliff:g id="APPLICATION">%1$s</xliff:g> பயன்பாட்டைத் திறக்கவா?"</string>
<string name="usb_accessory_confirm_prompt" msgid="4333670517539993561">"<xliff:g id="USB_ACCESSORY">%2$s</xliff:g>ஐக் கையாள, <xliff:g id="APPLICATION">%1$s</xliff:g> பயன்பாட்டைத் திறக்கவா?"</string>
- <string name="usb_accessory_uri_prompt" msgid="513450621413733343">"நிறுவிய பயன்பாடுகள் எதுவும், USB துணைக்கருவியுடன் இயங்காது. <xliff:g id="URL">%1$s</xliff:g> இல் துணைக்கருவி குறித்து மேலும் அறிக"</string>
+ <string name="usb_accessory_uri_prompt" msgid="513450621413733343">"நிறுவிய ஆப்ஸ் எதுவும், USB துணைக்கருவியுடன் இயங்காது. <xliff:g id="URL">%1$s</xliff:g> இல் துணைக்கருவி குறித்து மேலும் அறிக"</string>
<string name="title_usb_accessory" msgid="4966265263465181372">"USB துணைக்கருவி"</string>
<string name="label_view" msgid="6304565553218192990">"காட்சி"</string>
<string name="always_use_device" msgid="4015357883336738417">"<xliff:g id="USB_DEVICE">%2$s</xliff:g> இணைக்கப்பட்டிருக்கையில், <xliff:g id="APPLICATION">%1$s</xliff:g>ஐ எப்போதும் திற"</string>
@@ -448,6 +448,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"மீண்டும் காட்டாதே"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"எல்லாவற்றையும் அழி"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"அறிவிப்புகளை நிர்வகி"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"\'தொந்தரவு செய்ய வேண்டாம்\' அம்சத்தின் மூலம் அறிவிப்புகள் இடைநிறுத்தப்பட்டுள்ளன"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"இப்போது தொடங்கு"</string>
<string name="empty_shade_text" msgid="708135716272867002">"அறிவிப்புகள் இல்லை"</string>
@@ -638,22 +642,14 @@
<string name="inline_silent_button_keep_alerting" msgid="327696842264359693">"தொடர்ந்து விழிப்பூட்டு"</string>
<string name="inline_turn_off_notifications" msgid="8635596135532202355">"அறிவிப்புகளை முடக்கு"</string>
<string name="inline_keep_showing_app" msgid="1723113469580031041">"இந்தப் பயன்பாட்டின் அறிவிப்புகளைத் தொடர்ந்து காட்டவா?"</string>
- <!-- no translation found for notification_silence_title (7352089096356977930) -->
- <skip />
- <!-- no translation found for notification_alert_title (3966526305405016221) -->
- <skip />
- <!-- no translation found for notification_channel_summary_low (1065819618107531284) -->
- <skip />
- <!-- no translation found for notification_channel_summary_low_status (2702170424808743755) -->
- <skip />
- <!-- no translation found for notification_channel_summary_low_lock (7966605244472624458) -->
- <skip />
- <!-- no translation found for notification_channel_summary_low_status_lock (7012562768950012739) -->
- <skip />
- <!-- no translation found for notification_channel_summary_default (3847289783382316019) -->
- <skip />
- <!-- no translation found for notification_unblockable_desc (4556908766584964102) -->
- <skip />
+ <string name="notification_silence_title" msgid="7352089096356977930">"ஜென்டில்"</string>
+ <string name="notification_alert_title" msgid="3966526305405016221">"முன்னுரிமைப்படுத்தப்பட்டது"</string>
+ <string name="notification_channel_summary_low" msgid="1065819618107531284">"கீழ் இழுக்கும் ஷேடில் வரும் அறிவிப்புகளில் மட்டும் கவனம் செலுத்த உதவுகிறது. எப்போதும் நிசப்தம்."</string>
+ <string name="notification_channel_summary_low_status" msgid="2702170424808743755">"குறைந்த முன்னுரிமைப் பெற்ற அறிவிப்புகளைக் காட்டும். எப்போதும் நிசப்தம்."</string>
+ <string name="notification_channel_summary_low_lock" msgid="7966605244472624458">"குறைந்த முன்னுரிமைப் பெற்ற அறிவிப்புகளைக் காட்டும். எப்போதும் நிசப்தம்."</string>
+ <string name="notification_channel_summary_low_status_lock" msgid="7012562768950012739">"குறைந்த முன்னுரிமைப் பெற்ற அறிவிப்புகளைக் காட்டும். எப்போதும் நிசப்தம்."</string>
+ <string name="notification_channel_summary_default" msgid="3847289783382316019">"ஒலி &amp; நிலைப் பட்டி ஐகான் மூலம் உங்கள் கவனத்தைப் பெறுகிறது. பூட்டுத் திரையில் காட்டும்."</string>
+ <string name="notification_unblockable_desc" msgid="4556908766584964102">"இந்த அறிவிப்புகளை மாற்ற இயலாது."</string>
<string name="notification_multichannel_desc" msgid="4695920306092240550">"இந்த அறிவுப்புக் குழுக்களை இங்கே உள்ளமைக்க இயலாது"</string>
<string name="notification_delegate_header" msgid="2857691673814814270">"ப்ராக்ஸியான அறிவிப்பு"</string>
<string name="appops_camera" msgid="8100147441602585776">"இந்த ஆப்ஸானது கேமராவை உபயோகிக்கிறது."</string>
@@ -872,7 +868,7 @@
<string name="instant_apps_title" msgid="8738419517367449783">"<xliff:g id="APP">%1$s</xliff:g> இயங்குகிறது"</string>
<string name="instant_apps_message" msgid="1183313016396018086">"நிறுவ வேண்டிய தேவையில்லாமல் ஆப்ஸ் திறக்கப்பட்டது."</string>
<string name="instant_apps_message_with_help" msgid="6179830437630729747">"நிறுவ வேண்டிய தேவையில்லாமல் ஆப்ஸ் திறக்கப்பட்டது. மேலும் அறியத் தட்டவும்."</string>
- <string name="app_info" msgid="6856026610594615344">"பயன்பாட்டுத் தகவல்"</string>
+ <string name="app_info" msgid="6856026610594615344">"ஆப்ஸ் தகவல்"</string>
<string name="go_to_web" msgid="2650669128861626071">"உலாவிக்குச் செல்"</string>
<string name="mobile_data" msgid="7094582042819250762">"மொபைல் டேட்டா"</string>
<string name="mobile_data_text_format" msgid="3526214522670876454">"<xliff:g id="ID_1">%1$s</xliff:g> — <xliff:g id="ID_2">%2$s</xliff:g>"</string>
@@ -889,7 +885,7 @@
<string name="running_foreground_services_title" msgid="381024150898615683">"பின்னணியில் இயங்கும் பயன்பாடுகள்"</string>
<string name="running_foreground_services_msg" msgid="6326247670075574355">"பேட்டரி மற்றும் டேட்டா உபயோக விவரங்களைக் காண, தட்டவும்"</string>
<string name="mobile_data_disable_title" msgid="1068272097382942231">"மொபைல் டேட்டாவை ஆஃப் செய்யவா?"</string>
- <string name="mobile_data_disable_message" msgid="4756541658791493506">"<xliff:g id="CARRIER">%s</xliff:g> மொபைல் நிறுவனத்தின் மூலம் டேட்டா அல்லது இணையத்தை உங்களால் பயன்படுத்த முடியாது. வைஃபை வழியாக மட்டுமே இணையத்தைப் பயன்படுத்த முடியும்."</string>
+ <string name="mobile_data_disable_message" msgid="4756541658791493506">"<xliff:g id="CARRIER">%s</xliff:g> மூலம் டேட்டா அல்லது இணையத்தை உங்களால் பயன்படுத்த முடியாது. வைஃபை வழியாக மட்டுமே இணையத்தைப் பயன்படுத்த முடியும்."</string>
<string name="mobile_data_disable_message_default_carrier" msgid="6078110473451946831">"உங்கள் மொபைல் நிறுவனம்"</string>
<string name="touch_filtered_warning" msgid="8671693809204767551">"அனுமதிக் கோரிக்கையை ஆப்ஸ் மறைப்பதால், அமைப்புகளால் உங்கள் பதிலைச் சரிபார்க்க முடியாது."</string>
<string name="slice_permission_title" msgid="7465009437851044444">"<xliff:g id="APP_0">%1$s</xliff:g> ஆப்ஸை, <xliff:g id="APP_2">%2$s</xliff:g> பயன்பாட்டின் விழிப்பூட்டல்களைக் காண்பிக்க அனுமதிக்கவா?"</string>
diff --git a/packages/SystemUI/res/values-te/strings.xml b/packages/SystemUI/res/values-te/strings.xml
index 331542d65843..bb8c3d115067 100644
--- a/packages/SystemUI/res/values-te/strings.xml
+++ b/packages/SystemUI/res/values-te/strings.xml
@@ -448,6 +448,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"మళ్లీ చూపవద్దు"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"అన్నీ క్లియర్ చేయండి"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"నిర్వహించండి"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"అంతరాయం కలిగించవద్దు ద్వారా నోటిఫికేషన్‌లు పాజ్ చేయబడ్డాయి"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"ఇప్పుడే ప్రారంభించు"</string>
<string name="empty_shade_text" msgid="708135716272867002">"నోటిఫికేషన్‌లు లేవు"</string>
@@ -527,8 +531,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"స్క్రీన్ పిన్ చేయబడింది"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"దీని వలన మీరు అన్‌పిన్ చేసే వరకు ఇది వీక్షణలో ఉంచబడుతుంది. అన్‌పిన్ చేయడానికి వెనుకకు మరియు స్థూలదృష్టి తాకి &amp; అలాగే పట్టుకోండి."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"దీని వలన మీరు అన్‌పిన్ చేసే వరకు ఇది వీక్షణలో ఉంచబడుతుంది. అన్‌పిన్ చేయడానికి వెనుకకు మరియు హోమ్‌ని తాకి &amp; అలాగే పట్టుకోండి."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"మీరు అన్‌పిన్ చేసే వరకు ఇది వీక్షణలో ఉంచబడుతుంది. అన్‌పిన్ చేయడానికి, పైకి స్వైప్ చేసి &amp; పట్టుకోండి."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"దీని వలన మీరు అన్‌పిన్ చేసే వరకు ఇది వీక్షణలో ఉంచబడుతుంది. అన్‌పిన్ చేయడానికి స్థూలదృష్టిని తాకి &amp; అలాగే పట్టుకోండి."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"దీని వలన మీరు అన్‌పిన్ చేసే వరకు ఇది వీక్షణలో ఉంచబడుతుంది. అన్‌పిన్ చేయడానికి హోమ్‌ని తాకి &amp; అలాగే పట్టుకోండి."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"ఈ స్క్రీన్‌ను అన్‌పిన్ చేయడానికి, వెనుకకు మరియు అవలోకనం బటన్‌లను తాకి &amp; అలాగే పట్టుకోండి"</string>
@@ -644,7 +647,7 @@
<string name="notification_channel_summary_low_status" msgid="2702170424808743755">"ప్రాధాన్యత గల నోటిఫికేషన్‌ల దిగువన ప్రదర్శిస్తుంది. ఎల్లప్పుడూ నిశబ్దంగా ఉంచు."</string>
<string name="notification_channel_summary_low_lock" msgid="7966605244472624458">"ప్రాధాన్యత గల నోటిఫికేషన్‌ల దిగువన ప్రదర్శిస్తుంది. ఎల్లప్పుడూ నిశబ్దంగా ఉంచు."</string>
<string name="notification_channel_summary_low_status_lock" msgid="7012562768950012739">"ప్రాధాన్యత గల నోటిఫికేషన్‌ల దిగువన ప్రదర్శిస్తుంది. ఎల్లప్పుడూ నిశబ్దంగా ఉంచు."</string>
- <string name="notification_channel_summary_default" msgid="3847289783382316019">"శబ్దం &amp; స్థితి బార్ చిహ్నం ద్వారా మిమ్మల్ని దృష్టి వహించే విధంగా చేస్తుంది. లాక్ స్క్రీన్‌‌పై చూపుతుంది."</string>
+ <string name="notification_channel_summary_default" msgid="3847289783382316019">"శబ్దం &amp; స్టేటస్ బార్ చిహ్నం ద్వారా మీరు దృష్టి సారించేలా చేస్తుంది. లాక్ స్క్రీన్‌‌పై చూపుతుంది."</string>
<string name="notification_unblockable_desc" msgid="4556908766584964102">"ఈ నోటిఫికేషన్‌లను సవరించడం వీలుపడదు."</string>
<string name="notification_multichannel_desc" msgid="4695920306092240550">"ఈ నోటిఫికేషన్‌ల సమూహాన్ని ఇక్కడ కాన్ఫిగర్ చేయలేము"</string>
<string name="notification_delegate_header" msgid="2857691673814814270">"ప్రాక్సీ చేయబడిన నోటిఫికేషన్"</string>
@@ -912,8 +915,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"<xliff:g id="APP_NAME">%1$s</xliff:g>ని తెరువు"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"<xliff:g id="APP_NAME">%1$s</xliff:g> బబుల్‌ల సెట్టింగ్‌లు"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"<xliff:g id="APP_NAME">%1$s</xliff:g> నుండి బబుల్‌లను అనుమతించాలా?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"నిర్వహించండి"</string>
<string name="no_bubbles" msgid="337101288173078247">"తిరస్కరించు"</string>
<string name="yes_bubbles" msgid="668809525728633841">"అనుమతించు"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"నన్ను తర్వాత అడగు"</string>
diff --git a/packages/SystemUI/res/values-th/strings.xml b/packages/SystemUI/res/values-th/strings.xml
index 5a93381fb57a..5e3359c23c36 100644
--- a/packages/SystemUI/res/values-th/strings.xml
+++ b/packages/SystemUI/res/values-th/strings.xml
@@ -448,6 +448,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"ไม่ต้องแสดงข้อความนี้อีก"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"ล้างทั้งหมด"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"จัดการ"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"หยุดการแจ้งเตือนชั่วคราวโดย \"ห้ามรบกวน\""</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"เริ่มเลย"</string>
<string name="empty_shade_text" msgid="708135716272867002">"ไม่มีการแจ้งเตือน"</string>
@@ -527,8 +531,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"ตรึงหน้าจอแล้ว"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"การดำเนินการนี้จะแสดงหน้าจอนี้ไว้เสมอจนกว่าคุณจะเลิกตรึง แตะ \"กลับ\" และ \"ภาพรวม\" ค้างไว้เพื่อเลิกตรึง"</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"การดำเนินการนี้จะแสดงหน้าจอนี้ไว้เสมอจนกว่าคุณจะเลิกตรึง แตะ \"กลับ\" และ \"หน้าแรก\" ค้างไว้เพื่อเลิกตรึง"</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"วิธีนี้ช่วยให้เห็นหน้าจอตลอดจนกว่าจะเลิกตรึง เลื่อนขึ้นค้างไว้เพื่อเลิกตรึง"</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"การดำเนินการนี้จะแสดงหน้าจอนี้ไว้เสมอจนกว่าคุณจะเลิกตรึง แตะ \"ภาพรวม\" ค้างไว้เพื่อเลิกตรึง"</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"การดำเนินการนี้จะแสดงหน้าจอนี้ไว้เสมอจนกว่าคุณจะเลิกตรึง แตะ \"หน้าแรก\" ค้างไว้เพื่อเลิกตรึง"</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"หากต้องการเลิกตรึงหน้าจอนี้ ให้แตะปุ่ม \"กลับ\" และ \"ภาพรวม\" ค้างไว้"</string>
@@ -881,7 +884,7 @@
<string name="running_foreground_services_title" msgid="381024150898615683">"แอปที่กำลังทำงานในเบื้องหลัง"</string>
<string name="running_foreground_services_msg" msgid="6326247670075574355">"แตะเพื่อดูรายละเอียดเกี่ยวกับแบตเตอรี่และปริมาณการใช้อินเทอร์เน็ต"</string>
<string name="mobile_data_disable_title" msgid="1068272097382942231">"ปิดเน็ตมือถือไหม"</string>
- <string name="mobile_data_disable_message" msgid="4756541658791493506">"คุณจะใช้เน็ตมือถือหรืออินเทอร์เน็ตผ่าน <xliff:g id="CARRIER">%s</xliff:g> ไม่ได้ และจะใช้อินเทอร์เน็ตได้ผ่าน Wi-Fi เท่านั้น"</string>
+ <string name="mobile_data_disable_message" msgid="4756541658791493506">"คุณจะใช้เน็ตมือถือหรืออินเทอร์เน็ตผ่าน <xliff:g id="CARRIER">%s</xliff:g> ไม่ได้ แต่จะใช้ผ่าน Wi-Fi ได้เท่านั้น"</string>
<string name="mobile_data_disable_message_default_carrier" msgid="6078110473451946831">"ผู้ให้บริการของคุณ"</string>
<string name="touch_filtered_warning" msgid="8671693809204767551">"เนื่องจากแอปหนึ่งได้บดบังคำขอสิทธิ์ ระบบจึงไม่สามารถยืนยันคำตอบของคุณสำหรับการตั้งค่าได้"</string>
<string name="slice_permission_title" msgid="7465009437851044444">"อนุญาตให้ <xliff:g id="APP_0">%1$s</xliff:g> แสดงส่วนต่างๆ ของ <xliff:g id="APP_2">%2$s</xliff:g>"</string>
@@ -905,15 +908,14 @@
<string name="privacy_type_camera" msgid="1676604631892420333">"กล้องถ่ายรูป"</string>
<string name="privacy_type_location" msgid="6435497989657286700">"ตำแหน่ง"</string>
<string name="privacy_type_microphone" msgid="4153045784928554506">"ไมโครโฟน"</string>
- <string name="sensor_privacy_mode" msgid="8982771253020769598">"เซ็นเซอร์ปิดอยู่"</string>
+ <string name="sensor_privacy_mode" msgid="8982771253020769598">"ปิดเซ็นเซอร์"</string>
<string name="device_services" msgid="1191212554435440592">"บริการของอุปกรณ์"</string>
<string name="music_controls_no_title" msgid="5236895307087002011">"ไม่มีชื่อ"</string>
<string name="restart_button_description" msgid="2035077840254950187">"แตะเพื่อรีสตาร์ทแอปนี้และแสดงแบบเต็มหน้าจอ"</string>
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"เปิด <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"การตั้งค่าลูกโป่ง <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"อนุญาตลูกโป่งจาก <xliff:g id="APP_NAME">%1$s</xliff:g> ไหม"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"จัดการ"</string>
<string name="no_bubbles" msgid="337101288173078247">"ปฏิเสธ"</string>
<string name="yes_bubbles" msgid="668809525728633841">"อนุญาต"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"ถามฉันทีหลัง"</string>
diff --git a/packages/SystemUI/res/values-tl/strings.xml b/packages/SystemUI/res/values-tl/strings.xml
index e69ea973dbf2..88ae2513ec59 100644
--- a/packages/SystemUI/res/values-tl/strings.xml
+++ b/packages/SystemUI/res/values-tl/strings.xml
@@ -448,6 +448,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"Huwag ipakitang muli"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"I-clear lahat"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"Pamahalaan"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"Mga notification na na-pause ng Huwag Istorbohin"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"Magsimula ngayon"</string>
<string name="empty_shade_text" msgid="708135716272867002">"Walang mga notification"</string>
@@ -527,8 +531,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"Naka-pin ang screen"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"Pinapanatili nitong nakikita ito hanggang sa mag-unpin ka. Pindutin nang matagal ang Bumalik at Overview upang mag-unpin."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"Pinapanatili nitong nakikita ito hanggang sa mag-unpin ka. Pindutin nang matagal ang Bumalik at Home upang mag-unpin."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"Pinapanatili nitong nakikita ito hanggang sa mag-unpin ka. Mag-swipe pataas at i-hold para i-unpin."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"Pinapanatili nitong nakikita ito hanggang sa mag-unpin ka. Pindutin nang matagal ang Overview upang mag-unpin."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"Pinapanatili nitong nakikita ito hanggang sa mag-unpin ka. Pindutin nang matagal ang Home upang mag-unpin."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"Upang i-unpin ang screen na ito, pindutin nang matagal ang mga button na Bumalik at Overview"</string>
@@ -912,8 +915,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"Buksan ang <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"Mga setting para sa mga bubble ng <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"Payagan ang mga bubble mula sa <xliff:g id="APP_NAME">%1$s</xliff:g>?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"Pamahalaan"</string>
<string name="no_bubbles" msgid="337101288173078247">"Tanggihan"</string>
<string name="yes_bubbles" msgid="668809525728633841">"Payagan"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"Tanungin ako sa ibang pagkakataon"</string>
diff --git a/packages/SystemUI/res/values-tr/strings.xml b/packages/SystemUI/res/values-tr/strings.xml
index 7897a093262f..6f5346283b68 100644
--- a/packages/SystemUI/res/values-tr/strings.xml
+++ b/packages/SystemUI/res/values-tr/strings.xml
@@ -448,6 +448,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"Bir daha gösterme"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"Tümünü temizle"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"Yönet"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"Bildirimler, Rahatsız Etmeyin özelliği tarafından duraklatıldı"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"Şimdi başlat"</string>
<string name="empty_shade_text" msgid="708135716272867002">"Bildirim yok"</string>
@@ -527,8 +531,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"Ekran sabitlendi"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"Bu işlem, siz sabitlemeyi kaldırana kadar ekranı görünür durumda tutar. Sabitlemeyi kaldırmak için Geri\'ye ve Genel Bakış\'a dokunup basılı tutun."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"Bu işlem, siz sabitlemeyi kaldırana kadar ekranı görünür durumda tutar. Sabitlemeyi kaldırmak için Geri\'ye ve Ana sayfaya dokunup basılı tutun."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"Bu, sabitleme kaldırılana kadar öğenin görünmesini sağlar. Sabitlemeyi kaldırmak için yukarı kaydırıp basılı tutun."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"Bu işlem, siz sabitlemeyi kaldırana kadar ekranı görünür durumda tutar. Sabitlemeyi kaldırmak için Genel bakış\'a dokunup basılı tutun."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"Bu işlem, siz sabitlemeyi kaldırana kadar ekranı görünür durumda tutar. Sabitlemeyi kaldırmak için Ana sayfaya dokunup basılı tutun."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"Bu ekranın sabitlemesini kaldırmak için Geri ve Genel Bakış düğmelerine dokunup basılı tutun"</string>
@@ -640,11 +643,11 @@
<string name="inline_keep_showing_app" msgid="1723113469580031041">"Bu uygulamadan gelen bildirimler gösterilmeye devam edilsin mi?"</string>
<string name="notification_silence_title" msgid="7352089096356977930">"Sessiz"</string>
<string name="notification_alert_title" msgid="3966526305405016221">"Öncelikli"</string>
- <string name="notification_channel_summary_low" msgid="1065819618107531284">"Bildirimleri yalnızca aşağıya açılır gölgede göstererek işinize odaklanmanızı sağlar. Her zaman sessiz."</string>
- <string name="notification_channel_summary_low_status" msgid="2702170424808743755">"Aşağıda öncelikli bildirimleri görüntüler. Her zaman sessiz."</string>
- <string name="notification_channel_summary_low_lock" msgid="7966605244472624458">"Aşağıda öncelikli bildirimleri görüntüler. Her zaman sessiz."</string>
- <string name="notification_channel_summary_low_status_lock" msgid="7012562768950012739">"Aşağıda öncelikli bildirimleri görüntüler. Her zaman sessiz."</string>
- <string name="notification_channel_summary_default" msgid="3847289783382316019">"Ses ve bir durum çubuğu simgesiyle dikkatinizi çeker. Kilit ekranında gösterir."</string>
+ <string name="notification_channel_summary_low" msgid="1065819618107531284">"Bildirimleri yalnızca aşağıya açılır gölgede göstererek işinize odaklanmanızı sağlar. Her zaman sessizdir."</string>
+ <string name="notification_channel_summary_low_status" msgid="2702170424808743755">"Öncelikli bildirimlerin altında görüntülenir. Her zaman sessizdir."</string>
+ <string name="notification_channel_summary_low_lock" msgid="7966605244472624458">"Öncelikli bildirimlerin altında görüntülenir. Her zaman sessizdir."</string>
+ <string name="notification_channel_summary_low_status_lock" msgid="7012562768950012739">"Öncelikli bildirimlerin altında görüntülenir. Her zaman sessizdir."</string>
+ <string name="notification_channel_summary_default" msgid="3847289783382316019">"Ses ve bir durum çubuğu simgesiyle dikkatinizi çeker. Kilit ekranında gösterilir."</string>
<string name="notification_unblockable_desc" msgid="4556908766584964102">"Bu bildirimler değiştirilemez."</string>
<string name="notification_multichannel_desc" msgid="4695920306092240550">"Bu bildirim grubu burada yapılandırılamaz"</string>
<string name="notification_delegate_header" msgid="2857691673814814270">"Proxy uygulanan bildirim"</string>
@@ -912,8 +915,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"<xliff:g id="APP_NAME">%1$s</xliff:g> öğesini açın."</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"<xliff:g id="APP_NAME">%1$s</xliff:g> baloncukları için ayarlar"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"<xliff:g id="APP_NAME">%1$s</xliff:g> baloncuklarına izin verilsin mi?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"Yönet"</string>
<string name="no_bubbles" msgid="337101288173078247">"Reddet"</string>
<string name="yes_bubbles" msgid="668809525728633841">"İzin Ver"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"Daha sonra yeniden sor"</string>
diff --git a/packages/SystemUI/res/values-uk/strings.xml b/packages/SystemUI/res/values-uk/strings.xml
index c5338bbb6894..404caabbb778 100644
--- a/packages/SystemUI/res/values-uk/strings.xml
+++ b/packages/SystemUI/res/values-uk/strings.xml
@@ -340,7 +340,7 @@
<string name="quick_settings_cast_no_wifi" msgid="2696477881905521882">"Wi-Fi не під’єднано"</string>
<string name="quick_settings_brightness_dialog_title" msgid="8599674057673605368">"Яскравість"</string>
<string name="quick_settings_brightness_dialog_auto_brightness_label" msgid="5064982743784071218">"АВТО"</string>
- <string name="quick_settings_inversion_label" msgid="8790919884718619648">"Інвертувати кольори"</string>
+ <string name="quick_settings_inversion_label" msgid="8790919884718619648">"Інвертовані кольори"</string>
<string name="quick_settings_color_space_label" msgid="853443689745584770">"Режим коригування кольору"</string>
<string name="quick_settings_more_settings" msgid="326112621462813682">"Більше налаштувань"</string>
<string name="quick_settings_done" msgid="3402999958839153376">"Готово"</string>
@@ -454,6 +454,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"Більше не показувати"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"Очистити все"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"Керувати"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"Режим \"Не турбувати\" призупинив сповіщення"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"Почати зараз"</string>
<string name="empty_shade_text" msgid="708135716272867002">"Сповіщень немає"</string>
@@ -533,8 +537,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"Екран закріплено"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"Ви постійно бачитимете екран, доки не відкріпите його. Щоб відкріпити екран, натисніть і втримуйте кнопки \"Назад\" та \"Огляд\"."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"Ви бачитимете цей екран, доки не відкріпите його. Для цього натисніть і утримуйте кнопки \"Назад\" та \"Головний екран\"."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"Ви бачитимете цей екран, доки не відкріпите його. Для цього проведіть пальцем угору й утримуйте екран."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"Ви постійно бачитимете екран, доки не відкріпите його. Щоб відкріпити екран, натисніть і втримуйте кнопку \"Огляд\"."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"Ви бачитимете цей екран, доки не відкріпите його. Для цього натисніть і утримуйте кнопку \"Головний екран\"."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"Щоб відкріпити цей екран, натисніть і утримуйте кнопки \"Назад\" та \"Огляд\""</string>
@@ -922,8 +925,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"Відкрити додаток <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"Налаштування спливаючих підказок від додатка <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"Дозволити спливаючі підказки від додатка <xliff:g id="APP_NAME">%1$s</xliff:g>?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"Керувати"</string>
<string name="no_bubbles" msgid="337101288173078247">"Заборонити"</string>
<string name="yes_bubbles" msgid="668809525728633841">"Дозволити"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"Запитати пізніше"</string>
diff --git a/packages/SystemUI/res/values-ur/strings.xml b/packages/SystemUI/res/values-ur/strings.xml
index bb78fe45cc58..7ddd28eb7f34 100644
--- a/packages/SystemUI/res/values-ur/strings.xml
+++ b/packages/SystemUI/res/values-ur/strings.xml
@@ -448,6 +448,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"دوبارہ نہ دکھائیں"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"سبھی کو صاف کریں"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"نظم کریں"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"\'ڈسٹرب نہ کریں\' کے ذریعے اطلاعات کو موقوف کیا گیا"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"ابھی شروع کریں"</string>
<string name="empty_shade_text" msgid="708135716272867002">"کوئی اطلاعات نہیں ہیں"</string>
@@ -527,8 +531,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"اسکرین پن کردہ ہے"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"یہ اسے اس وقت تک نظر میں رکھتا ہے جب تک آپ اس سے پن ہٹا نہیں دیتے۔ پن ہٹانے کیلئے پیچھے اور مجموعی جائزہ بٹنز کو ٹچ کریں اور دبائے رکھیں۔"</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"یہ اس کو اس وقت تک مد نظر رکھتا ہے جب تک آپ اس سے پن نہیں ہٹا دیتے۔ پن ہٹانے کیلئے \"پیچھے\" اور \"ہوم\" بٹنز کو ٹچ کریں اور دبائے رکھیں۔"</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"یہ اس کو اس وقت تک مد نظر رکھتا ہے جب تک آپ اس سے پن نہیں ہٹا دیتے۔ پن ہٹانے کے لیے سوائپ کریں اور پکڑ کر رکھیں۔"</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"یہ اسے اس وقت تک نظر میں رکھتا ہے جب تک آپ اس سے پن ہٹا نہیں دیتے۔ پن ہٹانے کیلئے مجموعی جائزہ بٹن کو ٹچ کریں اور دبائے رکھیں۔"</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"یہ اس کو اس وقت تک مد نظر رکھتا ہے جب تک آپ اس سے پن نہیں ہٹا دیتے۔ پن ہٹانے کیلئے \"ہوم\" بٹن کو ٹچ کریں اور دبائے رکھیں۔"</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"اس اسکرین سے پن ہٹانے کیلئے، \"پیچھے\" اور \"مجموعی جائزہ\" بٹنز کو ٹچ کریں اور دبائے رکھیں"</string>
@@ -639,17 +642,12 @@
<string name="inline_turn_off_notifications" msgid="8635596135532202355">"اطلاعات کو آف کریں"</string>
<string name="inline_keep_showing_app" msgid="1723113469580031041">"اس ایپ کی طرف سے اطلاعات دکھانا جاری رکھیں؟"</string>
<string name="notification_silence_title" msgid="7352089096356977930">"لطیف"</string>
- <string name="notification_alert_title" msgid="3966526305405016221">"ترجیح دی گئی"</string>
- <!-- no translation found for notification_channel_summary_low (1065819618107531284) -->
- <skip />
- <!-- no translation found for notification_channel_summary_low_status (2702170424808743755) -->
- <skip />
- <!-- no translation found for notification_channel_summary_low_lock (7966605244472624458) -->
- <skip />
- <!-- no translation found for notification_channel_summary_low_status_lock (7012562768950012739) -->
- <skip />
- <!-- no translation found for notification_channel_summary_default (3847289783382316019) -->
- <skip />
+ <string name="notification_alert_title" msgid="3966526305405016221">"ترجیحی"</string>
+ <string name="notification_channel_summary_low" msgid="1065819618107531284">"صرف نیچے کی طرف کھینچیں شیڈ میں اطلاعات کے ساتھ فوکس کرنے میں آپ کی مدد کرتا ہے۔ ہمیشہ خاموش۔"</string>
+ <string name="notification_channel_summary_low_status" msgid="2702170424808743755">"کم ترجیحی اطلاعات ڈسپلے کرتا ہے۔ ہمیشہ خاموش۔"</string>
+ <string name="notification_channel_summary_low_lock" msgid="7966605244472624458">"کم ترجیحی اطلاعات ڈسپلے کرتا ہے۔ ہمیشہ خاموش۔"</string>
+ <string name="notification_channel_summary_low_status_lock" msgid="7012562768950012739">"کم ترجیحی اطلاعات ڈسپلے کرتا ہے۔ ہمیشہ خاموش۔"</string>
+ <string name="notification_channel_summary_default" msgid="3847289783382316019">"آواز اور اسٹیٹس بار کے آئیکن کے ساتھ آپ کی توجہ حاصل کرتا ہے۔ مقفل اسکرین پر دکھاتا ہے۔"</string>
<string name="notification_unblockable_desc" msgid="4556908766584964102">"ان اطلاعات کی ترمیم نہیں کی جا سکتی۔"</string>
<string name="notification_multichannel_desc" msgid="4695920306092240550">"اطلاعات کے اس گروپ کو یہاں کنفیگر نہیں کیا جا سکتا"</string>
<string name="notification_delegate_header" msgid="2857691673814814270">"پراکسی اطلاع"</string>
@@ -917,8 +915,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"<xliff:g id="APP_NAME">%1$s</xliff:g> کھولیں"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"<xliff:g id="APP_NAME">%1$s</xliff:g> بلبلوں کے لیے ترتیبات"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"<xliff:g id="APP_NAME">%1$s</xliff:g> کی جانب سے بلبلوں کو اجازت دیں؟"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"نظم کریں"</string>
<string name="no_bubbles" msgid="337101288173078247">"مسترد کریں"</string>
<string name="yes_bubbles" msgid="668809525728633841">"اجازت دیں"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"مجھ سے بعد میں پوچھیں"</string>
diff --git a/packages/SystemUI/res/values-uz/strings.xml b/packages/SystemUI/res/values-uz/strings.xml
index d12b4af5abcf..1314bae7b40f 100644
--- a/packages/SystemUI/res/values-uz/strings.xml
+++ b/packages/SystemUI/res/values-uz/strings.xml
@@ -448,6 +448,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"Boshqa ko‘rsatilmasin"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"Hammasini tozalash"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"Boshqarish"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"Bezovta qilinmasin rejimida bildirishnomalar pauza qilingan"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"Boshlash"</string>
<string name="empty_shade_text" msgid="708135716272867002">"Bildirishnomalar yo‘q"</string>
@@ -527,8 +531,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"Ekran qadaldi"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"Ekran yechilmaguncha u o‘zgarmas holatda qoladi. Uni yechish uchun “Orqaga” va “Umumiy ma’lumot” tugmalarini bosib turing."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"Ekran yechib olinmagunicha u mahkamlangan holatda qoladi. Uni yechish uchun Orqaga va Asosiy tugmalarni birga bosib turing."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"Yechilmaguncha chiqib turadi. Yechish uchun tepaga suring va qoʻlingizni kerakli holatda tutib turing."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"Ekran yechilmaguncha u o‘zgarmas holatda qoladi. Uni yechish uchun “Umumiy ma’lumot” tugmasini bosib turing."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"Ekran yechib olinmagunicha u mahkamlangan holatda qoladi. Uni yechish uchun Orqaga va Asosiy tugmlarni birga bosib turing."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"Bu ekrandan chiqish uchun Orqaga va Menyu tugmalarini bosib turing"</string>
@@ -640,10 +643,10 @@
<string name="inline_keep_showing_app" msgid="1723113469580031041">"Bu ilovadan keladigan bildirishnomalar chiqaversinmi?"</string>
<string name="notification_silence_title" msgid="7352089096356977930">"Tovushsiz"</string>
<string name="notification_alert_title" msgid="3966526305405016221">"Muhim"</string>
- <string name="notification_channel_summary_low" msgid="1065819618107531284">"Sizni chalgʻitmaslik uchun bildirishnomalar faqat maxsus panelda chiqadi. Doim tovushsiz."</string>
- <string name="notification_channel_summary_low_status" msgid="2702170424808743755">"Muhimligi past xabarlar chiqsin. Doim tovushsiz."</string>
- <string name="notification_channel_summary_low_lock" msgid="7966605244472624458">"Muhimligi past xabarlar chiqsin. Doim tovushsiz."</string>
- <string name="notification_channel_summary_low_status_lock" msgid="7012562768950012739">"Muhimligi past xabarlar chiqsin. Doim tovushsiz."</string>
+ <string name="notification_channel_summary_low" msgid="1065819618107531284">"Bildirishnomalar faqat maxsus panelda chiqadi. Doim tovushsiz."</string>
+ <string name="notification_channel_summary_low_status" msgid="2702170424808743755">"Muhimlik darajasi past bildirishnomalarning chiqishi. Doim tovushsiz."</string>
+ <string name="notification_channel_summary_low_lock" msgid="7966605244472624458">"Muhimlik darajasi past bildirishnomalarning chiqishi. Doim tovushsiz."</string>
+ <string name="notification_channel_summary_low_status_lock" msgid="7012562768950012739">"Muhimlik darajasi past bildirishnomalarning chiqishi. Doim tovushsiz."</string>
<string name="notification_channel_summary_default" msgid="3847289783382316019">"Kelgan bildirishnomalarni maxsus tovush va holat paneliga chiqadigan nishoncha orqali bilish mumkin. Bildirishnomalar ekran qulfida ham chiqadi."</string>
<string name="notification_unblockable_desc" msgid="4556908766584964102">"Bu bildirishnomalarni tahrirlash imkonsiz."</string>
<string name="notification_multichannel_desc" msgid="4695920306092240550">"Ushbu bildirishnomalar guruhi bu yerda sozlanmaydi"</string>
@@ -912,8 +915,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"Ochish: <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"<xliff:g id="APP_NAME">%1$s</xliff:g> pufakchalari uchun sozlamalar"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"<xliff:g id="APP_NAME">%1$s</xliff:g> pufakchalariga ruxsat berilsinmi?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"Boshqarish"</string>
<string name="no_bubbles" msgid="337101288173078247">"Rad etish"</string>
<string name="yes_bubbles" msgid="668809525728633841">"Ruxsat"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"Keyinroq soʻralsin"</string>
diff --git a/packages/SystemUI/res/values-vi/strings.xml b/packages/SystemUI/res/values-vi/strings.xml
index 8001cf116ad2..0d6f4efc9599 100644
--- a/packages/SystemUI/res/values-vi/strings.xml
+++ b/packages/SystemUI/res/values-vi/strings.xml
@@ -448,6 +448,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"Không hiển thị lại"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"Xóa tất cả"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"Quản lý"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"Chế độ Không làm phiền đã tạm dừng thông báo"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"Bắt đầu ngay"</string>
<string name="empty_shade_text" msgid="708135716272867002">"Không có thông báo nào"</string>
@@ -527,8 +531,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"Màn hình được ghim"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"Thao tác này sẽ duy trì hiển thị màn hình cho đến khi bạn bỏ ghim. Hãy chạm và giữ Quay lại và Tổng quan để bỏ ghim."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"Thao tác này sẽ duy trì hiển thị màn hình cho đến khi bạn bỏ ghim. Hãy chạm và giữ nút Quay lại và nút Màn hình chính để bỏ ghim."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"Màn hình tiếp tục hiển thị cho tới khi bạn bỏ ghim. Hãy vuốt lên và giữ để bỏ ghim."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"Thao tác này sẽ duy trì hiển thị màn hình cho đến khi bạn bỏ ghim. Hãy chạm và giữ Tổng quan để bỏ ghim."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"Thao tác này sẽ duy trì hiển thị màn hình cho đến khi bạn bỏ ghim. Hãy chạm và giữ nút Màn hình chính để bỏ ghim."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"Để bỏ ghim màn hình này, hãy chạm và giữ nút Quay lại và nút Tổng quan"</string>
@@ -881,7 +884,7 @@
<string name="running_foreground_services_title" msgid="381024150898615683">"Ứng dụng đang chạy trong nền"</string>
<string name="running_foreground_services_msg" msgid="6326247670075574355">"Nhấn để biết chi tiết về mức sử dụng dữ liệu và pin"</string>
<string name="mobile_data_disable_title" msgid="1068272097382942231">"Tắt dữ liệu di động?"</string>
- <string name="mobile_data_disable_message" msgid="4756541658791493506">"Bạn sẽ không có quyền truy cập vào dữ liệu hoặc Internet thông qua <xliff:g id="CARRIER">%s</xliff:g>. Bạn chỉ có thể truy cập Internet thông qua Wi-Fi."</string>
+ <string name="mobile_data_disable_message" msgid="4756541658791493506">"Bạn sẽ không có quyền sử dụng dữ liệu hoặc truy cập Internet thông qua <xliff:g id="CARRIER">%s</xliff:g>. Bạn chỉ có thể truy cập Internet thông qua Wi-Fi."</string>
<string name="mobile_data_disable_message_default_carrier" msgid="6078110473451946831">"nhà mạng của bạn"</string>
<string name="touch_filtered_warning" msgid="8671693809204767551">"Vì ứng dụng đang che khuất yêu cầu cấp quyền nên Cài đặt không thể xác minh câu trả lời của bạn."</string>
<string name="slice_permission_title" msgid="7465009437851044444">"Cho phép <xliff:g id="APP_0">%1$s</xliff:g> hiển thị các lát của <xliff:g id="APP_2">%2$s</xliff:g>?"</string>
@@ -912,8 +915,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"Mở <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"Tùy chọn cài đặt cho bong bóng <xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"Bạn muốn cho phép bong bóng của <xliff:g id="APP_NAME">%1$s</xliff:g>?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"Quản lý"</string>
<string name="no_bubbles" msgid="337101288173078247">"Từ chối"</string>
<string name="yes_bubbles" msgid="668809525728633841">"Cho phép"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"Hỏi tôi sau"</string>
diff --git a/packages/SystemUI/res/values-zh-rCN/strings.xml b/packages/SystemUI/res/values-zh-rCN/strings.xml
index 69210de28129..23c0339b6568 100644
--- a/packages/SystemUI/res/values-zh-rCN/strings.xml
+++ b/packages/SystemUI/res/values-zh-rCN/strings.xml
@@ -448,6 +448,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"不再显示"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"全部清除"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"管理"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"勿扰模式暂停的通知"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"立即开始"</string>
<string name="empty_shade_text" msgid="708135716272867002">"没有通知"</string>
@@ -527,8 +531,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"已固定屏幕"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"这将会固定显示此屏幕,直到您取消固定为止。触摸并按住“返回”和“概览”即可取消固定屏幕。"</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"这将会固定显示此屏幕,直到您取消固定为止。触摸并按住“返回”和“主屏幕”即可取消固定屏幕。"</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"这会使此屏幕固定显示,直到您取消固定为止。向上滑动并按住即可取消固定。"</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"这将会固定显示此屏幕,直到您取消固定为止。触摸并按住“概览”即可取消固定屏幕。"</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"这将会固定显示此屏幕,直到您取消固定为止。触摸并按住“主屏幕”即可取消固定屏幕。"</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"要取消固定此屏幕,请触摸并按住“返回”和“概览”按钮"</string>
@@ -881,7 +884,7 @@
<string name="running_foreground_services_title" msgid="381024150898615683">"在后台运行的应用"</string>
<string name="running_foreground_services_msg" msgid="6326247670075574355">"点按即可详细了解电量和流量消耗情况"</string>
<string name="mobile_data_disable_title" msgid="1068272097382942231">"要关闭移动数据网络吗?"</string>
- <string name="mobile_data_disable_message" msgid="4756541658791493506">"您将无法通过<xliff:g id="CARRIER">%s</xliff:g>获取移动数据访问权限或连接到互联网。您只能通过 WLAN 连接到互联网。"</string>
+ <string name="mobile_data_disable_message" msgid="4756541658791493506">"您将无法通过<xliff:g id="CARRIER">%s</xliff:g>使用移动数据或互联网,只能通过 WLAN 连接到互联网。"</string>
<string name="mobile_data_disable_message_default_carrier" msgid="6078110473451946831">"您的运营商"</string>
<string name="touch_filtered_warning" msgid="8671693809204767551">"由于某个应用遮挡了权限请求界面,因此“设置”应用无法验证您的回应。"</string>
<string name="slice_permission_title" msgid="7465009437851044444">"要允许“<xliff:g id="APP_0">%1$s</xliff:g>”显示“<xliff:g id="APP_2">%2$s</xliff:g>”图块吗?"</string>
diff --git a/packages/SystemUI/res/values-zh-rHK/strings.xml b/packages/SystemUI/res/values-zh-rHK/strings.xml
index deff2e9aea5f..a0d35dc134af 100644
--- a/packages/SystemUI/res/values-zh-rHK/strings.xml
+++ b/packages/SystemUI/res/values-zh-rHK/strings.xml
@@ -448,6 +448,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"不用再顯示"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"全部清除"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"管理"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"「請勿騷擾」模式已將通知暫停"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"立即開始"</string>
<string name="empty_shade_text" msgid="708135716272867002">"沒有通知"</string>
@@ -527,8 +531,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"螢幕已固定"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"畫面將會繼續顯示,直至您取消固定。按住 [返回] 和 [概覽] 即可取消固定。"</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"畫面將會繼續顯示,直至您取消固定為止。按住 [返回] 按鈕和主按鈕即可取消固定。"</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"畫面將會繼續顯示,直至您取消固定為止。向上滑動並按住即可取消固定。"</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"畫面將會繼續顯示,直至您取消固定。按住 [概覽] 即可取消固定。"</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"畫面將會繼續顯示,直至您取消固定為止。按住主按鈕即可取消固定。"</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"如要取消固定此畫面,請按住 [返回] 按鈕和 [概覽] 按鈕"</string>
@@ -912,8 +915,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"開啟「<xliff:g id="APP_NAME">%1$s</xliff:g>」"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"「<xliff:g id="APP_NAME">%1$s</xliff:g>」小視窗設定"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"要允許開啟「<xliff:g id="APP_NAME">%1$s</xliff:g>」的小視窗嗎?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"管理"</string>
<string name="no_bubbles" msgid="337101288173078247">"拒絕"</string>
<string name="yes_bubbles" msgid="668809525728633841">"允許"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"稍後再詢問我"</string>
diff --git a/packages/SystemUI/res/values-zh-rTW/strings.xml b/packages/SystemUI/res/values-zh-rTW/strings.xml
index fe3fe0f4cfa4..96eb28eb11a8 100644
--- a/packages/SystemUI/res/values-zh-rTW/strings.xml
+++ b/packages/SystemUI/res/values-zh-rTW/strings.xml
@@ -448,6 +448,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"不要再顯示"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"全部清除"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"管理"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"「零打擾」模式已將通知設為暫停"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"立即開始"</string>
<string name="empty_shade_text" msgid="708135716272867002">"沒有通知"</string>
@@ -527,8 +531,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"螢幕已固定"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"這會讓目前的螢幕畫面保持顯示狀態,直到取消固定為止。按住 [返回] 按鈕和 [總覽] 按鈕即可取消固定。"</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"這會讓應用程式顯示在螢幕上,直到取消固定為止。按住 [返回] 按鈕和主螢幕按鈕即可取消固定。"</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"這會讓目前的螢幕畫面保持顯示狀態,直到取消固定為止。向上滑動並按住即可取消固定。"</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"這會讓目前的螢幕畫面保持顯示狀態,直到取消固定為止。按住 [總覽] 按鈕即可取消固定。"</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"這會讓應用程式顯示在螢幕上,直到取消固定為止。按住主螢幕按鈕即可取消固定。"</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"如要取消固定這個螢幕畫面,請按住「返回」按鈕和「總覽」按鈕"</string>
@@ -912,8 +915,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"開啟「<xliff:g id="APP_NAME">%1$s</xliff:g>」"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"「<xliff:g id="APP_NAME">%1$s</xliff:g>」泡泡的設定"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"要允許「<xliff:g id="APP_NAME">%1$s</xliff:g>」顯示泡泡嗎?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"管理"</string>
<string name="no_bubbles" msgid="337101288173078247">"拒絕"</string>
<string name="yes_bubbles" msgid="668809525728633841">"允許"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"稍後再詢問我"</string>
diff --git a/packages/SystemUI/res/values-zu/strings.xml b/packages/SystemUI/res/values-zu/strings.xml
index 66aa602321d9..9c760edb8a52 100644
--- a/packages/SystemUI/res/values-zu/strings.xml
+++ b/packages/SystemUI/res/values-zu/strings.xml
@@ -448,6 +448,10 @@
<string name="media_projection_remember_text" msgid="3103510882172746752">"Ungabonisi futhi"</string>
<string name="clear_all_notifications_text" msgid="814192889771462828">"Sula konke"</string>
<string name="manage_notifications_text" msgid="2386728145475108753">"Phatha"</string>
+ <!-- no translation found for notification_section_header_gentle (8356064473678167305) -->
+ <skip />
+ <!-- no translation found for accessibility_notification_section_header_gentle_clear_all (4270384919249494640) -->
+ <skip />
<string name="dnd_suppressing_shade_text" msgid="1904574852846769301">"Izaziso zimiswe okwesikhashana ukungaphazamisi"</string>
<string name="media_projection_action_text" msgid="8470872969457985954">"Qala manje"</string>
<string name="empty_shade_text" msgid="708135716272867002">"Azikho izaziso"</string>
@@ -527,8 +531,7 @@
<string name="screen_pinning_title" msgid="3273740381976175811">"Isikrini siphiniwe"</string>
<string name="screen_pinning_description" msgid="8909878447196419623">"Lokhu kuyigcina ibukeka uze ususe ukuphina. Thinta uphinde ubambe okuthi Emuva Nokubuka konke ukuze ususe ukuphina."</string>
<string name="screen_pinning_description_recents_invisible" msgid="8281145542163727971">"Lokhu kuyigcina ibonakala uze uyisuse. Thinta uphinde ubambe okuthi Emuva nokuthi Ekhaya ukuze ususe ukuphina."</string>
- <!-- no translation found for screen_pinning_description_gestural (1191513974909607884) -->
- <skip />
+ <string name="screen_pinning_description_gestural" msgid="1191513974909607884">"Lokhu kuyigcina ibonakala uze ususe ukuphina. Swayiphela phezulu uphinde ubambe ukuze ususe ukuphina."</string>
<string name="screen_pinning_description_accessible" msgid="426190689254018656">"Lokhu kuyigcina ibukeka uze ususe ukuphina. Thinta uphinde ubambe Ukubuka konke ukuze ususe ukuphina."</string>
<string name="screen_pinning_description_recents_invisible_accessible" msgid="6134833683151189507">"Lokhu kuyigcina ibukeka uze ususe ukuphina. Thinta uphinde ubambe okuthi Ekhaya ukuze ususe ukuphina."</string>
<string name="screen_pinning_toast" msgid="2266705122951934150">"Ukuze ususe ukuphina lesi sikrini, thinta uphinde ubambe izinkinobho zokubuyela emuva nezokubuka konke"</string>
@@ -912,8 +915,7 @@
<string name="bubbles_deep_link_button_description" msgid="8895837143057564517">"Vula i-<xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_settings_button_description" msgid="2970630476657287189">"Izilungiselelo zamabhamuza e-<xliff:g id="APP_NAME">%1$s</xliff:g>"</string>
<string name="bubbles_prompt" msgid="8807968030159469710">"Vumela amabhamuza kusukela ku-<xliff:g id="APP_NAME">%1$s</xliff:g>?"</string>
- <!-- no translation found for manage_bubbles_text (7027739766859191408) -->
- <skip />
+ <string name="manage_bubbles_text" msgid="7027739766859191408">"Phatha"</string>
<string name="no_bubbles" msgid="337101288173078247">"Yenqaba"</string>
<string name="yes_bubbles" msgid="668809525728633841">"Vumela"</string>
<string name="ask_me_later_bubbles" msgid="2147688438402939029">"Ngibuze ngesinye isikhathi"</string>
diff --git a/packages/SystemUI/res/values/colors.xml b/packages/SystemUI/res/values/colors.xml
index 14a120b36279..6d7e20594912 100644
--- a/packages/SystemUI/res/values/colors.xml
+++ b/packages/SystemUI/res/values/colors.xml
@@ -98,6 +98,8 @@
<color name="notification_guts_button_color">@color/GM2_blue_700</color>
<color name="notification_section_header_label_color">@color/GM2_grey_900</color>
+ <!-- The divider view for the notification channel editor half-shelf -->
+ <color name="notification_channel_dialog_separator">@color/GM2_grey_200</color>
<color name="assist_orb_color">#ffffff</color>
diff --git a/packages/SystemUI/res/values/dimens.xml b/packages/SystemUI/res/values/dimens.xml
index 0fa542c498bc..fbb439af7c51 100644
--- a/packages/SystemUI/res/values/dimens.xml
+++ b/packages/SystemUI/res/values/dimens.xml
@@ -749,7 +749,7 @@
<dimen name="keyguard_lock_width">42dp</dimen>
<dimen name="keyguard_lock_padding">20dp</dimen>
- <dimen name="keyguard_indication_margin_bottom">44dp</dimen>
+ <dimen name="keyguard_indication_margin_bottom">40dp</dimen>
<!-- The text size for battery level -->
<dimen name="battery_level_text_size">12sp</dimen>
@@ -1095,6 +1095,8 @@
<dimen name="bubble_padding">8dp</dimen>
<!-- Size of individual bubbles. -->
<dimen name="individual_bubble_size">52dp</dimen>
+ <!-- Size of the circle around the bubbles when they're in the dismiss target. -->
+ <dimen name="bubble_dismiss_encircle_size">56dp</dimen>
<!-- How much to inset the icon in the circle -->
<dimen name="bubble_icon_inset">16dp</dimen>
<!-- Padding around the view displayed when the bubble is expanded -->
@@ -1131,7 +1133,12 @@
<dimen name="bubble_header_icon_size">48dp</dimen>
<!-- Space between the pointer triangle and the bubble expanded view -->
<dimen name="bubble_pointer_margin">8dp</dimen>
-
+ <!-- Height of the permission prompt shown with bubbles -->
+ <dimen name="bubble_permission_height">120dp</dimen>
+ <!-- Padding applied to the bubble dismiss target. Touches in this padding cause the bubbles to
+ snap to the dismiss target. -->
+ <dimen name="bubble_dismiss_target_padding_x">40dp</dimen>
+ <dimen name="bubble_dismiss_target_padding_y">20dp</dimen>
<!-- Size of the RAT type for CellularTile -->
<dimen name="celltile_rat_type_size">10sp</dimen>
</resources>
diff --git a/packages/SystemUI/res/values/strings.xml b/packages/SystemUI/res/values/strings.xml
index 6ba72b6b85ad..87d03ee978c4 100644
--- a/packages/SystemUI/res/values/strings.xml
+++ b/packages/SystemUI/res/values/strings.xml
@@ -1688,6 +1688,12 @@
<!-- Notification: Control panel: Label for the app that posted this notification, if it's not the package that the notification was posted for -->
<string name="notification_delegate_header">Proxied notification</string>
+ <!-- [CHAR LIMIT=40 Notification: Label for the inline channel blocking view -->
+ <string name="notification_channel_dialog_title">All <xliff:g id="app_name" example="YouTube">%1$s</xliff:g> notifications</string>
+
+ <!-- [CHAR LIMIT=20 Notification: "See more" button -->
+ <string name="see_more_title">See more</string>
+
<!-- Notification Inline controls: describes what the app is doing in the background [CHAR_LIMIT=NONE] -->
<string name="appops_camera">This app is using the camera.</string>
<!-- Notification Inline controls: describes what the app is doing in the background [CHAR_LIMIT=NONE] -->
@@ -2442,4 +2448,6 @@
<string name="bubble_accessibility_action_move_bottom_left">Move bottom left</string>
<!-- Action in accessibility menu to move the stack of bubbles to the bottom right of the screen. [CHAR LIMIT=30]-->
<string name="bubble_accessibility_action_move_bottom_right">Move bottom right</string>
+ <!-- Text used for the bubble dismiss area. Bubbles dragged to, or flung towards, this area will go away. [CHAR LIMIT=20] -->
+ <string name="bubble_dismiss_text">Dismiss</string>
</resources>
diff --git a/packages/SystemUI/res/values/styles.xml b/packages/SystemUI/res/values/styles.xml
index 083418e9a4bc..16328f8f299f 100644
--- a/packages/SystemUI/res/values/styles.xml
+++ b/packages/SystemUI/res/values/styles.xml
@@ -450,6 +450,12 @@
<item name="android:alpha">0.54</item>
</style>
+ <style name="TextAppearance.NotificationInfo.Title">
+ <item name="android:fontFamily">@*android:string/config_bodyFontFamily</item>
+ <item name="android:textColor">@color/notification_primary_text_color</item>
+ <item name="android:textStyle">bold</item>
+ </style>
+
<style name="TextAppearance.NotificationInfo.Button">
<item name="android:fontFamily">@*android:string/config_bodyFontFamilyMedium</item>
<item name="android:textSize">16sp</item>
diff --git a/packages/SystemUI/src/com/android/keyguard/KeyguardClockSwitch.java b/packages/SystemUI/src/com/android/keyguard/KeyguardClockSwitch.java
index c15c7872b6f8..d0b2c58e8021 100644
--- a/packages/SystemUI/src/com/android/keyguard/KeyguardClockSwitch.java
+++ b/packages/SystemUI/src/com/android/keyguard/KeyguardClockSwitch.java
@@ -416,7 +416,7 @@ public class KeyguardClockSwitch extends RelativeLayout {
mClockView.setVisibility(hasHeader ? View.INVISIBLE : View.VISIBLE);
mClockViewBold.setVisibility(hasHeader ? View.VISIBLE : View.INVISIBLE);
int paddingBottom = mContext.getResources().getDimensionPixelSize(hasHeader
- ? R.dimen.widget_vertical_padding_clock : R.dimen.header_subtitle_padding);
+ ? R.dimen.widget_vertical_padding_clock : R.dimen.title_clock_padding);
mClockView.setPadding(mClockView.getPaddingLeft(), mClockView.getPaddingTop(),
mClockView.getPaddingRight(), paddingBottom);
mClockViewBold.setPadding(mClockViewBold.getPaddingLeft(), mClockViewBold.getPaddingTop(),
diff --git a/packages/SystemUI/src/com/android/keyguard/KeyguardPatternView.java b/packages/SystemUI/src/com/android/keyguard/KeyguardPatternView.java
index 8899bd9ea9f2..55499dab05f3 100644
--- a/packages/SystemUI/src/com/android/keyguard/KeyguardPatternView.java
+++ b/packages/SystemUI/src/com/android/keyguard/KeyguardPatternView.java
@@ -231,6 +231,13 @@ public class KeyguardPatternView extends LinearLayout implements KeyguardSecurit
public void showUsabilityHint() {
}
+ @Override
+ public boolean disallowInterceptTouch(MotionEvent event) {
+ mTempRect.set(mLockPatternView.getLeft(), mLockPatternView.getTop(),
+ mLockPatternView.getRight(), mLockPatternView.getBottom());
+ return mTempRect.contains((int) event.getX(), (int) event.getY());
+ }
+
/** TODO: hook this up */
public void cleanUp() {
if (DEBUG) Log.v(TAG, "Cleanup() called on " + this);
diff --git a/packages/SystemUI/src/com/android/keyguard/KeyguardSecurityContainer.java b/packages/SystemUI/src/com/android/keyguard/KeyguardSecurityContainer.java
index 6f581596ab1a..d051defc1f25 100644
--- a/packages/SystemUI/src/com/android/keyguard/KeyguardSecurityContainer.java
+++ b/packages/SystemUI/src/com/android/keyguard/KeyguardSecurityContainer.java
@@ -26,12 +26,18 @@ import android.util.AttributeSet;
import android.util.Log;
import android.util.Slog;
import android.util.StatsLog;
+import android.util.TypedValue;
import android.view.LayoutInflater;
+import android.view.MotionEvent;
+import android.view.VelocityTracker;
import android.view.View;
+import android.view.ViewConfiguration;
import android.view.WindowManager;
import android.widget.FrameLayout;
import androidx.annotation.VisibleForTesting;
+import androidx.dynamicanimation.animation.DynamicAnimation;
+import androidx.dynamicanimation.animation.SpringAnimation;
import com.android.internal.logging.MetricsLogger;
import com.android.internal.logging.nano.MetricsProto.MetricsEvent;
@@ -60,6 +66,11 @@ public class KeyguardSecurityContainer extends FrameLayout implements KeyguardSe
// Bouncer is dismissed due to sim card unlock code entered.
private static final int BOUNCER_DISMISS_SIM = 4;
+ // Make the view move slower than the finger, as if the spring were applying force.
+ private static final float TOUCH_Y_MULTIPLIER = 0.25f;
+ // How much you need to drag the bouncer to trigger an auth retry (in dps.)
+ private static final float MIN_DRAG_SIZE = 10;
+
private KeyguardSecurityModel mSecurityModel;
private LockPatternUtils mLockPatternUtils;
@@ -70,10 +81,18 @@ public class KeyguardSecurityContainer extends FrameLayout implements KeyguardSe
private SecurityCallback mSecurityCallback;
private AlertDialog mAlertDialog;
private InjectionInflationController mInjectionInflationController;
+ private boolean mSwipeUpToRetry;
+ private final ViewConfiguration mViewConfiguration;
+ private final SpringAnimation mSpringAnimation;
+ private final VelocityTracker mVelocityTracker = VelocityTracker.obtain();
private final KeyguardUpdateMonitor mUpdateMonitor;
private final MetricsLogger mMetricsLogger = Dependency.get(MetricsLogger.class);
+ private float mLastTouchY = -1;
+ private int mActivePointerId = -1;
+ private boolean mIsDragging;
+ private float mStartTouchY = -1;
// Used to notify the container when something interesting happens.
public interface SecurityCallback {
@@ -104,9 +123,10 @@ public class KeyguardSecurityContainer extends FrameLayout implements KeyguardSe
mSecurityModel = new KeyguardSecurityModel(context);
mLockPatternUtils = new LockPatternUtils(context);
mUpdateMonitor = KeyguardUpdateMonitor.getInstance(mContext);
-
+ mSpringAnimation = new SpringAnimation(this, DynamicAnimation.Y);
mInjectionInflationController = new InjectionInflationController(
SystemUIFactory.getInstance().getRootComponent());
+ mViewConfiguration = ViewConfiguration.get(context);
}
public void setSecurityCallback(SecurityCallback callback) {
@@ -118,6 +138,8 @@ public class KeyguardSecurityContainer extends FrameLayout implements KeyguardSe
if (mCurrentSecuritySelection != SecurityMode.None) {
getSecurityView(mCurrentSecuritySelection).onResume(reason);
}
+ updateBiometricRetry();
+ updatePaddings();
}
@Override
@@ -131,6 +153,95 @@ public class KeyguardSecurityContainer extends FrameLayout implements KeyguardSe
}
}
+ @Override
+ public boolean shouldDelayChildPressedState() {
+ return true;
+ }
+
+ @Override
+ public boolean onInterceptTouchEvent(MotionEvent event) {
+ switch (event.getActionMasked()) {
+ case MotionEvent.ACTION_DOWN:
+ int pointerIndex = event.getActionIndex();
+ mStartTouchY = event.getY(pointerIndex);
+ mActivePointerId = event.getPointerId(pointerIndex);
+ mVelocityTracker.clear();
+ break;
+ case MotionEvent.ACTION_MOVE:
+ if (mIsDragging) {
+ return true;
+ }
+ if (!mSwipeUpToRetry) {
+ return false;
+ }
+ // Avoid dragging the pattern view
+ if (mCurrentSecurityView.disallowInterceptTouch(event)) {
+ return false;
+ }
+ int index = event.findPointerIndex(mActivePointerId);
+ int touchSlop = mViewConfiguration.getScaledTouchSlop();
+ if (mCurrentSecurityView != null
+ && mStartTouchY - event.getY(index) > touchSlop) {
+ mIsDragging = true;
+ return true;
+ }
+ break;
+ case MotionEvent.ACTION_CANCEL:
+ case MotionEvent.ACTION_UP:
+ mIsDragging = false;
+ break;
+ }
+ return false;
+ }
+
+ @Override
+ public boolean onTouchEvent(MotionEvent event) {
+ final int action = event.getActionMasked();
+ switch (action) {
+ case MotionEvent.ACTION_MOVE:
+ mVelocityTracker.addMovement(event);
+ int pointerIndex = event.findPointerIndex(mActivePointerId);
+ float y = event.getY(pointerIndex);
+ if (mLastTouchY != -1) {
+ float dy = y - mLastTouchY;
+ setTranslationY(getTranslationY() + dy * TOUCH_Y_MULTIPLIER);
+ }
+ mLastTouchY = y;
+ break;
+ case MotionEvent.ACTION_UP:
+ case MotionEvent.ACTION_CANCEL:
+ mActivePointerId = -1;
+ mLastTouchY = -1;
+ mIsDragging = false;
+ startSpringAnimation(mVelocityTracker.getYVelocity());
+ break;
+ case MotionEvent.ACTION_POINTER_UP:
+ int index = event.getActionIndex();
+ int pointerId = event.getPointerId(index);
+ if (pointerId == mActivePointerId) {
+ // This was our active pointer going up. Choose a new
+ // active pointer and adjust accordingly.
+ final int newPointerIndex = index == 0 ? 1 : 0;
+ mLastTouchY = event.getY(newPointerIndex);
+ mActivePointerId = event.getPointerId(newPointerIndex);
+ }
+ break;
+ }
+ if (action == MotionEvent.ACTION_UP) {
+ if (-getTranslationY() > TypedValue.applyDimension(TypedValue.COMPLEX_UNIT_DIP,
+ MIN_DRAG_SIZE, getResources().getDisplayMetrics())) {
+ mUpdateMonitor.requestFaceAuth();
+ }
+ }
+ return true;
+ }
+
+ private void startSpringAnimation(float startVelocity) {
+ mSpringAnimation
+ .setStartVelocity(startVelocity)
+ .animateToFinalPosition(0);
+ }
+
public void startAppearAnimation() {
if (mCurrentSecuritySelection != SecurityMode.None) {
getSecurityView(mCurrentSecuritySelection).startAppearAnimation();
@@ -145,6 +256,18 @@ public class KeyguardSecurityContainer extends FrameLayout implements KeyguardSe
return false;
}
+ /**
+ * Enables/disables swipe up to retry on the bouncer.
+ */
+ private void updateBiometricRetry() {
+ SecurityMode securityMode = getSecurityMode();
+ int userId = KeyguardUpdateMonitor.getCurrentUser();
+ mSwipeUpToRetry = mUpdateMonitor.isUnlockWithFacePossible(userId)
+ && securityMode != SecurityMode.SimPin
+ && securityMode != SecurityMode.SimPuk
+ && securityMode != SecurityMode.None;
+ }
+
public CharSequence getTitle() {
return mSecurityViewFlipper.getTitle();
}
@@ -195,6 +318,20 @@ public class KeyguardSecurityContainer extends FrameLayout implements KeyguardSe
mSecurityViewFlipper.setLockPatternUtils(mLockPatternUtils);
}
+ @Override
+ protected void onAttachedToWindow() {
+ super.onAttachedToWindow();
+ updatePaddings();
+ }
+
+ private void updatePaddings() {
+ int bottomPadding = getRootWindowInsets().getSystemWindowInsets().bottom;
+ if (getPaddingBottom() == bottomPadding) {
+ return;
+ }
+ setPadding(getPaddingLeft(), getPaddingTop(), getPaddingRight(), bottomPadding);
+ }
+
private void showDialog(String title, String message) {
if (mAlertDialog != null) {
mAlertDialog.dismiss();
@@ -467,7 +604,6 @@ public class KeyguardSecurityContainer extends FrameLayout implements KeyguardSe
}
public void reportUnlockAttempt(int userId, boolean success, int timeoutMs) {
- KeyguardUpdateMonitor monitor = KeyguardUpdateMonitor.getInstance(mContext);
if (success) {
StatsLog.write(StatsLog.KEYGUARD_BOUNCER_PASSWORD_ENTERED,
StatsLog.KEYGUARD_BOUNCER_PASSWORD_ENTERED__RESULT__SUCCESS);
diff --git a/packages/SystemUI/src/com/android/keyguard/KeyguardSecurityView.java b/packages/SystemUI/src/com/android/keyguard/KeyguardSecurityView.java
index 272b3bdf56a4..e10819473dea 100644
--- a/packages/SystemUI/src/com/android/keyguard/KeyguardSecurityView.java
+++ b/packages/SystemUI/src/com/android/keyguard/KeyguardSecurityView.java
@@ -16,6 +16,7 @@
package com.android.keyguard;
import android.content.res.ColorStateList;
+import android.view.MotionEvent;
import com.android.internal.widget.LockPatternUtils;
@@ -137,4 +138,14 @@ public interface KeyguardSecurityView {
* @return The View's title.
*/
CharSequence getTitle();
+
+ /**
+ * If the parent should not be allowed to intercept touch events.
+ * @param event A touch event.
+ * @return {@code true} if touch should be passed forward.
+ * @see android.view.ViewGroup#requestDisallowInterceptTouchEvent(boolean)
+ */
+ default boolean disallowInterceptTouch(MotionEvent event) {
+ return false;
+ }
}
diff --git a/packages/SystemUI/src/com/android/keyguard/KeyguardSliceView.java b/packages/SystemUI/src/com/android/keyguard/KeyguardSliceView.java
index c1bf4d4dd78c..e219e24a8944 100644
--- a/packages/SystemUI/src/com/android/keyguard/KeyguardSliceView.java
+++ b/packages/SystemUI/src/com/android/keyguard/KeyguardSliceView.java
@@ -38,6 +38,7 @@ import android.text.TextUtils;
import android.text.TextUtils.TruncateAt;
import android.util.AttributeSet;
import android.util.Log;
+import android.util.TypedValue;
import android.view.View;
import android.view.animation.Animation;
import android.widget.Button;
@@ -98,6 +99,7 @@ public class KeyguardSliceView extends LinearLayout implements View.OnClickListe
private LiveData<Slice> mLiveData;
private int mDisplayId = INVALID_DISPLAY;
private int mIconSize;
+ private int mIconSizeWithHeader;
/**
* Runnable called whenever the view contents change.
*/
@@ -106,6 +108,8 @@ public class KeyguardSliceView extends LinearLayout implements View.OnClickListe
private boolean mHasHeader;
private final int mRowWithHeaderPadding;
private final int mRowPadding;
+ private float mRowTextSize;
+ private float mRowWithHeaderTextSize;
@Inject
public KeyguardSliceView(@Named(VIEW_CONTEXT) Context context, AttributeSet attrs,
@@ -141,6 +145,11 @@ public class KeyguardSliceView extends LinearLayout implements View.OnClickListe
mRow = findViewById(R.id.row);
mTextColor = Utils.getColorAttrDefaultColor(mContext, R.attr.wallpaperTextColor);
mIconSize = (int) mContext.getResources().getDimension(R.dimen.widget_icon_size);
+ mIconSizeWithHeader = (int) mContext.getResources().getDimension(R.dimen.header_icon_size);
+ mRowTextSize = mContext.getResources().getDimensionPixelSize(
+ R.dimen.widget_label_font_size);
+ mRowWithHeaderTextSize = mContext.getResources().getDimensionPixelSize(
+ R.dimen.header_row_font_size);
mTitle.setOnClickListener(this);
}
@@ -244,16 +253,19 @@ public class KeyguardSliceView extends LinearLayout implements View.OnClickListe
final SliceItem titleItem = rc.getTitleItem();
button.setText(titleItem == null ? null : titleItem.getText());
button.setContentDescription(rc.getContentDescription());
+ button.setTextSize(TypedValue.COMPLEX_UNIT_PX,
+ mHasHeader ? mRowWithHeaderTextSize : mRowTextSize);
Drawable iconDrawable = null;
SliceItem icon = SliceQuery.find(item.getSlice(),
android.app.slice.SliceItem.FORMAT_IMAGE);
if (icon != null) {
+ final int iconSize = mHasHeader ? mIconSizeWithHeader : mIconSize;
iconDrawable = icon.getIcon().loadDrawable(mContext);
if (iconDrawable != null) {
final int width = (int) (iconDrawable.getIntrinsicWidth()
- / (float) iconDrawable.getIntrinsicHeight() * mIconSize);
- iconDrawable.setBounds(0, 0, Math.max(width, 1), mIconSize);
+ / (float) iconDrawable.getIntrinsicHeight() * iconSize);
+ iconDrawable.setBounds(0, 0, Math.max(width, 1), iconSize);
}
}
button.setCompoundDrawables(iconDrawable, null, null, null);
@@ -361,6 +373,11 @@ public class KeyguardSliceView extends LinearLayout implements View.OnClickListe
@Override
public void onDensityOrFontScaleChanged() {
mIconSize = mContext.getResources().getDimensionPixelSize(R.dimen.widget_icon_size);
+ mIconSizeWithHeader = (int) mContext.getResources().getDimension(R.dimen.header_icon_size);
+ mRowTextSize = mContext.getResources().getDimensionPixelSize(
+ R.dimen.widget_label_font_size);
+ mRowWithHeaderTextSize = mContext.getResources().getDimensionPixelSize(
+ R.dimen.header_row_font_size);
}
public void refresh() {
diff --git a/packages/SystemUI/src/com/android/keyguard/KeyguardStatusView.java b/packages/SystemUI/src/com/android/keyguard/KeyguardStatusView.java
index b02d51495474..1dc347491623 100644
--- a/packages/SystemUI/src/com/android/keyguard/KeyguardStatusView.java
+++ b/packages/SystemUI/src/com/android/keyguard/KeyguardStatusView.java
@@ -33,6 +33,7 @@ import android.util.Slog;
import android.util.TypedValue;
import android.view.View;
import android.widget.GridLayout;
+import android.widget.LinearLayout;
import android.widget.TextView;
import androidx.core.graphics.ColorUtils;
@@ -55,6 +56,7 @@ public class KeyguardStatusView extends GridLayout implements
private final LockPatternUtils mLockPatternUtils;
private final IActivityManager mIActivityManager;
+ private LinearLayout mStatusViewContainer;
private TextView mLogoutView;
private KeyguardClockSwitch mClockView;
private TextView mOwnerInfo;
@@ -66,6 +68,14 @@ public class KeyguardStatusView extends GridLayout implements
private float mDarkAmount = 0;
private int mTextColor;
+ /**
+ * Bottom margin that defines the margin between bottom of smart space and top of notification
+ * icons on AOD.
+ */
+ private int mBottomMargin;
+ private int mBottomMarginWithHeader;
+ private boolean mShowingHeader;
+
private KeyguardUpdateMonitorCallback mInfoCallback = new KeyguardUpdateMonitorCallback() {
@Override
@@ -161,6 +171,7 @@ public class KeyguardStatusView extends GridLayout implements
@Override
protected void onFinishInflate() {
super.onFinishInflate();
+ mStatusViewContainer = findViewById(R.id.status_view_container);
mLogoutView = findViewById(R.id.logout);
if (mLogoutView != null) {
mLogoutView.setOnClickListener(this::onLogoutClicked);
@@ -190,7 +201,19 @@ public class KeyguardStatusView extends GridLayout implements
* Moves clock, adjusting margins when slice content changes.
*/
private void onSliceContentChanged() {
- mClockView.setKeyguardShowingHeader(mKeyguardSlice.hasHeader());
+ final boolean hasHeader = mKeyguardSlice.hasHeader();
+ mClockView.setKeyguardShowingHeader(hasHeader);
+ if (mShowingHeader == hasHeader) {
+ return;
+ }
+ mShowingHeader = hasHeader;
+ // Update bottom margin since header has appeared/disappeared.
+ if (mStatusViewContainer != null) {
+ MarginLayoutParams params = (MarginLayoutParams) mStatusViewContainer.getLayoutParams();
+ params.setMargins(params.leftMargin, params.topMargin, params.rightMargin,
+ hasHeader ? mBottomMarginWithHeader : mBottomMargin);
+ mStatusViewContainer.setLayoutParams(params);
+ }
}
@Override
@@ -209,6 +232,7 @@ public class KeyguardStatusView extends GridLayout implements
mOwnerInfo.setTextSize(TypedValue.COMPLEX_UNIT_PX,
getResources().getDimensionPixelSize(R.dimen.widget_label_font_size));
}
+ loadBottomMargin();
}
public void dozeTimeTick() {
@@ -318,6 +342,12 @@ public class KeyguardStatusView extends GridLayout implements
}
}
+ private void loadBottomMargin() {
+ mBottomMargin = getResources().getDimensionPixelSize(R.dimen.widget_vertical_padding);
+ mBottomMarginWithHeader = getResources().getDimensionPixelSize(
+ R.dimen.widget_vertical_padding_with_header);
+ }
+
// DateFormat.getBestDateTimePattern is extremely expensive, and refresh is called often.
// This is an optimization to ensure we only recompute the patterns when the inputs change.
private static final class Patterns {
diff --git a/packages/SystemUI/src/com/android/keyguard/KeyguardUpdateMonitor.java b/packages/SystemUI/src/com/android/keyguard/KeyguardUpdateMonitor.java
index 83b98b0f8bb1..dd6ccb2b3a88 100644
--- a/packages/SystemUI/src/com/android/keyguard/KeyguardUpdateMonitor.java
+++ b/packages/SystemUI/src/com/android/keyguard/KeyguardUpdateMonitor.java
@@ -1686,7 +1686,11 @@ public class KeyguardUpdateMonitor implements TrustManager.TrustListener {
&& mFpm.getEnrolledFingerprints(userId).size() > 0;
}
- private boolean isUnlockWithFacePossible(int userId) {
+ /**
+ * If face hardware is available and user has enrolled. Not considering encryption or
+ * lockdown state.
+ */
+ public boolean isUnlockWithFacePossible(int userId) {
return mFaceManager != null && mFaceManager.isHardwareDetected()
&& !isFaceDisabled(userId)
&& mFaceManager.hasEnrolledTemplates(userId);
@@ -2273,6 +2277,10 @@ public class KeyguardUpdateMonitor implements TrustManager.TrustListener {
return isSimPinSecure();
}
+ /**
+ * If any SIM cards are currently secure.
+ * @see #isSimPinSecure(State)
+ */
public boolean isSimPinSecure() {
// True if any SIM is pin secure
for (SubscriptionInfo info : getSubscriptionInfo(false /* forceReload */)) {
@@ -2338,11 +2346,13 @@ public class KeyguardUpdateMonitor implements TrustManager.TrustListener {
return changed;
}
+ /**
+ * If the {@code state} is currently requiring a SIM PIN, PUK, or is disabled.
+ */
public static boolean isSimPinSecure(IccCardConstants.State state) {
- final IccCardConstants.State simState = state;
- return (simState == IccCardConstants.State.PIN_REQUIRED
- || simState == IccCardConstants.State.PUK_REQUIRED
- || simState == IccCardConstants.State.PERM_DISABLED);
+ return (state == IccCardConstants.State.PIN_REQUIRED
+ || state == IccCardConstants.State.PUK_REQUIRED
+ || state == IccCardConstants.State.PERM_DISABLED);
}
public DisplayClientState getCachedDisplayClientState() {
diff --git a/packages/SystemUI/src/com/android/systemui/Dependency.java b/packages/SystemUI/src/com/android/systemui/Dependency.java
index 4b6306ad8fc0..48a7495e073f 100644
--- a/packages/SystemUI/src/com/android/systemui/Dependency.java
+++ b/packages/SystemUI/src/com/android/systemui/Dependency.java
@@ -15,6 +15,7 @@
package com.android.systemui;
import android.annotation.Nullable;
+import android.app.INotificationManager;
import android.content.Context;
import android.content.res.Configuration;
import android.hardware.SensorPrivacyManager;
@@ -68,6 +69,7 @@ import com.android.systemui.statusbar.notification.NotificationInterruptionState
import com.android.systemui.statusbar.notification.VisualStabilityManager;
import com.android.systemui.statusbar.notification.collection.NotificationData.KeyguardEnvironment;
import com.android.systemui.statusbar.notification.logging.NotificationLogger;
+import com.android.systemui.statusbar.notification.row.ChannelEditorDialogController;
import com.android.systemui.statusbar.notification.row.NotificationBlockingHelperManager;
import com.android.systemui.statusbar.notification.row.NotificationGutsManager;
import com.android.systemui.statusbar.phone.AutoHideController;
@@ -298,6 +300,8 @@ public class Dependency extends SystemUI {
@Inject Lazy<SensorPrivacyController> mSensorPrivacyController;
@Inject Lazy<DumpController> mDumpController;
@Inject Lazy<DockManager> mDockManager;
+ @Inject Lazy<ChannelEditorDialogController> mChannelEditorDialogController;
+ @Inject Lazy<INotificationManager> mINotificationManager;
@Inject
public Dependency() {
@@ -473,6 +477,8 @@ public class Dependency extends SystemUI {
mProviders.put(SensorPrivacyController.class, mSensorPrivacyController::get);
mProviders.put(DumpController.class, mDumpController::get);
mProviders.put(DockManager.class, mDockManager::get);
+ mProviders.put(ChannelEditorDialogController.class, mChannelEditorDialogController::get);
+ mProviders.put(INotificationManager.class, mINotificationManager::get);
// TODO(b/118592525): to support multi-display , we start to add something which is
// per-display, while others may be global. I think it's time to add
diff --git a/packages/SystemUI/src/com/android/systemui/DependencyProvider.java b/packages/SystemUI/src/com/android/systemui/DependencyProvider.java
index f649976ccf01..321206f173cd 100644
--- a/packages/SystemUI/src/com/android/systemui/DependencyProvider.java
+++ b/packages/SystemUI/src/com/android/systemui/DependencyProvider.java
@@ -22,6 +22,7 @@ import static com.android.systemui.Dependency.MAIN_HANDLER_NAME;
import static com.android.systemui.Dependency.TIME_TICK_HANDLER_NAME;
import android.annotation.Nullable;
+import android.app.INotificationManager;
import android.content.Context;
import android.hardware.SensorPrivacyManager;
import android.hardware.display.NightDisplayListener;
@@ -132,6 +133,14 @@ public class DependencyProvider {
ServiceManager.getService(Context.STATUS_BAR_SERVICE));
}
+ /** */
+ @Singleton
+ @Provides
+ public INotificationManager provideINotificationManager() {
+ return INotificationManager.Stub.asInterface(
+ ServiceManager.getService(Context.NOTIFICATION_SERVICE));
+ }
+
@Singleton
@Provides
// Single instance of DisplayMetrics, gets updated by StatusBar, but can be used
diff --git a/packages/SystemUI/src/com/android/systemui/bubbles/BubbleController.java b/packages/SystemUI/src/com/android/systemui/bubbles/BubbleController.java
index 2d0944ad246f..48edf67a3ed4 100644
--- a/packages/SystemUI/src/com/android/systemui/bubbles/BubbleController.java
+++ b/packages/SystemUI/src/com/android/systemui/bubbles/BubbleController.java
@@ -108,7 +108,7 @@ public class BubbleController implements ConfigurationController.ConfigurationLi
static final int DISMISS_ACCESSIBILITY_ACTION = 6;
static final int DISMISS_NO_LONGER_BUBBLE = 7;
- static final int MAX_BUBBLES = 5; // TODO: actually enforce this
+ public static final int MAX_BUBBLES = 5; // TODO: actually enforce this
// Enables some subset of notifs to automatically become bubbles
private static final boolean DEBUG_ENABLE_AUTO_BUBBLE = false;
diff --git a/packages/SystemUI/src/com/android/systemui/bubbles/BubbleDismissView.java b/packages/SystemUI/src/com/android/systemui/bubbles/BubbleDismissView.java
new file mode 100644
index 000000000000..4db1e276f431
--- /dev/null
+++ b/packages/SystemUI/src/com/android/systemui/bubbles/BubbleDismissView.java
@@ -0,0 +1,227 @@
+/*
+ * Copyright (C) 2019 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.systemui.bubbles;
+
+import static android.view.ViewGroup.LayoutParams.MATCH_PARENT;
+
+import android.content.Context;
+import android.graphics.drawable.Drawable;
+import android.view.Gravity;
+import android.view.LayoutInflater;
+import android.view.View;
+import android.view.animation.AccelerateDecelerateInterpolator;
+import android.widget.FrameLayout;
+import android.widget.ImageView;
+import android.widget.LinearLayout;
+import android.widget.TextView;
+
+import androidx.dynamicanimation.animation.DynamicAnimation;
+import androidx.dynamicanimation.animation.SpringAnimation;
+import androidx.dynamicanimation.animation.SpringForce;
+
+import com.android.systemui.R;
+
+/** Dismiss view that contains a scrim gradient, as well as a dismiss icon, text, and circle. */
+public class BubbleDismissView extends FrameLayout {
+ /** Duration for animations involving the dismiss target text/icon/gradient. */
+ private static final int DISMISS_TARGET_ANIMATION_BASE_DURATION = 150;
+
+ private View mDismissGradient;
+
+ private LinearLayout mDismissTarget;
+ private ImageView mDismissIcon;
+ private TextView mDismissText;
+ private View mDismissCircle;
+
+ private SpringAnimation mDismissTargetAlphaSpring;
+ private SpringAnimation mDismissTargetVerticalSpring;
+
+ public BubbleDismissView(Context context) {
+ super(context);
+ setVisibility(GONE);
+
+ mDismissGradient = new FrameLayout(mContext);
+
+ FrameLayout.LayoutParams gradientParams =
+ new FrameLayout.LayoutParams(MATCH_PARENT, MATCH_PARENT);
+ gradientParams.gravity = Gravity.BOTTOM;
+ mDismissGradient.setLayoutParams(gradientParams);
+
+ Drawable gradient = mContext.getResources().getDrawable(R.drawable.pip_dismiss_scrim);
+ gradient.setAlpha((int) (255 * 0.85f));
+ mDismissGradient.setBackground(gradient);
+
+ mDismissGradient.setVisibility(GONE);
+ addView(mDismissGradient);
+
+ LayoutInflater.from(context).inflate(R.layout.bubble_dismiss_target, this, true);
+ mDismissTarget = findViewById(R.id.bubble_dismiss_icon_container);
+ mDismissIcon = findViewById(R.id.bubble_dismiss_close_icon);
+ mDismissText = findViewById(R.id.bubble_dismiss_text);
+ mDismissCircle = findViewById(R.id.bubble_dismiss_circle);
+
+ // Set up the basic target area animations. These are very simple animations that don't need
+ // fancy interpolators.
+ final AccelerateDecelerateInterpolator interpolator =
+ new AccelerateDecelerateInterpolator();
+ mDismissGradient.animate()
+ .setDuration(DISMISS_TARGET_ANIMATION_BASE_DURATION)
+ .setInterpolator(interpolator);
+ mDismissText.animate()
+ .setDuration(DISMISS_TARGET_ANIMATION_BASE_DURATION)
+ .setInterpolator(interpolator);
+ mDismissIcon.animate()
+ .setDuration(DISMISS_TARGET_ANIMATION_BASE_DURATION)
+ .setInterpolator(interpolator);
+ mDismissCircle.animate()
+ .setDuration(DISMISS_TARGET_ANIMATION_BASE_DURATION / 2)
+ .setInterpolator(interpolator);
+
+ mDismissTargetAlphaSpring =
+ new SpringAnimation(mDismissTarget, DynamicAnimation.ALPHA)
+ .setSpring(new SpringForce()
+ .setStiffness(SpringForce.STIFFNESS_LOW)
+ .setDampingRatio(SpringForce.DAMPING_RATIO_LOW_BOUNCY));
+ mDismissTargetVerticalSpring =
+ new SpringAnimation(mDismissTarget, DynamicAnimation.TRANSLATION_Y)
+ .setSpring(new SpringForce()
+ .setStiffness(SpringForce.STIFFNESS_MEDIUM)
+ .setDampingRatio(SpringForce.DAMPING_RATIO_LOW_BOUNCY));
+
+ mDismissTargetAlphaSpring.addEndListener((anim, canceled, alpha, velocity) -> {
+ // Since DynamicAnimations end when they're 'nearly' done, we can't rely on alpha being
+ // exactly zero when this listener is triggered. However, if it's less than 50% we can
+ // safely assume it was animating out rather than in.
+ if (alpha < 0.5f) {
+ // If the alpha spring was animating the view out, set it to GONE when it's done.
+ setVisibility(GONE);
+ }
+ });
+ }
+
+ /** Springs in the dismiss target and fades in the gradient. */
+ void springIn() {
+ setVisibility(View.VISIBLE);
+
+ // Fade in the dismiss target (icon + text).
+ mDismissTarget.setAlpha(0f);
+ mDismissTargetAlphaSpring.animateToFinalPosition(1f);
+
+ // Spring up the dismiss target (icon + text).
+ mDismissTarget.setTranslationY(mDismissTarget.getHeight() / 2f);
+ mDismissTargetVerticalSpring.animateToFinalPosition(0);
+
+ // Fade in the gradient.
+ mDismissGradient.setVisibility(VISIBLE);
+ mDismissGradient.animate().alpha(1f);
+
+ // Make sure the dismiss elements are in the separated position (in case we hid the target
+ // while they were condensed to cover the bubbles being in the target).
+ mDismissIcon.setAlpha(1f);
+ mDismissIcon.setScaleX(1f);
+ mDismissIcon.setScaleY(1f);
+ mDismissIcon.setTranslationX(0f);
+ mDismissText.setAlpha(1f);
+ mDismissText.setTranslationX(0f);
+ }
+
+ /** Springs out the dismiss target and fades out the gradient. */
+ void springOut() {
+ // Fade out the target.
+ mDismissTargetAlphaSpring.animateToFinalPosition(0f);
+
+ // Spring the target down a bit.
+ mDismissTargetVerticalSpring.animateToFinalPosition(mDismissTarget.getHeight() / 2f);
+
+ // Fade out the gradient and then set it to GONE so it's not in the SBV hierarchy.
+ mDismissGradient.animate().alpha(0f).withEndAction(
+ () -> mDismissGradient.setVisibility(GONE));
+
+ // Pop out the dismiss circle.
+ mDismissCircle.animate().alpha(0f).scaleX(1.2f).scaleY(1.2f);
+ }
+
+ /**
+ * Encircles the center of the dismiss target, pulling the X towards the center and hiding the
+ * text.
+ */
+ void animateEncircleCenterWithX(boolean encircle) {
+ // Pull the text towards the center if we're encircling (it'll be faded out, leaving only
+ // the X icon over the bubbles), or back to normal if we're un-encircling.
+ final float textTranslation = encircle
+ ? -mDismissIcon.getWidth() / 4f
+ : 0f;
+
+ // Center the icon if we're encircling, or put it back to normal if not.
+ final float iconTranslation = encircle
+ ? mDismissTarget.getWidth() / 2f
+ - mDismissIcon.getWidth() / 2f
+ - mDismissIcon.getLeft()
+ : 0f;
+
+ // Fade in/out the text and translate it.
+ mDismissText.animate()
+ .alpha(encircle ? 0f : 1f)
+ .translationX(textTranslation);
+
+ mDismissIcon.animate()
+ .setDuration(150)
+ .translationX(iconTranslation);
+
+ // Fade out the gradient if we're encircling (the bubbles will 'absorb' it by darkening
+ // themselves).
+ mDismissGradient.animate()
+ .alpha(encircle ? 0f : 1f);
+
+ // Prepare the circle to be 'dropped in'.
+ if (encircle) {
+ mDismissCircle.setAlpha(0f);
+ mDismissCircle.setScaleX(1.2f);
+ mDismissCircle.setScaleY(1.2f);
+ }
+
+ // Drop in the circle, or pull it back up.
+ mDismissCircle.animate()
+ .alpha(encircle ? 1f : 0f)
+ .scaleX(encircle ? 1f : 0f)
+ .scaleY(encircle ? 1f : 0f);
+ }
+
+ /** Animates the circle and the centered icon out. */
+ void animateEncirclingCircleDisappearance() {
+ // Pop out the dismiss icon and circle.
+ mDismissIcon.animate()
+ .setDuration(50)
+ .scaleX(0.9f)
+ .scaleY(0.9f)
+ .alpha(0f);
+ mDismissCircle.animate()
+ .scaleX(0.9f)
+ .scaleY(0.9f)
+ .alpha(0f);
+ }
+
+ /** Returns the Y value of the center of the dismiss target. */
+ float getDismissTargetCenterY() {
+ return getTop() + mDismissTarget.getTop() + mDismissTarget.getHeight() / 2f;
+ }
+
+ /** Returns the dismiss target, which contains the text/icon and any added padding. */
+ View getDismissTarget() {
+ return mDismissTarget;
+ }
+}
diff --git a/packages/SystemUI/src/com/android/systemui/bubbles/BubbleStackView.java b/packages/SystemUI/src/com/android/systemui/bubbles/BubbleStackView.java
index 35dc1775cb7f..2b1742592fba 100644
--- a/packages/SystemUI/src/com/android/systemui/bubbles/BubbleStackView.java
+++ b/packages/SystemUI/src/com/android/systemui/bubbles/BubbleStackView.java
@@ -19,12 +19,18 @@ package com.android.systemui.bubbles;
import static android.view.ViewGroup.LayoutParams.MATCH_PARENT;
import static android.view.ViewGroup.LayoutParams.WRAP_CONTENT;
+import android.animation.Animator;
+import android.animation.AnimatorListenerAdapter;
+import android.animation.ValueAnimator;
import android.annotation.NonNull;
import android.content.Context;
import android.content.res.Resources;
import android.content.res.TypedArray;
import android.graphics.Color;
+import android.graphics.ColorMatrix;
+import android.graphics.ColorMatrixColorFilter;
import android.graphics.Outline;
+import android.graphics.Paint;
import android.graphics.Point;
import android.graphics.PointF;
import android.graphics.Rect;
@@ -32,6 +38,8 @@ import android.graphics.RectF;
import android.graphics.drawable.LayerDrawable;
import android.graphics.drawable.ShapeDrawable;
import android.os.Bundle;
+import android.os.VibrationEffect;
+import android.os.Vibrator;
import android.service.notification.StatusBarNotification;
import android.util.Log;
import android.util.StatsLog;
@@ -84,6 +92,9 @@ public class BubbleStackView extends FrameLayout {
/** Max width of the flyout, in terms of percent of the screen width. */
private static final float FLYOUT_MAX_WIDTH_PERCENT = .6f;
+ /** Percent to darken the bubbles when they're in the dismiss target. */
+ private static final float DARKEN_PERCENT = 0.3f;
+
/** How long to wait, in milliseconds, before hiding the flyout. */
@VisibleForTesting
static final int FLYOUT_HIDE_AFTER = 5000;
@@ -131,6 +142,10 @@ public class BubbleStackView extends FrameLayout {
private final SpringAnimation mExpandedViewYAnim;
private final BubbleData mBubbleData;
+ private final Vibrator mVibrator;
+ private final ValueAnimator mDesaturateAndDarkenAnimator;
+ private final Paint mDesaturateAndDarkenPaint = new Paint();
+
private PhysicsAnimationLayout mBubbleContainer;
private StackAnimationController mStackAnimationController;
private ExpandedAnimationController mExpandedAnimationController;
@@ -183,6 +198,20 @@ public class BubbleStackView extends FrameLayout {
private boolean mViewUpdatedRequested = false;
private boolean mIsExpansionAnimating = false;
+ private boolean mShowingDismiss = false;
+
+ /**
+ * Whether the user is currently dragging their finger within the dismiss target. In this state
+ * the stack will be magnetized to the center of the target, so we shouldn't move it until the
+ * touch exits the dismiss target area.
+ */
+ private boolean mDraggingInDismissTarget = false;
+
+ /** Whether the stack is magneting towards the dismiss target. */
+ private boolean mAnimatingMagnet = false;
+
+ /** The view to desaturate/darken when magneted to the dismiss target. */
+ private View mDesaturateAndDarkenTargetView;
private LayoutInflater mInflater;
@@ -222,6 +251,8 @@ public class BubbleStackView extends FrameLayout {
@NonNull private final SurfaceSynchronizer mSurfaceSynchronizer;
+ private BubbleDismissView mDismissContainer;
+ private Runnable mAfterMagnet;
public BubbleStackView(Context context, BubbleData data,
@Nullable SurfaceSynchronizer synchronizer) {
@@ -253,6 +284,8 @@ public class BubbleStackView extends FrameLayout {
WindowManager wm = (WindowManager) context.getSystemService(Context.WINDOW_SERVICE);
wm.getDefaultDisplay().getSize(mDisplaySize);
+ mVibrator = (Vibrator) context.getSystemService(Context.VIBRATOR_SERVICE);
+
int padding = res.getDimensionPixelSize(R.dimen.bubble_expanded_view_padding);
int elevation = res.getDimensionPixelSize(R.dimen.bubble_elevation);
@@ -286,6 +319,13 @@ public class BubbleStackView extends FrameLayout {
addView(mFlyoutContainer);
setupFlyout();
+ mDismissContainer = new BubbleDismissView(mContext);
+ mDismissContainer.setLayoutParams(new FrameLayout.LayoutParams(
+ MATCH_PARENT,
+ getResources().getDimensionPixelSize(R.dimen.pip_dismiss_gradient_height),
+ Gravity.BOTTOM));
+ addView(mDismissContainer);
+
mExpandedViewXAnim =
new SpringAnimation(mExpandedViewContainer, DynamicAnimation.TRANSLATION_X);
mExpandedViewXAnim.setSpring(
@@ -342,6 +382,29 @@ public class BubbleStackView extends FrameLayout {
// This must be a separate OnDrawListener since it should be called for every draw.
getViewTreeObserver().addOnDrawListener(mSystemGestureExcludeUpdater);
+
+ final ColorMatrix animatedMatrix = new ColorMatrix();
+ final ColorMatrix darkenMatrix = new ColorMatrix();
+
+ mDesaturateAndDarkenAnimator = ValueAnimator.ofFloat(1f, 0f);
+ mDesaturateAndDarkenAnimator.addUpdateListener(animation -> {
+ final float animatedValue = (float) animation.getAnimatedValue();
+ animatedMatrix.setSaturation(animatedValue);
+
+ final float animatedDarkenValue = (1f - animatedValue) * DARKEN_PERCENT;
+ darkenMatrix.setScale(
+ 1f - animatedDarkenValue /* red */,
+ 1f - animatedDarkenValue /* green */,
+ 1f - animatedDarkenValue /* blue */,
+ 1f /* alpha */);
+
+ // Concat the matrices so that the animatedMatrix both desaturates and darkens.
+ animatedMatrix.postConcat(darkenMatrix);
+
+ // Update the paint and apply it to the bubble container.
+ mDesaturateAndDarkenPaint.setColorFilter(new ColorMatrixColorFilter(animatedMatrix));
+ mDesaturateAndDarkenTargetView.setLayerPaint(mDesaturateAndDarkenPaint);
+ });
}
/**
@@ -838,23 +901,22 @@ public class BubbleStackView extends FrameLayout {
}
mExpandedAnimationController.dragBubbleOut(bubble, x, y);
+ springInDismissTarget();
}
/** Called when a drag operation on an individual bubble has finished. */
public void onBubbleDragFinish(
- View bubble, float x, float y, float velX, float velY, boolean dismissed) {
+ View bubble, float x, float y, float velX, float velY) {
if (DEBUG) {
- Log.d(TAG, "onBubbleDragFinish: bubble=" + bubble + ", dismissed=" + dismissed);
+ Log.d(TAG, "onBubbleDragFinish: bubble=" + bubble);
}
+
if (!mIsExpanded || mIsExpansionAnimating) {
return;
}
- if (dismissed) {
- mExpandedAnimationController.prepareForDismissalWithVelocity(bubble, velX, velY);
- } else {
- mExpandedAnimationController.snapBubbleBack(bubble, velX, velY);
- }
+ mExpandedAnimationController.snapBubbleBack(bubble, velX, velY);
+ springOutDismissTargetAndHideCircle();
}
void onDragStart() {
@@ -870,6 +932,7 @@ public class BubbleStackView extends FrameLayout {
hideFlyoutImmediate();
mIsDragging = true;
+ mDraggingInDismissTarget = false;
}
void onDragged(float x, float y) {
@@ -877,7 +940,8 @@ public class BubbleStackView extends FrameLayout {
return;
}
- mStackAnimationController.moveFirstBubbleWithStackFollowing(x, y);
+ springInDismissTarget();
+ mStackAnimationController.moveStackFromTouch(x, y);
}
void onDragFinish(float x, float y, float velX, float velY) {
@@ -894,10 +958,171 @@ public class BubbleStackView extends FrameLayout {
mStackAnimationController.flingStackThenSpringToEdge(x, velX, velY);
logBubbleEvent(null /* no bubble associated with bubble stack move */,
StatsLog.BUBBLE_UICHANGED__ACTION__STACK_MOVED);
+
+ springOutDismissTargetAndHideCircle();
}
- void onDragFinishAsDismiss() {
- mIsDragging = false;
+ /** Prepares and starts the desaturate/darken animation on the bubble stack. */
+ private void animateDesaturateAndDarken(View targetView, boolean desaturateAndDarken) {
+ mDesaturateAndDarkenTargetView = targetView;
+
+ if (desaturateAndDarken) {
+ // Use the animated paint for the bubbles.
+ mDesaturateAndDarkenTargetView.setLayerType(
+ View.LAYER_TYPE_HARDWARE, mDesaturateAndDarkenPaint);
+ mDesaturateAndDarkenAnimator.removeAllListeners();
+ mDesaturateAndDarkenAnimator.start();
+ } else {
+ mDesaturateAndDarkenAnimator.removeAllListeners();
+ mDesaturateAndDarkenAnimator.addListener(new AnimatorListenerAdapter() {
+ @Override
+ public void onAnimationEnd(Animator animation) {
+ super.onAnimationEnd(animation);
+ // Stop using the animated paint.
+ resetDesaturationAndDarken();
+ }
+ });
+ mDesaturateAndDarkenAnimator.reverse();
+ }
+ }
+
+ private void resetDesaturationAndDarken() {
+ mDesaturateAndDarkenAnimator.removeAllListeners();
+ mDesaturateAndDarkenAnimator.cancel();
+ mDesaturateAndDarkenTargetView.setLayerType(View.LAYER_TYPE_NONE, null);
+ }
+
+ /**
+ * Magnets the stack to the target, while also transforming the target to encircle the stack and
+ * desaturating/darkening the bubbles.
+ */
+ void animateMagnetToDismissTarget(
+ View magnetView, boolean toTarget, float x, float y, float velX, float velY) {
+ mDraggingInDismissTarget = toTarget;
+
+ if (toTarget) {
+ // The Y-value for the bubble stack to be positioned in the center of the dismiss target
+ final float destY = mDismissContainer.getDismissTargetCenterY() - mBubbleSize / 2f;
+
+ mAnimatingMagnet = true;
+
+ final Runnable afterMagnet = () -> {
+ mAnimatingMagnet = false;
+ if (mAfterMagnet != null) {
+ mAfterMagnet.run();
+ }
+ };
+
+ if (magnetView == this) {
+ mStackAnimationController.magnetToDismiss(velX, velY, destY, afterMagnet);
+ animateDesaturateAndDarken(mBubbleContainer, true);
+ } else {
+ mExpandedAnimationController.magnetBubbleToDismiss(
+ magnetView, velX, velY, destY, afterMagnet);
+
+ animateDesaturateAndDarken(magnetView, true);
+ }
+
+ mDismissContainer.animateEncircleCenterWithX(true);
+
+ } else {
+ mAnimatingMagnet = false;
+
+ if (magnetView == this) {
+ mStackAnimationController.demagnetizeFromDismissToPoint(x, y, velX, velY);
+ animateDesaturateAndDarken(mBubbleContainer, false);
+ } else {
+ mExpandedAnimationController.demagnetizeBubbleTo(x, y, velX, velY);
+ animateDesaturateAndDarken(magnetView, false);
+ }
+
+ mDismissContainer.animateEncircleCenterWithX(false);
+ }
+
+ mVibrator.vibrate(VibrationEffect.get(toTarget
+ ? VibrationEffect.EFFECT_CLICK
+ : VibrationEffect.EFFECT_TICK));
+ }
+
+ /**
+ * Magnets the stack to the dismiss target if it's not already there. Then, dismiss the stack
+ * using the 'implode' animation and animate out the target.
+ */
+ void magnetToStackIfNeededThenAnimateDismissal(
+ View touchedView, float velX, float velY, Runnable after) {
+ final Runnable animateDismissal = () -> {
+ mAfterMagnet = null;
+
+ mVibrator.vibrate(VibrationEffect.get(VibrationEffect.EFFECT_CLICK));
+ mDismissContainer.animateEncirclingCircleDisappearance();
+
+ // 'Implode' the stack and then hide the dismiss target.
+ if (touchedView == this) {
+ mStackAnimationController.implodeStack(
+ () -> {
+ mAnimatingMagnet = false;
+ mShowingDismiss = false;
+ mDraggingInDismissTarget = false;
+ after.run();
+ resetDesaturationAndDarken();
+ });
+ } else {
+ mExpandedAnimationController.dismissDraggedOutBubble(() -> {
+ mAnimatingMagnet = false;
+ mShowingDismiss = false;
+ mDraggingInDismissTarget = false;
+ resetDesaturationAndDarken();
+ after.run();
+ });
+ }
+ };
+
+ if (mAnimatingMagnet) {
+ // If the magnet animation is currently playing, dismiss the stack after it's done. This
+ // happens if the stack is flung towards the target.
+ mAfterMagnet = animateDismissal;
+ } else if (mDraggingInDismissTarget) {
+ // If we're in the dismiss target, but not animating, we already magneted - dismiss
+ // immediately.
+ animateDismissal.run();
+ } else {
+ // Otherwise, we need to start the magnet animation and then dismiss afterward.
+ animateMagnetToDismissTarget(touchedView, true, -1 /* x */, -1 /* y */, velX, velY);
+ mAfterMagnet = animateDismissal;
+ }
+ }
+
+ /** Animates in the dismiss target, including the gradient behind it. */
+ private void springInDismissTarget() {
+ if (mShowingDismiss) {
+ return;
+ }
+
+ mShowingDismiss = true;
+
+ // Show the dismiss container and bring it to the front so the bubbles will go behind it.
+ mDismissContainer.springIn();
+ mDismissContainer.bringToFront();
+ mDismissContainer.setZ(Short.MAX_VALUE - 1);
+ }
+
+ /**
+ * Animates the dismiss target out, as well as the circle that encircles the bubbles, if they
+ * were dragged into the target and encircled.
+ */
+ private void springOutDismissTargetAndHideCircle() {
+ if (!mShowingDismiss) {
+ return;
+ }
+
+ mDismissContainer.springOut();
+ mShowingDismiss = false;
+ }
+
+
+ /** Whether the location of the given MotionEvent is within the dismiss target area. */
+ public boolean isInDismissTarget(MotionEvent ev) {
+ return isIntersecting(mDismissContainer.getDismissTarget(), ev.getRawX(), ev.getRawY());
}
/**
@@ -1066,7 +1291,7 @@ public class BubbleStackView extends FrameLayout {
private void setupFlyout() {
// Retrieve the styled floating background color.
TypedArray ta = mContext.obtainStyledAttributes(
- new int[] {android.R.attr.colorBackgroundFloating});
+ new int[]{android.R.attr.colorBackgroundFloating});
final int floatingBackgroundColor = ta.getColor(0, Color.WHITE);
ta.recycle();
diff --git a/packages/SystemUI/src/com/android/systemui/bubbles/BubbleTouchHandler.java b/packages/SystemUI/src/com/android/systemui/bubbles/BubbleTouchHandler.java
index 82e6279772f4..f429c2c124b3 100644
--- a/packages/SystemUI/src/com/android/systemui/bubbles/BubbleTouchHandler.java
+++ b/packages/SystemUI/src/com/android/systemui/bubbles/BubbleTouchHandler.java
@@ -16,8 +16,6 @@
package com.android.systemui.bubbles;
-import static com.android.systemui.pip.phone.PipDismissViewController.SHOW_TARGET_DELAY;
-
import android.content.Context;
import android.graphics.PointF;
import android.os.Handler;
@@ -27,17 +25,35 @@ import android.view.View;
import android.view.ViewConfiguration;
import com.android.systemui.Dependency;
-import com.android.systemui.pip.phone.PipDismissViewController;
/**
* Handles interpreting touches on a {@link BubbleStackView}. This includes expanding, collapsing,
* dismissing, and flings.
*/
class BubbleTouchHandler implements View.OnTouchListener {
- /** Velocity required to dismiss a bubble without dragging it into the dismiss target. */
- private static final float DISMISS_MIN_VELOCITY = 4000f;
+ /** Velocity required to dismiss the stack without dragging it into the dismiss target. */
+ private static final float STACK_DISMISS_MIN_VELOCITY = 4000f;
+
+ /**
+ * Velocity required to dismiss an individual bubble without dragging it into the dismiss
+ * target.
+ *
+ * This is higher than the stack dismiss velocity since unlike the stack, a downward fling could
+ * also be an attempted gesture to return the bubble to the row of expanded bubbles, which would
+ * usually be below the dragged bubble. By increasing the required velocity, it's less likely
+ * that the user is trying to drop it back into the row vs. fling it away.
+ */
+ private static final float INDIVIDUAL_BUBBLE_DISMISS_MIN_VELOCITY = 6000f;
private static final String TAG = "BubbleTouchHandler";
+ /**
+ * When the stack is flung towards the bottom of the screen, it'll be dismissed if it's flung
+ * towards the center of the screen (where the dismiss target is). This value is the width of
+ * the target area to be considered 'towards the target'. For example 50% means that the stack
+ * needs to be flung towards the middle 50%, and the 25% on the left and right sides won't
+ * count.
+ */
+ private static final float DISMISS_FLING_TARGET_WIDTH_PERCENT = 0.5f;
private final PointF mTouchDown = new PointF();
private final PointF mViewPositionOnTouchDown = new PointF();
@@ -45,7 +61,6 @@ class BubbleTouchHandler implements View.OnTouchListener {
private final BubbleData mBubbleData;
private BubbleController mController = Dependency.get(BubbleController.class);
- private PipDismissViewController mDismissViewController;
private boolean mMovedEnough;
private int mTouchSlopSquared;
@@ -53,12 +68,6 @@ class BubbleTouchHandler implements View.OnTouchListener {
private boolean mInDismissTarget;
private Handler mHandler = new Handler();
- private Runnable mShowDismissAffordance = new Runnable() {
- @Override
- public void run() {
- mDismissViewController.showDismissTarget();
- }
- };
/** View that was initially touched, when we received the first ACTION_DOWN event. */
private View mTouchedView;
@@ -67,7 +76,6 @@ class BubbleTouchHandler implements View.OnTouchListener {
BubbleData bubbleData, Context context) {
final int touchSlop = ViewConfiguration.get(context).getScaledTouchSlop();
mTouchSlopSquared = touchSlop * touchSlop;
- mDismissViewController = new PipDismissViewController(context);
mBubbleData = bubbleData;
mStack = stackView;
}
@@ -104,11 +112,6 @@ class BubbleTouchHandler implements View.OnTouchListener {
mTouchDown.set(rawX, rawY);
- if (!isFlyout) {
- mDismissViewController.createDismissTarget();
- mHandler.postDelayed(mShowDismissAffordance, SHOW_TARGET_DELAY);
- }
-
if (isStack) {
mViewPositionOnTouchDown.set(mStack.getStackPosition());
mStack.onDragStart();
@@ -140,9 +143,18 @@ class BubbleTouchHandler implements View.OnTouchListener {
}
}
- // TODO - when we're in the target stick to it / animate in some way?
- mInDismissTarget = mDismissViewController.updateTarget(
- isStack ? mStack.getBubbleAt(0) : mTouchedView);
+ final boolean currentlyInDismissTarget = mStack.isInDismissTarget(event);
+ if (currentlyInDismissTarget != mInDismissTarget) {
+ mInDismissTarget = currentlyInDismissTarget;
+
+ mVelocityTracker.computeCurrentVelocity(/* maxVelocity */ 1000);
+ final float velX = mVelocityTracker.getXVelocity();
+ final float velY = mVelocityTracker.getYVelocity();
+
+ // If the touch event is within the dismiss target, magnet the stack to it.
+ mStack.animateMagnetToDismissTarget(
+ mTouchedView, mInDismissTarget, viewX, viewY, velX, velY);
+ }
break;
case MotionEvent.ACTION_CANCEL:
@@ -151,28 +163,40 @@ class BubbleTouchHandler implements View.OnTouchListener {
case MotionEvent.ACTION_UP:
trackMovement(event);
- if (mInDismissTarget && isStack) {
- mController.dismissStack(BubbleController.DISMISS_USER_GESTURE);
- mStack.onDragFinishAsDismiss();
+ mVelocityTracker.computeCurrentVelocity(/* maxVelocity */ 1000);
+ final float velX = mVelocityTracker.getXVelocity();
+ final float velY = mVelocityTracker.getYVelocity();
+
+ final boolean shouldDismiss =
+ isStack
+ ? mInDismissTarget
+ || isFastFlingTowardsDismissTarget(rawX, rawY, velX, velY)
+ : mInDismissTarget
+ || velY > INDIVIDUAL_BUBBLE_DISMISS_MIN_VELOCITY;
+
+ if (shouldDismiss) {
+ final String individualBubbleKey =
+ isStack ? null : ((BubbleView) mTouchedView).getKey();
+ mStack.magnetToStackIfNeededThenAnimateDismissal(mTouchedView, velX, velY,
+ () -> {
+ if (isStack) {
+ mController.dismissStack(BubbleController.DISMISS_USER_GESTURE);
+ } else {
+ mController.removeBubble(
+ individualBubbleKey,
+ BubbleController.DISMISS_USER_GESTURE);
+ }
+ });
} else if (isFlyout) {
// TODO(b/129768381): Expand if tapped, dismiss if swiped away.
if (!mBubbleData.isExpanded() && !mMovedEnough) {
mBubbleData.setExpanded(true);
}
} else if (mMovedEnough) {
- mVelocityTracker.computeCurrentVelocity(/* maxVelocity */ 1000);
- final float velX = mVelocityTracker.getXVelocity();
- final float velY = mVelocityTracker.getYVelocity();
if (isStack) {
mStack.onDragFinish(viewX, viewY, velX, velY);
} else {
- final boolean dismissed = mInDismissTarget || velY > DISMISS_MIN_VELOCITY;
- mStack.onBubbleDragFinish(
- mTouchedView, viewX, viewY, velX, velY, /* dismissed */ dismissed);
- if (dismissed) {
- mController.removeBubble(((BubbleView) mTouchedView).getKey(),
- BubbleController.DISMISS_USER_GESTURE);
- }
+ mStack.onBubbleDragFinish(mTouchedView, viewX, viewY, velX, velY);
}
} else if (mTouchedView == mStack.getExpandedBubbleView()) {
mBubbleData.setExpanded(false);
@@ -191,9 +215,38 @@ class BubbleTouchHandler implements View.OnTouchListener {
return true;
}
+ /**
+ * Whether the given touch data represents a powerful fling towards the bottom-center of the
+ * screen (the dismiss target).
+ */
+ private boolean isFastFlingTowardsDismissTarget(
+ float rawX, float rawY, float velX, float velY) {
+ // Not a fling downward towards the target if velocity is zero or negative.
+ if (velY <= 0) {
+ return false;
+ }
+
+ float bottomOfScreenInterceptX = rawX;
+
+ // Only do math if the X velocity is non-zero, otherwise X won't change.
+ if (velX != 0) {
+ // Rise over run...
+ final float slope = velY / velX;
+ // ...y = mx + b, b = y / mx...
+ final float yIntercept = rawY - slope * rawX;
+ // ...calculate the x value when y = bottom of the screen.
+ bottomOfScreenInterceptX = (mStack.getHeight() - yIntercept) / slope;
+ }
+
+ final float dismissTargetWidth =
+ mStack.getWidth() * DISMISS_FLING_TARGET_WIDTH_PERCENT;
+ return velY > STACK_DISMISS_MIN_VELOCITY
+ && bottomOfScreenInterceptX > dismissTargetWidth / 2f
+ && bottomOfScreenInterceptX < mStack.getWidth() - dismissTargetWidth / 2f;
+ }
+
/** Clears all touch-related state. */
private void resetForNextGesture() {
- cleanUpDismissTarget();
if (mVelocityTracker != null) {
mVelocityTracker.recycle();
mVelocityTracker = null;
@@ -203,15 +256,6 @@ class BubbleTouchHandler implements View.OnTouchListener {
mInDismissTarget = false;
}
- /**
- * Removes the dismiss target and cancels any pending callbacks to show it.
- */
- private void cleanUpDismissTarget() {
- mHandler.removeCallbacks(mShowDismissAffordance);
- mDismissViewController.destroyDismissTarget();
- }
-
-
private void trackMovement(MotionEvent event) {
if (mVelocityTracker == null) {
mVelocityTracker = VelocityTracker.obtain();
diff --git a/packages/SystemUI/src/com/android/systemui/bubbles/animation/ExpandedAnimationController.java b/packages/SystemUI/src/com/android/systemui/bubbles/animation/ExpandedAnimationController.java
index 95fbfe33ee71..a9ad464867a2 100644
--- a/packages/SystemUI/src/com/android/systemui/bubbles/animation/ExpandedAnimationController.java
+++ b/packages/SystemUI/src/com/android/systemui/bubbles/animation/ExpandedAnimationController.java
@@ -64,6 +64,20 @@ public class ExpandedAnimationController
/** Size of dismiss target at bottom of screen. */
private float mPipDismissHeight;
+ /** Whether the dragged-out bubble is in the dismiss target. */
+ private boolean mIndividualBubbleWithinDismissTarget = false;
+
+ /**
+ * Whether the dragged out bubble is springing towards the touch point, rather than using the
+ * default behavior of moving directly to the touch point.
+ *
+ * This happens when the user's finger exits the dismiss area while the bubble is magnetized to
+ * the center. Since the touch point differs from the bubble location, we need to animate the
+ * bubble back to the touch point to avoid a jarring instant location change from the center of
+ * the target to the touch point just outside the target bounds.
+ */
+ private boolean mSpringingBubbleToTouch = false;
+
public ExpandedAnimationController(Point displaySize) {
mDisplaySize = displaySize;
}
@@ -151,8 +165,23 @@ public class ExpandedAnimationController
* bubble is dragged back into the row.
*/
public void dragBubbleOut(View bubbleView, float x, float y) {
- bubbleView.setTranslationX(x);
- bubbleView.setTranslationY(y);
+ if (mSpringingBubbleToTouch) {
+ if (mLayout.arePropertiesAnimatingOnView(
+ bubbleView, DynamicAnimation.TRANSLATION_X, DynamicAnimation.TRANSLATION_Y)) {
+ animationForChild(mBubbleDraggingOut)
+ .translationX(x)
+ .translationY(y)
+ .withStiffness(SpringForce.STIFFNESS_HIGH)
+ .start();
+ } else {
+ mSpringingBubbleToTouch = false;
+ }
+ }
+
+ if (!mSpringingBubbleToTouch && !mIndividualBubbleWithinDismissTarget) {
+ bubbleView.setTranslationX(x);
+ bubbleView.setTranslationY(y);
+ }
final boolean draggedOutEnough =
y > getExpandedY() + mBubbleSizePx || y < getExpandedY() - mBubbleSizePx;
@@ -164,6 +193,53 @@ public class ExpandedAnimationController
}
}
+ /** Plays a dismiss animation on the dragged out bubble. */
+ public void dismissDraggedOutBubble(Runnable after) {
+ mIndividualBubbleWithinDismissTarget = false;
+
+ // Fill the space from the soon to be dismissed bubble.
+ animateStackByBubbleWidthsStartingFrom(
+ /* numBubbleWidths */ -1,
+ /* startIndex */ mLayout.indexOfChild(mBubbleDraggingOut) + 1);
+
+ animationForChild(mBubbleDraggingOut)
+ .withStiffness(SpringForce.STIFFNESS_HIGH)
+ .scaleX(1.1f)
+ .scaleY(1.1f)
+ .alpha(0f, after)
+ .start();
+ }
+
+ /** Magnets the given bubble to the dismiss target. */
+ public void magnetBubbleToDismiss(
+ View bubbleView, float velX, float velY, float destY, Runnable after) {
+ mIndividualBubbleWithinDismissTarget = true;
+ mSpringingBubbleToTouch = false;
+ animationForChild(bubbleView)
+ .withStiffness(SpringForce.STIFFNESS_MEDIUM)
+ .withDampingRatio(SpringForce.DAMPING_RATIO_LOW_BOUNCY)
+ .withPositionStartVelocities(velX, velY)
+ .translationX(mLayout.getWidth() / 2f - mBubbleSizePx / 2f)
+ .translationY(destY, after)
+ .start();
+ }
+
+ /**
+ * Springs the dragged-out bubble towards the given coordinates and sets flags to have touch
+ * events update the spring's final position until it's settled.
+ */
+ public void demagnetizeBubbleTo(float x, float y, float velX, float velY) {
+ mIndividualBubbleWithinDismissTarget = false;
+ mSpringingBubbleToTouch = true;
+
+ animationForChild(mBubbleDraggingOut)
+ .translationX(x)
+ .translationY(y)
+ .withPositionStartVelocities(velX, velY)
+ .withStiffness(SpringForce.STIFFNESS_HIGH)
+ .start();
+ }
+
/**
* Snaps a bubble back to its position within the bubble row, and animates the rest of the
* bubbles to accommodate it if it was previously dragged out past the threshold.
@@ -274,28 +350,21 @@ public class ExpandedAnimationController
@Override
void onChildRemoved(View child, int index, Runnable finishRemoval) {
- // Bubble pops out to the top.
- // TODO: Reverse this when bubbles are at the bottom.
-
final PhysicsAnimationLayout.PhysicsPropertyAnimator animator = animationForChild(child);
- animator.alpha(0f, finishRemoval /* endAction */);
// If we're removing the dragged-out bubble, that means it got dismissed.
if (child.equals(mBubbleDraggingOut)) {
- animator.position(
- mLayout.getWidth() / 2f - mBubbleSizePx / 2f,
- mLayout.getHeight() + mBubbleSizePx)
- .withPositionStartVelocities(mBubbleDraggingOutVelX, mBubbleDraggingOutVelY)
- .scaleX(ANIMATE_SCALE_PERCENT)
- .scaleY(ANIMATE_SCALE_PERCENT);
-
mBubbleDraggingOut = null;
+ finishRemoval.run();
} else {
- animator.translationY(getExpandedY() - mBubbleSizePx * ANIMATE_TRANSLATION_FACTOR);
+ animator.alpha(0f, finishRemoval /* endAction */)
+ .withStiffness(SpringForce.STIFFNESS_HIGH)
+ .withDampingRatio(SpringForce.DAMPING_RATIO_NO_BOUNCY)
+ .scaleX(1.1f)
+ .scaleY(1.1f)
+ .start();
}
- animator.start();
-
// Animate all the other bubbles to their new positions sans this bubble.
animateBubblesAfterIndexToCorrectX(index);
}
diff --git a/packages/SystemUI/src/com/android/systemui/bubbles/animation/PhysicsAnimationLayout.java b/packages/SystemUI/src/com/android/systemui/bubbles/animation/PhysicsAnimationLayout.java
index 460652612593..997d2c4627d8 100644
--- a/packages/SystemUI/src/com/android/systemui/bubbles/animation/PhysicsAnimationLayout.java
+++ b/packages/SystemUI/src/com/android/systemui/bubbles/animation/PhysicsAnimationLayout.java
@@ -290,6 +290,10 @@ public class PhysicsAnimationLayout extends FrameLayout {
final Runnable checkIfAllFinished = () -> {
if (!arePropertiesAnimating(properties)) {
action.run();
+
+ for (DynamicAnimation.ViewProperty property : properties) {
+ removeEndActionForProperty(property);
+ }
}
};
@@ -379,10 +383,21 @@ public class PhysicsAnimationLayout extends FrameLayout {
/** Checks whether any animations of the given properties are still running. */
public boolean arePropertiesAnimating(DynamicAnimation.ViewProperty... properties) {
for (int i = 0; i < getChildCount(); i++) {
- for (DynamicAnimation.ViewProperty property : properties) {
- if (getAnimationAtIndex(property, i).isRunning()) {
- return true;
- }
+ if (arePropertiesAnimatingOnView(getChildAt(i), properties)) {
+ return true;
+ }
+ }
+
+ return false;
+ }
+
+ /** Checks whether any animations of the given properties are running on the given view. */
+ public boolean arePropertiesAnimatingOnView(
+ View view, DynamicAnimation.ViewProperty... properties) {
+ for (DynamicAnimation.ViewProperty property : properties) {
+ final SpringAnimation animation = getAnimationFromView(property, view);
+ if (animation != null && animation.isRunning()) {
+ return true;
}
}
@@ -556,7 +571,11 @@ public class PhysicsAnimationLayout extends FrameLayout {
DynamicAnimation anim, boolean canceled, float value, float velocity) {
if (!arePropertiesAnimating(mProperty)) {
if (mEndActionForProperty.containsKey(mProperty)) {
- mEndActionForProperty.get(mProperty).run();
+ final Runnable callback = mEndActionForProperty.get(mProperty);
+
+ if (callback != null) {
+ callback.run();
+ }
}
}
}
@@ -578,6 +597,12 @@ public class PhysicsAnimationLayout extends FrameLayout {
/** Start delay to use when start is called. */
private long mStartDelay = 0;
+ /** Damping ratio to use for the animations. */
+ private float mDampingRatio = -1;
+
+ /** Stiffness to use for the animations. */
+ private float mStiffness = -1;
+
/** End actions to call when animations for the given property complete. */
private Map<DynamicAnimation.ViewProperty, Runnable[]> mEndActionsForProperty =
new HashMap<>();
@@ -687,6 +712,24 @@ public class PhysicsAnimationLayout extends FrameLayout {
}
/**
+ * Set the damping ratio to use for this animation. If not supplied, will default to the
+ * value from {@link PhysicsAnimationController#getSpringForce}.
+ */
+ public PhysicsPropertyAnimator withDampingRatio(float dampingRatio) {
+ mDampingRatio = dampingRatio;
+ return this;
+ }
+
+ /**
+ * Set the stiffness to use for this animation. If not supplied, will default to the
+ * value from {@link PhysicsAnimationController#getSpringForce}.
+ */
+ public PhysicsPropertyAnimator withStiffness(float stiffness) {
+ mStiffness = stiffness;
+ return this;
+ }
+
+ /**
* Set the start velocities to use for TRANSLATION_X and TRANSLATION_Y animations. This
* overrides any value set via {@link #withStartVelocity(float)} for those properties.
*/
@@ -711,12 +754,14 @@ public class PhysicsAnimationLayout extends FrameLayout {
// If there are end actions, set an end listener on the layout for all the properties
// we're about to animate.
- if (after != null) {
+ if (after != null && after.length > 0) {
final DynamicAnimation.ViewProperty[] propertiesArray =
properties.toArray(new DynamicAnimation.ViewProperty[0]);
- for (Runnable callback : after) {
- setEndActionForMultipleProperties(callback, propertiesArray);
- }
+ setEndActionForMultipleProperties(() -> {
+ for (Runnable callback : after) {
+ callback.run();
+ }
+ }, propertiesArray);
}
// If we used position-specific end actions, we'll need to listen for both TRANSLATION_X
@@ -746,12 +791,15 @@ public class PhysicsAnimationLayout extends FrameLayout {
// Actually start the animations.
for (DynamicAnimation.ViewProperty property : properties) {
+ final SpringForce defaultSpringForce = mController.getSpringForce(property, mView);
animateValueForChild(
property,
mView,
mAnimatedProperties.get(property),
mPositionStartVelocities.getOrDefault(property, mDefaultStartVelocity),
mStartDelay,
+ mStiffness >= 0 ? mStiffness : defaultSpringForce.getStiffness(),
+ mDampingRatio >= 0 ? mDampingRatio : defaultSpringForce.getDampingRatio(),
mEndActionsForProperty.get(property));
}
@@ -760,6 +808,8 @@ public class PhysicsAnimationLayout extends FrameLayout {
mPositionStartVelocities.clear();
mDefaultStartVelocity = 0;
mStartDelay = 0;
+ mStiffness = -1;
+ mDampingRatio = -1;
mEndActionsForProperty.clear();
}
@@ -778,6 +828,8 @@ public class PhysicsAnimationLayout extends FrameLayout {
float value,
float startVel,
long startDelay,
+ float stiffness,
+ float dampingRatio,
Runnable[] afterCallbacks) {
if (view != null) {
final SpringAnimation animation =
@@ -795,6 +847,9 @@ public class PhysicsAnimationLayout extends FrameLayout {
});
}
+ animation.getSpring().setStiffness(stiffness);
+ animation.getSpring().setDampingRatio(dampingRatio);
+
if (startVel > 0) {
animation.setStartVelocity(startVel);
}
diff --git a/packages/SystemUI/src/com/android/systemui/bubbles/animation/StackAnimationController.java b/packages/SystemUI/src/com/android/systemui/bubbles/animation/StackAnimationController.java
index bc249aedc605..f937525cf417 100644
--- a/packages/SystemUI/src/com/android/systemui/bubbles/animation/StackAnimationController.java
+++ b/packages/SystemUI/src/com/android/systemui/bubbles/animation/StackAnimationController.java
@@ -30,7 +30,6 @@ import androidx.dynamicanimation.animation.SpringAnimation;
import androidx.dynamicanimation.animation.SpringForce;
import com.android.systemui.R;
-import com.android.systemui.bubbles.BubbleController;
import com.google.android.collect.Sets;
@@ -116,6 +115,25 @@ public class StackAnimationController extends
*/
private boolean mIsMovingFromFlinging = false;
+ /**
+ * Whether the stack is within the dismiss target (either by being dragged, magnet'd, or flung).
+ */
+ private boolean mWithinDismissTarget = false;
+
+ /**
+ * Whether the first bubble is springing towards the touch point, rather than using the default
+ * behavior of moving directly to the touch point with the rest of the stack following it.
+ *
+ * This happens when the user's finger exits the dismiss area while the stack is magnetized to
+ * the center. Since the touch point differs from the stack location, we need to animate the
+ * stack back to the touch point to avoid a jarring instant location change from the center of
+ * the target to the touch point just outside the target bounds.
+ *
+ * This is reset once the spring animations end, since that means the first bubble has
+ * successfully 'caught up' to the touch.
+ */
+ private boolean mFirstBubbleSpringingToTouch = false;
+
/** Horizontal offset of bubbles in the stack. */
private float mStackOffset;
/** Diameter of the bubbles themselves. */
@@ -445,6 +463,120 @@ public class StackAnimationController extends
return allowableRegion;
}
+ /** Moves the stack in response to a touch event. */
+ public void moveStackFromTouch(float x, float y) {
+
+ // If we're springing to the touch point to 'catch up' after dragging out of the dismiss
+ // target, then update the stack position animations instead of moving the bubble directly.
+ if (mFirstBubbleSpringingToTouch) {
+ final SpringAnimation springToTouchX =
+ (SpringAnimation) mStackPositionAnimations.get(DynamicAnimation.TRANSLATION_X);
+ final SpringAnimation springToTouchY =
+ (SpringAnimation) mStackPositionAnimations.get(DynamicAnimation.TRANSLATION_Y);
+
+ // If either animation is still running, we haven't caught up. Update the animations.
+ if (springToTouchX.isRunning() || springToTouchY.isRunning()) {
+ springToTouchX.animateToFinalPosition(x);
+ springToTouchY.animateToFinalPosition(y);
+ } else {
+ // If the animations have finished, the stack is now at the touch point. We can
+ // resume moving the bubble directly.
+ mFirstBubbleSpringingToTouch = false;
+ }
+ }
+
+ if (!mFirstBubbleSpringingToTouch && !mWithinDismissTarget) {
+ moveFirstBubbleWithStackFollowing(x, y);
+ }
+ }
+
+ /**
+ * Demagnetizes the stack, springing it towards the given point. This also sets flags so that
+ * subsequent touch events will update the final position of the demagnetization spring instead
+ * of directly moving the bubbles, until demagnetization is complete.
+ */
+ public void demagnetizeFromDismissToPoint(float x, float y, float velX, float velY) {
+ mWithinDismissTarget = false;
+ mFirstBubbleSpringingToTouch = true;
+
+ springFirstBubbleWithStackFollowing(
+ DynamicAnimation.TRANSLATION_X,
+ new SpringForce()
+ .setDampingRatio(DEFAULT_BOUNCINESS)
+ .setStiffness(DEFAULT_STIFFNESS),
+ velX, x);
+
+ springFirstBubbleWithStackFollowing(
+ DynamicAnimation.TRANSLATION_Y,
+ new SpringForce()
+ .setDampingRatio(DEFAULT_BOUNCINESS)
+ .setStiffness(DEFAULT_STIFFNESS),
+ velY, y);
+ }
+
+ /**
+ * Spring the stack towards the dismiss target, respecting existing velocity. This also sets
+ * flags so that subsequent touch events will not move the stack until it's demagnetized.
+ */
+ public void magnetToDismiss(float velX, float velY, float destY, Runnable after) {
+ mWithinDismissTarget = true;
+ mFirstBubbleSpringingToTouch = false;
+
+ animationForChildAtIndex(0)
+ .translationX(mLayout.getWidth() / 2f - mIndividualBubbleSize / 2f)
+ .translationY(destY, after)
+ .withPositionStartVelocities(velX, velY)
+ .withStiffness(SpringForce.STIFFNESS_MEDIUM)
+ .withDampingRatio(SpringForce.DAMPING_RATIO_LOW_BOUNCY)
+ .start();
+ }
+
+ /**
+ * 'Implode' the stack by shrinking the bubbles via chained animations and fading them out.
+ */
+ public void implodeStack(Runnable after) {
+ // Pop and fade the bubbles sequentially.
+ animationForChildAtIndex(0)
+ .scaleX(0.5f)
+ .scaleY(0.5f)
+ .alpha(0f)
+ .withDampingRatio(SpringForce.DAMPING_RATIO_NO_BOUNCY)
+ .withStiffness(SpringForce.STIFFNESS_HIGH)
+ .start(() -> {
+ // Run the callback and reset flags. The child translation animations might
+ // still be running, but that's fine. Once the alpha is at 0f they're no longer
+ // visible anyway.
+ after.run();
+ mWithinDismissTarget = false;
+ });
+ }
+
+ /**
+ * Springs the first bubble to the given final position, with the rest of the stack 'following'.
+ */
+ protected void springFirstBubbleWithStackFollowing(
+ DynamicAnimation.ViewProperty property, SpringForce spring,
+ float vel, float finalPosition) {
+
+ if (mLayout.getChildCount() == 0) {
+ return;
+ }
+
+ Log.d(TAG, String.format("Springing %s to final position %f.",
+ PhysicsAnimationLayout.getReadablePropertyName(property),
+ finalPosition));
+
+ StackPositionProperty firstBubbleProperty = new StackPositionProperty(property);
+ SpringAnimation springAnimation =
+ new SpringAnimation(this, firstBubbleProperty)
+ .setSpring(spring)
+ .setStartVelocity(vel);
+
+ cancelStackPositionAnimation(property);
+ mStackPositionAnimations.put(property, springAnimation);
+ springAnimation.animateToFinalPosition(finalPosition);
+ }
+
@Override
Set<DynamicAnimation.ViewProperty> getAnimatedProperties() {
return Sets.newHashSet(
@@ -459,7 +591,9 @@ public class StackAnimationController extends
int getNextAnimationInChain(DynamicAnimation.ViewProperty property, int index) {
if (property.equals(DynamicAnimation.TRANSLATION_X)
|| property.equals(DynamicAnimation.TRANSLATION_Y)) {
- return index + 1; // Just chain them linearly.
+ return index + 1;
+ } else if (mWithinDismissTarget) {
+ return index + 1; // Chain all animations in dismiss (scale, alpha, etc. are used).
} else {
return NONE;
}
@@ -469,9 +603,15 @@ public class StackAnimationController extends
@Override
float getOffsetForChainedPropertyAnimation(DynamicAnimation.ViewProperty property) {
if (property.equals(DynamicAnimation.TRANSLATION_X)) {
- // Offset to the left if we're on the left, or the right otherwise.
- return mLayout.isFirstChildXLeftOfCenter(mStackPosition.x)
- ? -mStackOffset : mStackOffset;
+ // If we're in the dismiss target, have the bubbles pile on top of each other with no
+ // offset.
+ if (mWithinDismissTarget) {
+ return 0f;
+ } else {
+ // Offset to the left if we're on the left, or the right otherwise.
+ return mLayout.isFirstChildXLeftOfCenter(mStackPosition.x)
+ ? -mStackOffset : mStackOffset;
+ }
} else {
return 0f;
}
@@ -480,11 +620,8 @@ public class StackAnimationController extends
@Override
SpringForce getSpringForce(DynamicAnimation.ViewProperty property, View view) {
return new SpringForce()
- .setDampingRatio(BubbleController.getBubbleBounciness(
- mLayout.getContext(), DEFAULT_BOUNCINESS))
- .setStiffness(BubbleController.getBubbleStiffness(
- mLayout.getContext(),
- mIsMovingFromFlinging ? FLING_FOLLOW_STIFFNESS : DEFAULT_STIFFNESS));
+ .setDampingRatio(DEFAULT_BOUNCINESS)
+ .setStiffness(mIsMovingFromFlinging ? FLING_FOLLOW_STIFFNESS : DEFAULT_STIFFNESS);
}
@Override
@@ -594,32 +731,6 @@ public class StackAnimationController extends
}
/**
- * Springs the first bubble to the given final position, with the rest of the stack 'following'.
- */
- private void springFirstBubbleWithStackFollowing(
- DynamicAnimation.ViewProperty property, SpringForce spring,
- float vel, float finalPosition) {
-
- if (mLayout.getChildCount() == 0) {
- return;
- }
-
- Log.d(TAG, String.format("Springing %s to final position %f.",
- PhysicsAnimationLayout.getReadablePropertyName(property),
- finalPosition));
-
- StackPositionProperty firstBubbleProperty = new StackPositionProperty(property);
- SpringAnimation springAnimation =
- new SpringAnimation(this, firstBubbleProperty)
- .setSpring(spring)
- .setStartVelocity(vel);
-
- cancelStackPositionAnimation(property);
- mStackPositionAnimations.put(property, springAnimation);
- springAnimation.animateToFinalPosition(finalPosition);
- }
-
- /**
* Cancels any outstanding first bubble property animations that are running. This does not
* affect the SpringAnimations controlling the individual bubbles' 'following' effect - it only
* cancels animations started from {@link #springFirstBubbleWithStackFollowing} and
diff --git a/packages/SystemUI/src/com/android/systemui/classifier/ClassifierData.java b/packages/SystemUI/src/com/android/systemui/classifier/ClassifierData.java
index 95e497e6574c..587abba47932 100644
--- a/packages/SystemUI/src/com/android/systemui/classifier/ClassifierData.java
+++ b/packages/SystemUI/src/com/android/systemui/classifier/ClassifierData.java
@@ -44,7 +44,7 @@ public class ClassifierData {
// sampling rate, this creates potentialy false positives.
if (event.getActionMasked() == MotionEvent.ACTION_MOVE
&& mCurrentStrokes.size() != 0
- && event.getEventTimeNano() - mCurrentStrokes.get(0).getLastEventTimeNano()
+ && event.getEventTimeNano() - mCurrentStrokes.valueAt(0).getLastEventTimeNano()
< MINIMUM_DT_NANOS - MINIMUM_DT_SMEAR_NANOS) {
return false;
}
diff --git a/packages/SystemUI/src/com/android/systemui/classifier/FalsingManagerImpl.java b/packages/SystemUI/src/com/android/systemui/classifier/FalsingManagerImpl.java
index 9052093346cb..a4bd24416f61 100644
--- a/packages/SystemUI/src/com/android/systemui/classifier/FalsingManagerImpl.java
+++ b/packages/SystemUI/src/com/android/systemui/classifier/FalsingManagerImpl.java
@@ -22,6 +22,7 @@ import android.hardware.Sensor;
import android.hardware.SensorEvent;
import android.hardware.SensorEventListener;
import android.hardware.SensorManager;
+import android.hardware.biometrics.BiometricSourceType;
import android.net.Uri;
import android.os.Handler;
import android.os.Looper;
@@ -33,6 +34,8 @@ import android.view.MotionEvent;
import android.view.accessibility.AccessibilityManager;
import com.android.internal.logging.MetricsLogger;
+import com.android.keyguard.KeyguardUpdateMonitor;
+import com.android.keyguard.KeyguardUpdateMonitorCallback;
import com.android.systemui.Dependency;
import com.android.systemui.UiOffloadThread;
import com.android.systemui.analytics.DataCollector;
@@ -80,6 +83,7 @@ public class FalsingManagerImpl implements FalsingManagerFactory.FalsingManager
private boolean mBouncerOffOnDown = false;
private boolean mSessionActive = false;
private boolean mIsTouchScreen = true;
+ private boolean mJustUnlockedWithFace = false;
private int mState = StatusBarState.SHADE;
private boolean mScreenOn;
private boolean mShowingAod;
@@ -120,6 +124,17 @@ public class FalsingManagerImpl implements FalsingManagerFactory.FalsingManager
updateConfiguration();
}
};
+ private final KeyguardUpdateMonitorCallback mKeyguardUpdateCallback =
+ new KeyguardUpdateMonitorCallback() {
+ @Override
+ public void onBiometricAuthenticated(int userId,
+ BiometricSourceType biometricSourceType) {
+ if (userId == KeyguardUpdateMonitor.getCurrentUser()
+ && biometricSourceType == BiometricSourceType.FACE) {
+ mJustUnlockedWithFace = true;
+ }
+ }
+ };
FalsingManagerImpl(Context context) {
mContext = context;
@@ -138,6 +153,7 @@ public class FalsingManagerImpl implements FalsingManagerFactory.FalsingManager
updateConfiguration();
Dependency.get(StatusBarStateController.class).addCallback(mStatusBarStateListener);
+ KeyguardUpdateMonitor.getInstance(context).registerCallback(mKeyguardUpdateCallback);
}
private void updateConfiguration() {
@@ -199,6 +215,7 @@ public class FalsingManagerImpl implements FalsingManagerFactory.FalsingManager
}
mBouncerOn = false;
mSessionActive = true;
+ mJustUnlockedWithFace = false;
mIsFalseTouchCalls = 0;
if (mHumanInteractionClassifier.isEnabled()) {
@@ -285,6 +302,11 @@ public class FalsingManagerImpl implements FalsingManagerFactory.FalsingManager
// anti-falsed.
return false;
}
+ if (mJustUnlockedWithFace) {
+ // Unlocking with face is a strong user presence signal, we can assume the user
+ // is present until the next session starts.
+ return false;
+ }
mIsFalseTouchCalls++;
boolean isFalse = mHumanInteractionClassifier.isFalseTouch();
if (!isFalse) {
diff --git a/packages/SystemUI/src/com/android/systemui/globalactions/GlobalActionsDialog.java b/packages/SystemUI/src/com/android/systemui/globalactions/GlobalActionsDialog.java
index 1ffed4c35e14..2ee02fdc8a28 100644
--- a/packages/SystemUI/src/com/android/systemui/globalactions/GlobalActionsDialog.java
+++ b/packages/SystemUI/src/com/android/systemui/globalactions/GlobalActionsDialog.java
@@ -91,6 +91,7 @@ import com.android.systemui.plugins.ActivityStarter;
import com.android.systemui.plugins.GlobalActions.GlobalActionsManager;
import com.android.systemui.plugins.GlobalActionsPanelPlugin;
import com.android.systemui.statusbar.phone.ScrimController;
+import com.android.systemui.statusbar.phone.UnlockMethodCache;
import com.android.systemui.statusbar.policy.ConfigurationController;
import com.android.systemui.util.EmergencyDialerConstants;
import com.android.systemui.util.leak.RotationUtils;
@@ -207,6 +208,14 @@ public class GlobalActionsDialog implements DialogInterface.OnDismissListener,
Dependency.get(ConfigurationController.class).addCallback(this);
mActivityStarter = Dependency.get(ActivityStarter.class);
+ UnlockMethodCache unlockMethodCache = UnlockMethodCache.getInstance(context);
+ unlockMethodCache.addListener(
+ () -> {
+ if (mDialog != null && mDialog.mPanelController != null) {
+ boolean locked = !unlockMethodCache.canSkipBouncer();
+ mDialog.mPanelController.onDeviceLockStateChanged(locked);
+ }
+ });
}
/**
@@ -1576,6 +1585,8 @@ public class GlobalActionsDialog implements DialogInterface.OnDismissListener,
new ViewGroup.LayoutParams(
ViewGroup.LayoutParams.MATCH_PARENT,
ViewGroup.LayoutParams.MATCH_PARENT));
+ mBackgroundDrawable = mPanelController.getBackgroundDrawable();
+ mScrimAlpha = 1f;
}
}
@@ -1595,17 +1606,13 @@ public class GlobalActionsDialog implements DialogInterface.OnDismissListener,
mGlobalActionsLayout.setRotationListener(this::onRotate);
mGlobalActionsLayout.setAdapter(mAdapter);
- if (!shouldUsePanel()) {
- if (mBackgroundDrawable == null) {
- mBackgroundDrawable = new ScrimDrawable();
- }
- mScrimAlpha = ScrimController.GRADIENT_SCRIM_ALPHA;
- } else {
- mBackgroundDrawable = mContext.getDrawable(
- com.android.systemui.R.drawable.global_action_panel_scrim);
- mScrimAlpha = 1f;
+ if (shouldUsePanel()) {
initializePanel();
}
+ if (mBackgroundDrawable == null) {
+ mBackgroundDrawable = new ScrimDrawable();
+ mScrimAlpha = ScrimController.GRADIENT_SCRIM_ALPHA;
+ }
getWindow().setBackgroundDrawable(mBackgroundDrawable);
}
diff --git a/packages/SystemUI/src/com/android/systemui/qs/TileLayout.java b/packages/SystemUI/src/com/android/systemui/qs/TileLayout.java
index 8aacd725ceb4..14addb99c0c5 100644
--- a/packages/SystemUI/src/com/android/systemui/qs/TileLayout.java
+++ b/packages/SystemUI/src/com/android/systemui/qs/TileLayout.java
@@ -126,7 +126,7 @@ public class TileLayout extends ViewGroup implements QSTileLayout {
(mRows != 0 ? (mCellMarginTop - mCellMarginVertical) : 0);
if (height < 0) height = 0;
- setMeasuredDimension(width + getPaddingStart() + getPaddingEnd(), height);
+ setMeasuredDimension(width, height);
}
/**
diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/KeyguardIndicationController.java b/packages/SystemUI/src/com/android/systemui/statusbar/KeyguardIndicationController.java
index fcbb41659b08..a76c9dc9f40a 100644
--- a/packages/SystemUI/src/com/android/systemui/statusbar/KeyguardIndicationController.java
+++ b/packages/SystemUI/src/com/android/systemui/statusbar/KeyguardIndicationController.java
@@ -198,7 +198,7 @@ public class KeyguardIndicationController implements StateListener,
if (!mAccessibilityController.isAccessibilityEnabled()) {
return;
}
- mShadeController.showBouncer(false /* scrimmed */);
+ mShadeController.animateCollapsePanels(CommandQueue.FLAG_EXCLUDE_NONE, true /* force */);
}
/**
diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/notification/NotificationUtils.java b/packages/SystemUI/src/com/android/systemui/statusbar/notification/NotificationUtils.java
index 09eb8a1030ef..1af47dd0f4c0 100644
--- a/packages/SystemUI/src/com/android/systemui/statusbar/notification/NotificationUtils.java
+++ b/packages/SystemUI/src/com/android/systemui/statusbar/notification/NotificationUtils.java
@@ -18,6 +18,7 @@ package com.android.systemui.statusbar.notification;
import static android.provider.Settings.Secure.NOTIFICATION_NEW_INTERRUPTION_MODEL;
+import android.annotation.Nullable;
import android.content.Context;
import android.graphics.Color;
import android.provider.Settings;
@@ -33,6 +34,9 @@ import com.android.systemui.R;
public class NotificationUtils {
private static final int[] sLocationBase = new int[2];
private static final int[] sLocationOffset = new int[2];
+
+ @Nullable private static Boolean sUseNewInterruptionModel = null;
+
public static boolean isGrayscale(ImageView v, ContrastColorUtil colorUtil) {
Object isGrayscale = v.getTag(R.id.icon_is_grayscale);
if (isGrayscale != null) {
@@ -72,9 +76,15 @@ public class NotificationUtils {
return (int) (dimensionPixelSize * factor);
}
- /** Returns the value of the new interruption model setting. */
+ /**
+ * Returns the value of the new interruption model setting. This result is cached and cannot
+ * change except through reboots/process restarts.
+ */
public static boolean useNewInterruptionModel(Context context) {
- return Settings.Secure.getInt(context.getContentResolver(),
- NOTIFICATION_NEW_INTERRUPTION_MODEL, 1) != 0;
+ if (sUseNewInterruptionModel == null) {
+ sUseNewInterruptionModel = Settings.Secure.getInt(context.getContentResolver(),
+ NOTIFICATION_NEW_INTERRUPTION_MODEL, 1) != 0;
+ }
+ return sUseNewInterruptionModel;
}
}
diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/notification/row/ChannelEditorDialogController.kt b/packages/SystemUI/src/com/android/systemui/statusbar/notification/row/ChannelEditorDialogController.kt
new file mode 100644
index 000000000000..a065f67c6137
--- /dev/null
+++ b/packages/SystemUI/src/com/android/systemui/statusbar/notification/row/ChannelEditorDialogController.kt
@@ -0,0 +1,267 @@
+/*
+ * Copyright (C) 2019 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License
+ */
+
+package com.android.systemui.statusbar.notification.row
+
+import android.app.Dialog
+import android.app.INotificationManager
+import android.app.NotificationChannel
+import android.app.NotificationChannel.DEFAULT_CHANNEL_ID
+import android.app.NotificationChannelGroup
+import android.app.NotificationManager.IMPORTANCE_NONE
+import android.content.Context
+import android.graphics.Color
+import android.graphics.PixelFormat
+import android.graphics.drawable.Drawable
+import android.graphics.drawable.ColorDrawable
+import android.util.Log
+import android.view.Gravity
+import android.view.ViewGroup.LayoutParams.MATCH_PARENT
+import android.view.ViewGroup.LayoutParams.WRAP_CONTENT
+import android.view.Window
+import android.view.WindowManager
+import android.widget.TextView
+import com.android.internal.annotations.VisibleForTesting
+
+import com.android.systemui.R
+
+import javax.inject.Inject
+import javax.inject.Singleton
+
+const val TAG = "ChannelDialogController"
+
+@Singleton
+class ChannelEditorDialogController @Inject constructor(
+ c: Context,
+ private val noMan: INotificationManager
+) {
+ val context: Context = c.applicationContext
+
+ lateinit var dialog: Dialog
+
+ private var appIcon: Drawable? = null
+ private var appUid: Int? = null
+ private var packageName: String? = null
+ private var appName: String? = null
+ private var onSettingsClickListener: NotificationInfo.OnSettingsClickListener? = null
+
+ // Channels handed to us from NotificationInfo
+ @VisibleForTesting
+ internal val providedChannels = mutableListOf<NotificationChannel>()
+
+ // Map from NotificationChannel to importance
+ private val edits = mutableMapOf<NotificationChannel, Int>()
+ var appNotificationsEnabled = true
+
+ // Keep a mapping of NotificationChannel.getGroup() to the actual group name for display
+ @VisibleForTesting
+ internal val groupNameLookup = hashMapOf<String, CharSequence>()
+ private val channelGroupList = mutableListOf<NotificationChannelGroup>()
+
+ fun prepareDialogForApp(
+ appName: String,
+ packageName: String,
+ uid: Int,
+ channels: Set<NotificationChannel>,
+ appIcon: Drawable,
+ onSettingsClickListener: NotificationInfo.OnSettingsClickListener
+ ) {
+ this.appName = appName
+ this.packageName = packageName
+ this.appUid = uid
+ this.appIcon = appIcon
+ this.appNotificationsEnabled = checkAreAppNotificationsOn()
+ this.onSettingsClickListener = onSettingsClickListener
+
+ channelGroupList.clear()
+ channelGroupList.addAll(fetchNotificationChannelGroups())
+ buildGroupNameLookup()
+ padToFourChannels(channels)
+ }
+
+ private fun buildGroupNameLookup() {
+ channelGroupList.forEach { group ->
+ if (group.id != null) {
+ groupNameLookup[group.id] = group.name
+ }
+ }
+ }
+
+ private fun padToFourChannels(channels: Set<NotificationChannel>) {
+ providedChannels.clear()
+ // First, add all of the given channels
+ providedChannels.addAll(channels.asSequence().take(4))
+
+ // Then pad to 4 if we haven't been given that many
+ providedChannels.addAll(getDisplayableChannels(channelGroupList.asSequence())
+ .filterNot { providedChannels.contains(it) }
+ .distinct()
+ .take(4 - providedChannels.size))
+
+ // If we only got one channel and it has the default miscellaneous tag, then we actually
+ // are looking at an app with a targetSdk <= O, and it doesn't make much sense to show the
+ // channel
+ if (providedChannels.size == 1 && DEFAULT_CHANNEL_ID == providedChannels[0].id) {
+ providedChannels.clear()
+ }
+ }
+
+ private fun getDisplayableChannels(
+ groupList: Sequence<NotificationChannelGroup>
+ ): Sequence<NotificationChannel> {
+
+ val channels = groupList
+ .flatMap { group ->
+ group.channels.asSequence().filterNot { channel ->
+ channel.isImportanceLockedByOEM
+ || channel.importance == IMPORTANCE_NONE
+ || channel.isImportanceLockedByCriticalDeviceFunction
+ }
+ }
+
+ // TODO: sort these by avgSentWeekly, but for now let's just do alphabetical (why not)
+ return channels.sortedWith(compareBy { it.name?.toString() ?: it.id })
+ }
+
+ fun show() {
+ initDialog()
+ dialog.show()
+ }
+
+ private fun done() {
+ resetState()
+ dialog.dismiss()
+ }
+
+ private fun resetState() {
+ appIcon = null
+ appUid = null
+ packageName = null
+ appName = null
+
+ edits.clear()
+ providedChannels.clear()
+ groupNameLookup.clear()
+ }
+
+ fun groupNameForId(groupId: String?): CharSequence {
+ return groupNameLookup[groupId] ?: ""
+ }
+
+ fun proposeEditForChannel(channel: NotificationChannel, edit: Int) {
+ if (channel.importance == edit) {
+ edits.remove(channel)
+ } else {
+ edits[channel] = edit
+ }
+ }
+
+ @SuppressWarnings("unchecked")
+ private fun fetchNotificationChannelGroups(): List<NotificationChannelGroup> {
+ return try {
+ noMan.getNotificationChannelGroupsForPackage(packageName!!, appUid!!, false)
+ .list as? List<NotificationChannelGroup> ?: listOf()
+ } catch (e: Exception) {
+ Log.e(TAG, "Error fetching channel groups", e)
+ listOf()
+ }
+ }
+
+ private fun checkAreAppNotificationsOn(): Boolean {
+ return try {
+ noMan.areNotificationsEnabledForPackage(packageName!!, appUid!!)
+ } catch (e: Exception) {
+ Log.e(TAG, "Error calling NoMan", e)
+ false
+ }
+ }
+
+ private fun applyAppNotificationsOn(b: Boolean) {
+ try {
+ noMan.setNotificationsEnabledForPackage(packageName!!, appUid!!, b)
+ } catch (e: Exception) {
+ Log.e(TAG, "Error calling NoMan", e)
+ }
+ }
+
+ private fun setChannelImportance(channel: NotificationChannel, importance: Int) {
+ try {
+ channel.importance = importance
+ noMan.updateNotificationChannelForPackage(packageName!!, appUid!!, channel)
+ } catch (e: Exception) {
+ Log.e(TAG, "Unable to update notification importance", e)
+ }
+ }
+
+ @VisibleForTesting
+ fun apply() {
+ for ((channel, importance) in edits) {
+ if (channel.importance != importance) {
+ setChannelImportance(channel, importance)
+ }
+ }
+
+ if (appNotificationsEnabled != checkAreAppNotificationsOn()) {
+ applyAppNotificationsOn(appNotificationsEnabled)
+ }
+ }
+
+ private fun initDialog() {
+ dialog = Dialog(context)
+
+ dialog.window?.requestFeature(Window.FEATURE_NO_TITLE)
+ dialog.apply {
+ setContentView(R.layout.notif_half_shelf)
+ setCanceledOnTouchOutside(true)
+ findViewById<ChannelEditorListView>(R.id.half_shelf_container).apply {
+ controller = this@ChannelEditorDialogController
+ appIcon = this@ChannelEditorDialogController.appIcon
+ appName = this@ChannelEditorDialogController.appName
+ channels = providedChannels
+ }
+
+ findViewById<TextView>(R.id.done_button)?.setOnClickListener {
+ apply()
+ done()
+ }
+
+ findViewById<TextView>(R.id.see_more_button)?.setOnClickListener {
+ onSettingsClickListener?.onClick(it, null, appUid!!)
+ dismiss()
+ }
+
+ window?.apply {
+ setBackgroundDrawable(ColorDrawable(Color.TRANSPARENT))
+ addFlags(wmFlags)
+ setType(WindowManager.LayoutParams.TYPE_STATUS_BAR_PANEL)
+ setWindowAnimations(com.android.internal.R.style.Animation_InputMethod)
+
+ attributes = attributes.apply {
+ format = PixelFormat.TRANSLUCENT
+ title = ChannelEditorDialogController::class.java.simpleName
+ gravity = Gravity.BOTTOM or Gravity.CENTER_HORIZONTAL
+ width = MATCH_PARENT
+ height = WRAP_CONTENT
+ }
+ }
+ }
+ }
+
+ private val wmFlags = (WindowManager.LayoutParams.FLAG_DRAWS_SYSTEM_BAR_BACKGROUNDS
+ or WindowManager.LayoutParams.FLAG_LAYOUT_IN_SCREEN
+ or WindowManager.LayoutParams.FLAG_WATCH_OUTSIDE_TOUCH
+ or WindowManager.LayoutParams.FLAG_HARDWARE_ACCELERATED)
+}
diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/notification/row/ChannelEditorListView.kt b/packages/SystemUI/src/com/android/systemui/statusbar/notification/row/ChannelEditorListView.kt
new file mode 100644
index 000000000000..7fea30c607f6
--- /dev/null
+++ b/packages/SystemUI/src/com/android/systemui/statusbar/notification/row/ChannelEditorListView.kt
@@ -0,0 +1,172 @@
+/*
+ * Copyright (C) 2019 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License
+ */
+
+package com.android.systemui.statusbar.notification.row
+
+import android.app.NotificationChannel
+import android.app.NotificationManager.IMPORTANCE_DEFAULT
+import android.app.NotificationManager.IMPORTANCE_NONE
+import android.app.NotificationManager.IMPORTANCE_UNSPECIFIED
+import android.content.Context
+import android.graphics.drawable.Drawable
+import android.text.TextUtils
+import android.transition.AutoTransition
+import android.transition.TransitionManager
+import android.util.AttributeSet
+import android.view.LayoutInflater
+import android.view.View
+import android.widget.ImageView
+import android.widget.LinearLayout
+import android.widget.Switch
+import android.widget.TextView
+
+import com.android.systemui.R
+
+/**
+ * Half-shelf for notification channel controls
+ */
+class ChannelEditorListView(c: Context, attrs: AttributeSet) : LinearLayout(c, attrs) {
+ lateinit var controller: ChannelEditorDialogController
+ var appIcon: Drawable? = null
+ var appName: String? = null
+ var channels = mutableListOf<NotificationChannel>()
+ set(newValue) {
+ field = newValue
+ updateRows()
+ }
+
+ // The first row is for the entire app
+ private lateinit var appControlRow: AppControlView
+
+ override fun onFinishInflate() {
+ super.onFinishInflate()
+
+ appControlRow = findViewById(R.id.app_control)
+ }
+
+ private fun updateRows() {
+ val enabled = controller.appNotificationsEnabled
+
+ val transition = AutoTransition()
+ transition.duration = 200
+ TransitionManager.beginDelayedTransition(this, transition)
+
+ // Remove any rows
+ val n = childCount
+ for (i in n.downTo(0)) {
+ val child = getChildAt(i)
+ if (child is ChannelRow) {
+ removeView(child)
+ }
+ }
+
+ updateAppControlRow(enabled)
+
+ if (enabled) {
+ val inflater = LayoutInflater.from(context)
+ for (channel in channels) {
+ addChannelRow(channel, inflater)
+ }
+ }
+ }
+
+ private fun addChannelRow(channel: NotificationChannel, inflater: LayoutInflater) {
+ val row = inflater.inflate(R.layout.notif_half_shelf_row, null) as ChannelRow
+ row.controller = controller
+ row.channel = channel
+ addView(row)
+ }
+
+ private fun updateAppControlRow(enabled: Boolean) {
+ appControlRow.iconView.setImageDrawable(appIcon)
+ appControlRow.channelName.text = context.resources
+ .getString(R.string.notification_channel_dialog_title, appName)
+ appControlRow.switch.isChecked = enabled
+ appControlRow.switch.setOnCheckedChangeListener { _, b ->
+ controller.appNotificationsEnabled = b
+ updateRows()
+ }
+ }
+}
+
+class AppControlView(c: Context, attrs: AttributeSet) : LinearLayout(c, attrs) {
+ lateinit var iconView: ImageView
+ lateinit var channelName: TextView
+ lateinit var switch: Switch
+
+ override fun onFinishInflate() {
+ iconView = findViewById(R.id.icon)
+ channelName = findViewById(R.id.app_name)
+ switch = findViewById(R.id.toggle)
+ }
+}
+
+class ChannelRow(c: Context, attrs: AttributeSet) : LinearLayout(c, attrs) {
+
+ lateinit var controller: ChannelEditorDialogController
+ private lateinit var iconView: ImageView
+ private lateinit var channelName: TextView
+ private lateinit var channelDescription: TextView
+ private lateinit var switch: Switch
+ var gentle = false
+
+ var channel: NotificationChannel? = null
+ set(newValue) {
+ field = newValue
+ updateImportance()
+ updateViews()
+ }
+
+ override fun onFinishInflate() {
+ iconView = findViewById(R.id.icon)
+ channelName = findViewById(R.id.channel_name)
+ channelDescription = findViewById(R.id.channel_description)
+ switch = findViewById(R.id.toggle)
+ switch.setOnCheckedChangeListener { _, b ->
+ channel?.let {
+ controller.proposeEditForChannel(it, if (b) it.importance else IMPORTANCE_NONE)
+ }
+ }
+ }
+
+ private fun updateViews() {
+ val nc = channel ?: return
+
+ iconView.setImageDrawable(
+ if (gentle)
+ context.getDrawable(R.drawable.ic_notification_gentle)
+ else context.getDrawable(R.drawable.ic_notification_interruptive))
+
+ channelName.text = nc.name ?: "(missing)"
+
+ nc.group?.let { groupId ->
+ channelDescription.text = controller.groupNameForId(groupId)
+ }
+
+ if (nc.group == null || TextUtils.isEmpty(channelDescription.text)) {
+ channelDescription.visibility = View.GONE
+ } else {
+ channelDescription.visibility = View.VISIBLE
+ }
+
+ switch.isChecked = nc.importance != IMPORTANCE_NONE
+ }
+
+ private fun updateImportance() {
+ val importance = channel?.importance ?: 0
+ gentle = importance != IMPORTANCE_UNSPECIFIED && importance < IMPORTANCE_DEFAULT
+ }
+}
diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/notification/row/ExpandableNotificationRow.java b/packages/SystemUI/src/com/android/systemui/statusbar/notification/row/ExpandableNotificationRow.java
index 24c7b2917360..b3ca88f7ee25 100644
--- a/packages/SystemUI/src/com/android/systemui/statusbar/notification/row/ExpandableNotificationRow.java
+++ b/packages/SystemUI/src/com/android/systemui/statusbar/notification/row/ExpandableNotificationRow.java
@@ -2398,6 +2398,14 @@ public class ExpandableNotificationRow extends ActivatableNotificationView
* it's a summary notification).
*/
public int getNumUniqueChannels() {
+ return getUniqueChannels().size();
+ }
+
+ /**
+ * Returns the channels covered by the notification row (including its children if
+ * it's a summary notification).
+ */
+ public ArraySet<NotificationChannel> getUniqueChannels() {
ArraySet<NotificationChannel> channels = new ArraySet<>();
channels.add(mEntry.channel);
@@ -2417,7 +2425,8 @@ public class ExpandableNotificationRow extends ActivatableNotificationView
}
}
}
- return channels.size();
+
+ return channels;
}
public void updateChildrenHeaderAppearance() {
diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/notification/row/NotificationGutsManager.java b/packages/SystemUI/src/com/android/systemui/statusbar/notification/row/NotificationGutsManager.java
index faa78985d30d..f15d6b75020f 100644
--- a/packages/SystemUI/src/com/android/systemui/statusbar/notification/row/NotificationGutsManager.java
+++ b/packages/SystemUI/src/com/android/systemui/statusbar/notification/row/NotificationGutsManager.java
@@ -18,7 +18,6 @@ package com.android.systemui.statusbar.notification.row;
import static android.app.AppOpsManager.OP_CAMERA;
import static android.app.AppOpsManager.OP_RECORD_AUDIO;
import static android.app.AppOpsManager.OP_SYSTEM_ALERT_WINDOW;
-import static android.service.notification.NotificationListenerService.Ranking.USER_SENTIMENT_NEGATIVE;
import android.app.INotificationManager;
import android.app.NotificationChannel;
@@ -26,6 +25,7 @@ import android.content.Context;
import android.content.Intent;
import android.content.pm.PackageManager;
import android.net.Uri;
+import android.os.Bundle;
import android.os.ServiceManager;
import android.os.UserHandle;
import android.provider.Settings;
@@ -125,13 +125,18 @@ public class NotificationGutsManager implements Dumpable, NotificationLifetimeEx
* Sends an intent to open the notification settings for a particular package and optional
* channel.
*/
+ public static final String EXTRA_SHOW_FRAGMENT_ARGUMENTS = ":settings:show_fragment_args";
private void startAppNotificationSettingsActivity(String packageName, final int appUid,
final NotificationChannel channel, ExpandableNotificationRow row) {
final Intent intent = new Intent(Settings.ACTION_APP_NOTIFICATION_SETTINGS);
intent.putExtra(Settings.EXTRA_APP_PACKAGE, packageName);
intent.putExtra(Settings.EXTRA_APP_UID, appUid);
+
if (channel != null) {
+ final Bundle args = new Bundle();
intent.putExtra(EXTRA_FRAGMENT_ARG_KEY, channel.getId());
+ args.putString(EXTRA_FRAGMENT_ARG_KEY, channel.getId());
+ intent.putExtra(EXTRA_SHOW_FRAGMENT_ARGUMENTS, args);
}
mNotificationActivityStarter.startNotificationGutsIntent(intent, appUid, row);
}
@@ -301,7 +306,7 @@ public class NotificationGutsManager implements Dumpable, NotificationLifetimeEx
iNotificationManager,
packageName,
row.getEntry().channel,
- row.getNumUniqueChannels(),
+ row.getUniqueChannels(),
sbn,
mCheckSaveListener,
onSettingsClick,
diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/notification/row/NotificationInfo.java b/packages/SystemUI/src/com/android/systemui/statusbar/notification/row/NotificationInfo.java
index d49f1685e34a..942f56689170 100644
--- a/packages/SystemUI/src/com/android/systemui/statusbar/notification/row/NotificationInfo.java
+++ b/packages/SystemUI/src/com/android/systemui/statusbar/notification/row/NotificationInfo.java
@@ -63,6 +63,7 @@ import com.android.systemui.R;
import com.android.systemui.statusbar.notification.logging.NotificationCounters;
import java.util.List;
+import java.util.Set;
/**
* The guts of a notification revealed when performing a long press. This also houses the blocking
@@ -96,12 +97,14 @@ public class NotificationInfo extends LinearLayout implements NotificationGuts.G
private INotificationManager mINotificationManager;
private PackageManager mPm;
private MetricsLogger mMetricsLogger;
+ private ChannelEditorDialogController mChannelEditorDialogController;
private String mPackageName;
private String mAppName;
private int mAppUid;
private String mDelegatePkg;
private int mNumUniqueChannelsInRow;
+ private Set<NotificationChannel> mUniqueChannelsInRow;
private NotificationChannel mSingleNotificationChannel;
private int mStartingChannelImportance;
private boolean mWasShownHighPriority;
@@ -126,6 +129,7 @@ public class NotificationInfo extends LinearLayout implements NotificationGuts.G
private NotificationGuts mGutsContainer;
private Drawable mSelectedBackground;
private Drawable mUnselectedBackground;
+ private Drawable mPkgIcon;
/** Whether this view is being shown as part of the blocking helper. */
private boolean mIsForBlockingHelper;
@@ -233,7 +237,7 @@ public class NotificationInfo extends LinearLayout implements NotificationGuts.G
final INotificationManager iNotificationManager,
final String pkg,
final NotificationChannel notificationChannel,
- final int numUniqueChannelsInRow,
+ final Set<NotificationChannel> uniqueChannelsInRow,
final StatusBarNotification sbn,
final CheckSaveListener checkSaveListener,
final OnSettingsClickListener onSettingsClick,
@@ -244,7 +248,7 @@ public class NotificationInfo extends LinearLayout implements NotificationGuts.G
boolean wasShownHighPriority)
throws RemoteException {
bindNotification(pm, iNotificationManager, pkg, notificationChannel,
- numUniqueChannelsInRow, sbn, checkSaveListener, onSettingsClick,
+ uniqueChannelsInRow, sbn, checkSaveListener, onSettingsClick,
onAppSettingsClick, isDeviceProvisioned, isNonblockable,
false /* isBlockingHelper */,
importance, wasShownHighPriority);
@@ -255,7 +259,7 @@ public class NotificationInfo extends LinearLayout implements NotificationGuts.G
INotificationManager iNotificationManager,
String pkg,
NotificationChannel notificationChannel,
- int numUniqueChannelsInRow,
+ Set<NotificationChannel> uniqueChannelsInRow,
StatusBarNotification sbn,
CheckSaveListener checkSaveListener,
OnSettingsClickListener onSettingsClick,
@@ -268,8 +272,10 @@ public class NotificationInfo extends LinearLayout implements NotificationGuts.G
throws RemoteException {
mINotificationManager = iNotificationManager;
mMetricsLogger = Dependency.get(MetricsLogger.class);
+ mChannelEditorDialogController = Dependency.get(ChannelEditorDialogController.class);
mPackageName = pkg;
- mNumUniqueChannelsInRow = numUniqueChannelsInRow;
+ mUniqueChannelsInRow = uniqueChannelsInRow;
+ mNumUniqueChannelsInRow = uniqueChannelsInRow.size();
mSbn = sbn;
mPm = pm;
mAppSettingsClickListener = onAppSettingsClick;
@@ -355,7 +361,7 @@ public class NotificationInfo extends LinearLayout implements NotificationGuts.G
}
View turnOffButton = findViewById(R.id.turn_off_notifications);
- turnOffButton.setOnClickListener(getSettingsOnClickListener());
+ turnOffButton.setOnClickListener(getTurnOffNotificationsClickListener());
turnOffButton.setVisibility(turnOffButton.hasOnClickListeners() && !mIsNonblockable
? VISIBLE : GONE);
@@ -379,7 +385,7 @@ public class NotificationInfo extends LinearLayout implements NotificationGuts.G
private void bindHeader() {
// Package name
- Drawable pkgicon = null;
+ mPkgIcon = null;
ApplicationInfo info;
try {
info = mPm.getApplicationInfo(
@@ -390,13 +396,13 @@ public class NotificationInfo extends LinearLayout implements NotificationGuts.G
| PackageManager.MATCH_DIRECT_BOOT_AWARE);
if (info != null) {
mAppName = String.valueOf(mPm.getApplicationLabel(info));
- pkgicon = mPm.getApplicationIcon(info);
+ mPkgIcon = mPm.getApplicationIcon(info);
}
} catch (PackageManager.NameNotFoundException e) {
// app is gone, just show package name and generic icon
- pkgicon = mPm.getDefaultActivityIcon();
+ mPkgIcon = mPm.getDefaultActivityIcon();
}
- ((ImageView) findViewById(R.id.pkgicon)).setImageDrawable(pkgicon);
+ ((ImageView) findViewById(R.id.pkgicon)).setImageDrawable(mPkgIcon);
((TextView) findViewById(R.id.pkgname)).setText(mAppName);
// Delegate
@@ -437,6 +443,16 @@ public class NotificationInfo extends LinearLayout implements NotificationGuts.G
return null;
}
+ private OnClickListener getTurnOffNotificationsClickListener() {
+ return ((View view) -> {
+ if (mChannelEditorDialogController != null) {
+ mChannelEditorDialogController.prepareDialogForApp(mAppName, mPackageName, mAppUid,
+ mUniqueChannelsInRow, mPkgIcon, mOnSettingsClickListener);
+ mChannelEditorDialogController.show();
+ }
+ });
+ }
+
private void bindChannelDetails() throws RemoteException {
bindName();
bindGroup();
diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/phone/ButtonDispatcher.java b/packages/SystemUI/src/com/android/systemui/statusbar/phone/ButtonDispatcher.java
index 6a93c7c9e5c4..539bc7bcb3f6 100644
--- a/packages/SystemUI/src/com/android/systemui/statusbar/phone/ButtonDispatcher.java
+++ b/packages/SystemUI/src/com/android/systemui/statusbar/phone/ButtonDispatcher.java
@@ -23,7 +23,6 @@ import android.animation.ValueAnimator;
import android.view.View;
import android.view.View.AccessibilityDelegate;
-import com.android.systemui.plugins.statusbar.phone.NavBarButtonProvider.ButtonInterface;
import com.android.systemui.statusbar.policy.KeyButtonDrawable;
import java.util.ArrayList;
diff --git a/cmds/incidentd/src/cipher/cipher_blocks.proto b/packages/SystemUI/src/com/android/systemui/statusbar/phone/ButtonInterface.java
index 5c7ed242c7a5..150a9603a124 100644
--- a/cmds/incidentd/src/cipher/cipher_blocks.proto
+++ b/packages/SystemUI/src/com/android/systemui/statusbar/phone/ButtonInterface.java
@@ -11,15 +11,23 @@
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
- * limitations under the License.
+ * limitations under the License
*/
-syntax = "proto2";
+package com.android.systemui.statusbar.phone;
-package android.os.incidentd;
+import android.annotation.Nullable;
+import android.graphics.drawable.Drawable;
-// This proto is never instantiated anywhere. It only exists to keep a record of the format of the
-// encrypted data on disk.
-message CipherBlocks {
- repeated string blocks = 1;
+public interface ButtonInterface {
+
+ void setImageDrawable(@Nullable Drawable drawable);
+
+ void abortCurrentGesture();
+
+ void setVertical(boolean vertical);
+
+ void setDarkIntensity(float intensity);
+
+ void setDelayTouchFeedback(boolean shouldDelay);
}
diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/phone/NavigationBarFragment.java b/packages/SystemUI/src/com/android/systemui/statusbar/phone/NavigationBarFragment.java
index 8aa4f0382649..1429718d5d9c 100644
--- a/packages/SystemUI/src/com/android/systemui/statusbar/phone/NavigationBarFragment.java
+++ b/packages/SystemUI/src/com/android/systemui/statusbar/phone/NavigationBarFragment.java
@@ -709,7 +709,6 @@ public class NavigationBarFragment extends LifecycleFragment implements Callback
if (shouldDisableNavbarGestures()) {
return false;
}
- mNavigationBarView.onNavigationButtonLongPress(v);
mMetricsLogger.action(MetricsEvent.ACTION_ASSIST_LONG_PRESS);
Bundle args = new Bundle();
args.putInt(
@@ -749,12 +748,10 @@ public class NavigationBarFragment extends LifecycleFragment implements Callback
}
private boolean onLongPressBackHome(View v) {
- mNavigationBarView.onNavigationButtonLongPress(v);
return onLongPressNavigationButtons(v, R.id.back, R.id.home);
}
private boolean onLongPressBackRecents(View v) {
- mNavigationBarView.onNavigationButtonLongPress(v);
return onLongPressNavigationButtons(v, R.id.back, R.id.recent_apps);
}
@@ -981,6 +978,7 @@ public class NavigationBarFragment extends LifecycleFragment implements Callback
@Override
public void onNavigationModeChanged(int mode) {
mNavBarMode = mode;
+ updateScreenPinningGestures();
}
public void disableAnimationsDuringHide(long delay) {
diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/phone/NavigationBarInflaterView.java b/packages/SystemUI/src/com/android/systemui/statusbar/phone/NavigationBarInflaterView.java
index 7ab8da9d2561..a12ae96f57b0 100644
--- a/packages/SystemUI/src/com/android/systemui/statusbar/phone/NavigationBarInflaterView.java
+++ b/packages/SystemUI/src/com/android/systemui/statusbar/phone/NavigationBarInflaterView.java
@@ -35,23 +35,15 @@ import android.widget.Space;
import com.android.internal.annotations.VisibleForTesting;
import com.android.systemui.Dependency;
import com.android.systemui.R;
-import com.android.systemui.plugins.PluginListener;
-import com.android.systemui.plugins.statusbar.phone.NavBarButtonProvider;
import com.android.systemui.recents.OverviewProxyService;
-import com.android.systemui.shared.plugins.PluginManager;
import com.android.systemui.shared.system.QuickStepContract;
import com.android.systemui.statusbar.phone.ReverseLinearLayout.ReverseRelativeLayout;
import com.android.systemui.statusbar.policy.KeyButtonView;
-import com.android.systemui.tuner.TunerService;
-import com.android.systemui.tuner.TunerService.Tunable;
-import java.util.ArrayList;
-import java.util.List;
import java.util.Objects;
public class NavigationBarInflaterView extends FrameLayout
- implements Tunable, PluginListener<NavBarButtonProvider>,
- NavigationModeController.ModeChangedListener {
+ implements NavigationModeController.ModeChangedListener {
private static final String TAG = "NavBarInflater";
@@ -87,8 +79,6 @@ public class NavigationBarInflaterView extends FrameLayout
private static final String ABSOLUTE_SUFFIX = "A";
private static final String ABSOLUTE_VERTICAL_CENTERED_SUFFIX = "C";
- private final List<NavBarButtonProvider> mPlugins = new ArrayList<>();
-
protected LayoutInflater mLayoutInflater;
protected LayoutInflater mLandscapeInflater;
@@ -160,32 +150,11 @@ public class NavigationBarInflaterView extends FrameLayout
}
@Override
- protected void onAttachedToWindow() {
- super.onAttachedToWindow();
- Dependency.get(TunerService.class).addTunable(this, NAV_BAR_VIEWS, NAV_BAR_LEFT,
- NAV_BAR_RIGHT);
- Dependency.get(PluginManager.class).addPluginListener(this,
- NavBarButtonProvider.class, true /* Allow multiple */);
- }
-
- @Override
protected void onDetachedFromWindow() {
- Dependency.get(TunerService.class).removeTunable(this);
- Dependency.get(PluginManager.class).removePluginListener(this);
Dependency.get(NavigationModeController.class).removeListener(this);
super.onDetachedFromWindow();
}
- @Override
- public void onTuningChanged(String key, String newValue) {
- if (NAV_BAR_VIEWS.equals(key)) {
- setNavigationBarLayout(newValue);
- } else if (NAV_BAR_LEFT.equals(key) || NAV_BAR_RIGHT.equals(key)) {
- clearViews();
- inflateLayout(mCurrentLayout);
- }
- }
-
public void setNavigationBarLayout(String layoutValue) {
if (!Objects.equals(mCurrentLayout, layoutValue)) {
mUsingCustomLayout = layoutValue != null;
@@ -404,16 +373,9 @@ public class NavigationBarInflaterView extends FrameLayout
View v = null;
String button = extractButton(buttonSpec);
if (LEFT.equals(button)) {
- String s = Dependency.get(TunerService.class).getValue(NAV_BAR_LEFT, NAVSPACE);
- button = extractButton(s);
+ button = extractButton(NAVSPACE);
} else if (RIGHT.equals(button)) {
- String s = Dependency.get(TunerService.class).getValue(NAV_BAR_RIGHT, MENU_IME_ROTATE);
- button = extractButton(s);
- }
- // Let plugins go first so they can override a standard view if they want.
- for (NavBarButtonProvider provider : mPlugins) {
- v = provider.createView(buttonSpec, parent);
- if (v != null) return v;
+ button = extractButton(MENU_IME_ROTATE);
}
if (HOME.equals(button)) {
v = inflater.inflate(R.layout.home, parent, false);
@@ -522,18 +484,4 @@ public class NavigationBarInflaterView extends FrameLayout
private static float convertDpToPx(Context context, float dp) {
return dp * context.getResources().getDisplayMetrics().density;
}
-
- @Override
- public void onPluginConnected(NavBarButtonProvider plugin, Context context) {
- mPlugins.add(plugin);
- clearViews();
- inflateLayout(mCurrentLayout);
- }
-
- @Override
- public void onPluginDisconnected(NavBarButtonProvider plugin) {
- mPlugins.remove(plugin);
- clearViews();
- inflateLayout(mCurrentLayout);
- }
}
diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/phone/NavigationBarTransitions.java b/packages/SystemUI/src/com/android/systemui/statusbar/phone/NavigationBarTransitions.java
index 4e4a6aec57b5..9e0aff070364 100644
--- a/packages/SystemUI/src/com/android/systemui/statusbar/phone/NavigationBarTransitions.java
+++ b/packages/SystemUI/src/com/android/systemui/statusbar/phone/NavigationBarTransitions.java
@@ -174,7 +174,6 @@ public final class NavigationBarTransitions extends BarTransitions implements
if (mAutoDim) {
applyLightsOut(false, true);
}
- mView.onDarkIntensityChange(darkIntensity);
}
@Override
diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/phone/NavigationBarView.java b/packages/SystemUI/src/com/android/systemui/statusbar/phone/NavigationBarView.java
index 831d882d68a7..d85b8acfb462 100644
--- a/packages/SystemUI/src/com/android/systemui/statusbar/phone/NavigationBarView.java
+++ b/packages/SystemUI/src/com/android/systemui/statusbar/phone/NavigationBarView.java
@@ -16,7 +16,6 @@
package com.android.systemui.statusbar.phone;
-import static android.view.WindowManagerPolicyConstants.NAV_BAR_INVALID;
import static android.view.WindowManagerPolicyConstants.NAV_BAR_MODE_3BUTTON;
import static com.android.systemui.shared.system.QuickStepContract.SYSUI_STATE_NOTIFICATION_PANEL_EXPANDED;
@@ -38,10 +37,8 @@ import android.graphics.Rect;
import android.graphics.Region;
import android.graphics.Region.Op;
import android.os.Bundle;
-import android.os.RemoteException;
import android.util.AttributeSet;
import android.util.Log;
-import android.util.Slog;
import android.util.SparseArray;
import android.view.Display;
import android.view.MotionEvent;
@@ -52,7 +49,6 @@ import android.view.ViewTreeObserver.InternalInsetsInfo;
import android.view.ViewTreeObserver.OnComputeInternalInsetsListener;
import android.view.WindowInsets;
import android.view.WindowManager;
-import android.view.WindowManagerGlobal;
import android.view.accessibility.AccessibilityNodeInfo;
import android.view.accessibility.AccessibilityNodeInfo.AccessibilityAction;
import android.view.inputmethod.InputMethodManager;
@@ -65,13 +61,9 @@ import com.android.systemui.Interpolators;
import com.android.systemui.R;
import com.android.systemui.SysUiServiceProvider;
import com.android.systemui.assist.AssistManager;
-import com.android.systemui.plugins.PluginListener;
-import com.android.systemui.plugins.statusbar.phone.NavGesture;
-import com.android.systemui.plugins.statusbar.phone.NavGesture.GestureHelper;
import com.android.systemui.recents.OverviewProxyService;
import com.android.systemui.recents.Recents;
import com.android.systemui.recents.RecentsOnboarding;
-import com.android.systemui.shared.plugins.PluginManager;
import com.android.systemui.shared.system.ActivityManagerWrapper;
import com.android.systemui.shared.system.QuickStepContract;
import com.android.systemui.shared.system.WindowManagerWrapper;
@@ -82,7 +74,7 @@ import java.io.FileDescriptor;
import java.io.PrintWriter;
import java.util.function.Consumer;
-public class NavigationBarView extends FrameLayout implements PluginListener<NavGesture>,
+public class NavigationBarView extends FrameLayout implements
NavigationModeController.ModeChangedListener {
final static boolean DEBUG = false;
final static String TAG = "StatusBar/NavBarView";
@@ -118,7 +110,6 @@ public class NavigationBarView extends FrameLayout implements PluginListener<Nav
private KeyButtonDrawable mDockedIcon;
private final EdgeBackGestureHandler mEdgeBackGestureHandler;
- private GestureHelper mGestureHelper;
private final DeadZone mDeadZone;
private boolean mDeadZoneConsuming = false;
private final NavigationBarTransitions mBarTransitions;
@@ -349,9 +340,6 @@ public class NavigationBarView extends FrameLayout implements PluginListener<Nav
@Override
public boolean onTouchEvent(MotionEvent event) {
shouldDeadZoneConsumeTouchEvents(event);
- if (mGestureHelper != null && mGestureHelper.onTouchEvent(event)) {
- return true;
- }
return super.onTouchEvent(event);
}
@@ -628,6 +616,8 @@ public class NavigationBarView extends FrameLayout implements PluginListener<Nav
// as they are used for exiting.
final boolean pinningActive = ActivityManagerWrapper.getInstance().isScreenPinningActive();
if (mOverviewProxyService.isEnabled()) {
+ // Force disable recents when not in legacy mode
+ disableRecent |= !QuickStepContract.isLegacyMode(mNavBarMode);
if (pinningActive) {
disableBack = disableHome = false;
}
@@ -708,12 +698,6 @@ public class NavigationBarView extends FrameLayout implements PluginListener<Nav
}
}
- public void onNavigationButtonLongPress(View v) {
- if (mGestureHelper != null) {
- mGestureHelper.onNavigationButtonLongPress(v);
- }
- }
-
public void onPanelExpandedChange() {
updateSlippery();
mOverviewProxyService.setSystemUiStateFlag(SYSUI_STATE_NOTIFICATION_PANEL_EXPANDED,
@@ -809,17 +793,8 @@ public class NavigationBarView extends FrameLayout implements PluginListener<Nav
reloadNavIcons();
}
- public void onDarkIntensityChange(float intensity) {
- if (mGestureHelper != null) {
- mGestureHelper.onDarkIntensityChange(intensity);
- }
- }
-
@Override
protected void onDraw(Canvas canvas) {
- if (mGestureHelper != null) {
- mGestureHelper.onDraw(canvas);
- }
mDeadZone.onDraw(canvas);
super.onDraw(canvas);
}
@@ -835,9 +810,6 @@ public class NavigationBarView extends FrameLayout implements PluginListener<Nav
updateButtonLocation(getRotateSuggestionButton(), mRotationButtonBounds, true);
// TODO: Handle button visibility changes
mOverviewProxyService.onActiveNavBarRegionChanges(mActiveRegion);
- if (mGestureHelper != null) {
- mGestureHelper.onLayout(changed, left, top, right, bottom);
- }
mRecentsOnboarding.setNavBarHeight(getMeasuredHeight());
}
@@ -936,25 +908,11 @@ public class NavigationBarView extends FrameLayout implements PluginListener<Nav
if (!isLayoutDirectionResolved()) {
resolveLayoutDirection();
}
- updateTaskSwitchHelper();
updateNavButtonIcons();
getHomeButton().setVertical(mIsVertical);
}
- private void updateTaskSwitchHelper() {
- if (mGestureHelper == null) return;
- boolean isRtl = (getLayoutDirection() == View.LAYOUT_DIRECTION_RTL);
- int navBarPos = NAV_BAR_INVALID;
- try {
- navBarPos = WindowManagerGlobal.getWindowManagerService().getNavBarPosition(
- getContext().getDisplayId());
- } catch (RemoteException e) {
- Slog.e(TAG, "Failed to get nav bar position.", e);
- }
- mGestureHelper.setBarState(isRtl, navBarPos);
- }
-
@Override
protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
int w = MeasureSpec.getSize(widthMeasureSpec);
@@ -1001,7 +959,6 @@ public class NavigationBarView extends FrameLayout implements PluginListener<Nav
mTmpLastConfiguration.updateFrom(mConfiguration);
mConfiguration.updateFrom(newConfig);
boolean uiCarModeChanged = updateCarMode();
- updateTaskSwitchHelper();
updateIcons(mTmpLastConfiguration);
updateRecentsIcon();
mRecentsOnboarding.onConfigurationChanged(mConfiguration);
@@ -1070,9 +1027,6 @@ public class NavigationBarView extends FrameLayout implements PluginListener<Nav
super.onAttachedToWindow();
requestApplyInsets();
reorient();
- onPluginDisconnected(null); // Create default gesture helper
- Dependency.get(PluginManager.class).addPluginListener(this,
- NavGesture.class, false /* Only one */);
onNavigationModeChanged(mNavBarMode);
setUpSwipeUpOnboarding(isQuickStepSwipeUpEnabled());
@@ -1083,11 +1037,7 @@ public class NavigationBarView extends FrameLayout implements PluginListener<Nav
@Override
protected void onDetachedFromWindow() {
super.onDetachedFromWindow();
- Dependency.get(PluginManager.class).removePluginListener(this);
Dependency.get(NavigationModeController.class).removeListener(this);
- if (mGestureHelper != null) {
- mGestureHelper.destroy();
- }
setUpSwipeUpOnboarding(false);
for (int i = 0; i < mButtonDispatchers.size(); ++i) {
mButtonDispatchers.valueAt(i).onDestroy();
@@ -1105,21 +1055,6 @@ public class NavigationBarView extends FrameLayout implements PluginListener<Nav
}
}
- @Override
- public void onPluginConnected(NavGesture plugin, Context context) {
- mGestureHelper = plugin.getGestureHelper();
- updateTaskSwitchHelper();
- }
-
- @Override
- public void onPluginDisconnected(NavGesture plugin) {
- if (mGestureHelper != null) {
- mGestureHelper.destroy();
- mGestureHelper = null;
- }
- updateTaskSwitchHelper();
- }
-
public void dump(FileDescriptor fd, PrintWriter pw, String[] args) {
pw.println("NavigationBarView {");
final Rect r = new Rect();
@@ -1156,9 +1091,6 @@ public class NavigationBarView extends FrameLayout implements PluginListener<Nav
pw.println(" }");
mContextualButtonGroup.dump(pw);
- if (mGestureHelper != null) {
- mGestureHelper.dump(pw);
- }
mRecentsOnboarding.dump(pw);
mTintController.dump(pw);
}
diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/phone/NavigationHandle.java b/packages/SystemUI/src/com/android/systemui/statusbar/phone/NavigationHandle.java
index 7dc71f590ecd..0fe12943614c 100644
--- a/packages/SystemUI/src/com/android/systemui/statusbar/phone/NavigationHandle.java
+++ b/packages/SystemUI/src/com/android/systemui/statusbar/phone/NavigationHandle.java
@@ -29,7 +29,6 @@ import android.view.View;
import com.android.settingslib.Utils;
import com.android.systemui.R;
-import com.android.systemui.plugins.statusbar.phone.NavBarButtonProvider.ButtonInterface;
public class NavigationHandle extends View implements ButtonInterface {
private float mDarkIntensity = -1;
diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/phone/ShadeController.java b/packages/SystemUI/src/com/android/systemui/statusbar/phone/ShadeController.java
index 234a968e9f75..70cd43a5e17a 100644
--- a/packages/SystemUI/src/com/android/systemui/statusbar/phone/ShadeController.java
+++ b/packages/SystemUI/src/com/android/systemui/statusbar/phone/ShadeController.java
@@ -43,6 +43,12 @@ public interface ShadeController {
void instantExpandNotificationsPanel();
/**
+ * Collapse the shade animated, showing the bouncer when on {@link StatusBarState#KEYGUARD} or
+ * dismissing {@link StatusBar} when on {@link StatusBarState#SHADE}.
+ */
+ void animateCollapsePanels(int flags, boolean force);
+
+ /**
* If the notifications panel is not fully expanded, collapse it animated.
*
* @return Seems to always return false
diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/phone/StatusBar.java b/packages/SystemUI/src/com/android/systemui/statusbar/phone/StatusBar.java
index 776be00f8ea4..1b72e20803ce 100644
--- a/packages/SystemUI/src/com/android/systemui/statusbar/phone/StatusBar.java
+++ b/packages/SystemUI/src/com/android/systemui/statusbar/phone/StatusBar.java
@@ -3297,11 +3297,7 @@ public class StatusBar extends SystemUI implements DemoMode,
@Override
public void showBouncer(boolean scrimmed) {
- if (!mIsOccluded && !scrimmed && mState == StatusBarState.KEYGUARD) {
- animateCollapsePanels(CommandQueue.FLAG_EXCLUDE_NONE, true /* force */);
- } else {
- mStatusBarKeyguardViewManager.showBouncer(scrimmed);
- }
+ mStatusBarKeyguardViewManager.showBouncer(scrimmed);
}
@Override
diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/policy/BluetoothControllerImpl.java b/packages/SystemUI/src/com/android/systemui/statusbar/policy/BluetoothControllerImpl.java
index 8916242b682b..78e845a68445 100644
--- a/packages/SystemUI/src/com/android/systemui/statusbar/policy/BluetoothControllerImpl.java
+++ b/packages/SystemUI/src/com/android/systemui/statusbar/policy/BluetoothControllerImpl.java
@@ -243,6 +243,7 @@ public class BluetoothControllerImpl implements BluetoothController, BluetoothCa
@Override
public void onBluetoothStateChanged(int bluetoothState) {
+ if (DEBUG) Log.d(TAG, "BluetoothStateChanged=" + stateToString(bluetoothState));
mEnabled = bluetoothState == BluetoothAdapter.STATE_ON
|| bluetoothState == BluetoothAdapter.STATE_TURNING_ON;
mState = bluetoothState;
@@ -252,6 +253,7 @@ public class BluetoothControllerImpl implements BluetoothController, BluetoothCa
@Override
public void onDeviceAdded(CachedBluetoothDevice cachedDevice) {
+ if (DEBUG) Log.d(TAG, "DeviceAdded=" + cachedDevice.getAddress());
cachedDevice.registerCallback(this);
updateConnected();
mHandler.sendEmptyMessage(H.MSG_PAIRED_DEVICES_CHANGED);
@@ -259,6 +261,7 @@ public class BluetoothControllerImpl implements BluetoothController, BluetoothCa
@Override
public void onDeviceDeleted(CachedBluetoothDevice cachedDevice) {
+ if (DEBUG) Log.d(TAG, "DeviceDeleted=" + cachedDevice.getAddress());
mCachedState.remove(cachedDevice);
updateConnected();
mHandler.sendEmptyMessage(H.MSG_PAIRED_DEVICES_CHANGED);
@@ -266,6 +269,7 @@ public class BluetoothControllerImpl implements BluetoothController, BluetoothCa
@Override
public void onDeviceBondStateChanged(CachedBluetoothDevice cachedDevice, int bondState) {
+ if (DEBUG) Log.d(TAG, "DeviceBondStateChanged=" + cachedDevice.getAddress());
mCachedState.remove(cachedDevice);
updateConnected();
mHandler.sendEmptyMessage(H.MSG_PAIRED_DEVICES_CHANGED);
@@ -273,12 +277,28 @@ public class BluetoothControllerImpl implements BluetoothController, BluetoothCa
@Override
public void onDeviceAttributesChanged() {
+ if (DEBUG) Log.d(TAG, "DeviceAttributesChanged");
updateConnected();
mHandler.sendEmptyMessage(H.MSG_PAIRED_DEVICES_CHANGED);
}
@Override
public void onConnectionStateChanged(CachedBluetoothDevice cachedDevice, int state) {
+ if (DEBUG) {
+ Log.d(TAG, "ConnectionStateChanged=" + cachedDevice.getAddress() + " "
+ + stateToString(state));
+ }
+ mCachedState.remove(cachedDevice);
+ updateConnected();
+ mHandler.sendEmptyMessage(H.MSG_STATE_CHANGED);
+ }
+
+ @Override
+ public void onAclConnectionStateChanged(CachedBluetoothDevice cachedDevice, int state) {
+ if (DEBUG) {
+ Log.d(TAG, "ACLConnectionStateChanged=" + cachedDevice.getAddress() + " "
+ + stateToString(state));
+ }
mCachedState.remove(cachedDevice);
updateConnected();
mHandler.sendEmptyMessage(H.MSG_STATE_CHANGED);
diff --git a/packages/SystemUI/src/com/android/systemui/statusbar/policy/KeyButtonView.java b/packages/SystemUI/src/com/android/systemui/statusbar/policy/KeyButtonView.java
index 22a0b991ffae..c9579fdd3788 100644
--- a/packages/SystemUI/src/com/android/systemui/statusbar/policy/KeyButtonView.java
+++ b/packages/SystemUI/src/com/android/systemui/statusbar/policy/KeyButtonView.java
@@ -56,9 +56,9 @@ import com.android.internal.logging.nano.MetricsProto.MetricsEvent;
import com.android.systemui.Dependency;
import com.android.systemui.R;
import com.android.systemui.bubbles.BubbleController;
-import com.android.systemui.plugins.statusbar.phone.NavBarButtonProvider.ButtonInterface;
import com.android.systemui.recents.OverviewProxyService;
import com.android.systemui.shared.system.QuickStepContract;
+import com.android.systemui.statusbar.phone.ButtonInterface;
public class KeyButtonView extends ImageView implements ButtonInterface {
private static final String TAG = KeyButtonView.class.getSimpleName();
diff --git a/packages/SystemUI/src/com/android/systemui/tuner/PreviewNavInflater.java b/packages/SystemUI/src/com/android/systemui/tuner/PreviewNavInflater.java
deleted file mode 100644
index e7a695fc3efd..000000000000
--- a/packages/SystemUI/src/com/android/systemui/tuner/PreviewNavInflater.java
+++ /dev/null
@@ -1,74 +0,0 @@
-/*
- * Copyright (C) 2016 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file
- * except in compliance with the License. You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software distributed under the
- * License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
- * KIND, either express or implied. See the License for the specific language governing
- * permissions and limitations under the License.
- */
-
-package com.android.systemui.tuner;
-
-import android.content.Context;
-import android.util.AttributeSet;
-import android.view.MotionEvent;
-
-import com.android.systemui.Dependency;
-import com.android.systemui.statusbar.phone.NavigationBarInflaterView;
-
-public class PreviewNavInflater extends NavigationBarInflaterView {
-
- public PreviewNavInflater(Context context, AttributeSet attrs) {
- super(context, attrs);
- }
-
- @Override
- protected void onAttachedToWindow() {
- super.onAttachedToWindow();
- // Immediately remove tuner listening, since this is a preview, all values will be injected
- // manually.
- Dependency.get(TunerService.class).removeTunable(this);
- }
-
- @Override
- public boolean onInterceptTouchEvent(MotionEvent ev) {
- // Only a preview, not interactable.
- return true;
- }
-
- @Override
- public void onTuningChanged(String key, String newValue) {
- if (NAV_BAR_VIEWS.equals(key)) {
- // Since this is a preview we might get a bunch of random stuff, validate before sending
- // for inflation.
- if (isValidLayout(newValue)) {
- super.onTuningChanged(key, newValue);
- }
- } else {
- super.onTuningChanged(key, newValue);
- }
- }
-
- private boolean isValidLayout(String newValue) {
- if (newValue == null) {
- return true;
- }
- int separatorCount = 0;
- int lastGravitySeparator = 0;
- for (int i = 0; i < newValue.length(); i++) {
- if (newValue.charAt(i) == GRAVITY_SEPARATOR.charAt(0)) {
- if (i == 0 || (i - lastGravitySeparator) == 1) {
- return false;
- }
- lastGravitySeparator = i;
- separatorCount++;
- }
- }
- return separatorCount == 2 && (newValue.length() - lastGravitySeparator) != 1;
- }
-}
diff --git a/packages/SystemUI/tests/src/com/android/systemui/bubbles/animation/ExpandedAnimationControllerTest.java b/packages/SystemUI/tests/src/com/android/systemui/bubbles/animation/ExpandedAnimationControllerTest.java
index cd8480505c04..2990b3ee52ff 100644
--- a/packages/SystemUI/tests/src/com/android/systemui/bubbles/animation/ExpandedAnimationControllerTest.java
+++ b/packages/SystemUI/tests/src/com/android/systemui/bubbles/animation/ExpandedAnimationControllerTest.java
@@ -17,6 +17,8 @@
package com.android.systemui.bubbles.animation;
import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertNotEquals;
+import static org.mockito.Mockito.verify;
import android.content.res.Resources;
import android.graphics.Point;
@@ -31,6 +33,7 @@ import androidx.test.filters.SmallTest;
import com.android.systemui.R;
import org.junit.Before;
+import org.junit.Ignore;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.mockito.Mockito;
@@ -69,14 +72,14 @@ public class ExpandedAnimationControllerTest extends PhysicsAnimationLayoutTestC
waitForPropertyAnimations(DynamicAnimation.TRANSLATION_X, DynamicAnimation.TRANSLATION_Y);
testBubblesInCorrectExpandedPositions();
- Mockito.verify(afterExpand).run();
+ verify(afterExpand).run();
Runnable afterCollapse = Mockito.mock(Runnable.class);
mExpandedController.collapseBackToStack(afterCollapse);
waitForPropertyAnimations(DynamicAnimation.TRANSLATION_X, DynamicAnimation.TRANSLATION_Y);
testStackedAtPosition(mExpansionPoint.x, mExpansionPoint.y, -1);
- Mockito.verify(afterExpand).run();
+ verify(afterExpand).run();
}
@Test
@@ -140,6 +143,79 @@ public class ExpandedAnimationControllerTest extends PhysicsAnimationLayoutTestC
testBubblesInCorrectExpandedPositions();
}
+ @Test
+ public void testMagnetToDismiss_dismiss() throws InterruptedException {
+ expand();
+
+ final View draggedOutView = mViews.get(0);
+ final Runnable after = Mockito.mock(Runnable.class);
+
+ mExpandedController.prepareForBubbleDrag(draggedOutView);
+ mExpandedController.dragBubbleOut(draggedOutView, 25, 25);
+
+ // Magnet to dismiss, verify the bubble is at the dismiss target and the callback was
+ // called.
+ mExpandedController.magnetBubbleToDismiss(
+ mViews.get(0), 100 /* velX */, 100 /* velY */, 1000 /* destY */, after);
+ waitForPropertyAnimations(DynamicAnimation.TRANSLATION_X, DynamicAnimation.TRANSLATION_Y);
+ verify(after).run();
+ assertEquals(1000, mViews.get(0).getTranslationY(), .1f);
+
+ // Dismiss the now-magneted bubble, verify that the callback was called.
+ final Runnable afterDismiss = Mockito.mock(Runnable.class);
+ mExpandedController.dismissDraggedOutBubble(afterDismiss);
+ waitForPropertyAnimations(DynamicAnimation.ALPHA);
+ verify(after).run();
+
+ waitForPropertyAnimations(DynamicAnimation.TRANSLATION_X, DynamicAnimation.TRANSLATION_Y);
+
+ assertEquals(mBubblePadding, mViews.get(1).getTranslationX(), 1f);
+ }
+
+ @Test
+ @Ignore("Flaky")
+ public void testMagnetToDismiss_demagnetizeThenDrag() throws InterruptedException {
+ expand();
+
+ final View draggedOutView = mViews.get(0);
+ final Runnable after = Mockito.mock(Runnable.class);
+
+ mExpandedController.prepareForBubbleDrag(draggedOutView);
+ mExpandedController.dragBubbleOut(draggedOutView, 25, 25);
+
+ // Magnet to dismiss, verify the bubble is at the dismiss target and the callback was
+ // called.
+ mExpandedController.magnetBubbleToDismiss(
+ draggedOutView, 100 /* velX */, 100 /* velY */, 1000 /* destY */, after);
+ waitForPropertyAnimations(DynamicAnimation.TRANSLATION_X, DynamicAnimation.TRANSLATION_Y);
+ verify(after).run();
+ assertEquals(1000, mViews.get(0).getTranslationY(), .1f);
+
+ // Demagnetize the bubble towards (25, 25).
+ mExpandedController.demagnetizeBubbleTo(25 /* x */, 25 /* y */, 100, 100);
+
+ // Start dragging towards (20, 20).
+ mExpandedController.dragBubbleOut(draggedOutView, 20, 20);
+
+ // Since we just demagnetized, the bubble shouldn't be at (20, 20), it should be animating
+ // towards it.
+ assertNotEquals(20, draggedOutView.getTranslationX());
+ assertNotEquals(20, draggedOutView.getTranslationY());
+ waitForPropertyAnimations(DynamicAnimation.TRANSLATION_X, DynamicAnimation.TRANSLATION_Y);
+
+ // Waiting for the animations should result in the bubble ending at (20, 20) since the
+ // animation end value was updated.
+ assertEquals(20, draggedOutView.getTranslationX(), 1f);
+ assertEquals(20, draggedOutView.getTranslationY(), 1f);
+
+ // Drag to (30, 30).
+ mExpandedController.dragBubbleOut(draggedOutView, 30, 30);
+
+ // It should go there instantly since the animations finished.
+ assertEquals(30, draggedOutView.getTranslationX(), 1f);
+ assertEquals(30, draggedOutView.getTranslationY(), 1f);
+ }
+
/** Expand the stack and wait for animations to finish. */
private void expand() throws InterruptedException {
mExpandedController.expandFromStack(mExpansionPoint, Mockito.mock(Runnable.class));
diff --git a/packages/SystemUI/tests/src/com/android/systemui/bubbles/animation/PhysicsAnimationLayoutTestCase.java b/packages/SystemUI/tests/src/com/android/systemui/bubbles/animation/PhysicsAnimationLayoutTestCase.java
index 9fce092ef7ce..a398fba008bb 100644
--- a/packages/SystemUI/tests/src/com/android/systemui/bubbles/animation/PhysicsAnimationLayoutTestCase.java
+++ b/packages/SystemUI/tests/src/com/android/systemui/bubbles/animation/PhysicsAnimationLayoutTestCase.java
@@ -195,9 +195,11 @@ public class PhysicsAnimationLayoutTestCase extends SysuiTestCase {
@Override
protected void animateValueForChild(DynamicAnimation.ViewProperty property, View view,
- float value, float startVel, long startDelay, Runnable[] afterCallbacks) {
+ float value, float startVel, long startDelay, float stiffness,
+ float dampingRatio, Runnable[] afterCallbacks) {
mMainThreadHandler.post(() -> super.animateValueForChild(
- property, view, value, startVel, startDelay, afterCallbacks));
+ property, view, value, startVel, startDelay, stiffness, dampingRatio,
+ afterCallbacks));
}
}
diff --git a/packages/SystemUI/tests/src/com/android/systemui/bubbles/animation/StackAnimationControllerTest.java b/packages/SystemUI/tests/src/com/android/systemui/bubbles/animation/StackAnimationControllerTest.java
index 910cee3574dd..b83276bc93da 100644
--- a/packages/SystemUI/tests/src/com/android/systemui/bubbles/animation/StackAnimationControllerTest.java
+++ b/packages/SystemUI/tests/src/com/android/systemui/bubbles/animation/StackAnimationControllerTest.java
@@ -17,6 +17,8 @@
package com.android.systemui.bubbles.animation;
import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertNotEquals;
+import static org.mockito.Mockito.verify;
import android.graphics.PointF;
import android.testing.AndroidTestingRunner;
@@ -33,6 +35,7 @@ import org.junit.Before;
import org.junit.Ignore;
import org.junit.Test;
import org.junit.runner.RunWith;
+import org.mockito.Mockito;
import org.mockito.Spy;
@SmallTest
@@ -223,6 +226,59 @@ public class StackAnimationControllerTest extends PhysicsAnimationLayoutTestCase
assertEquals(prevStackPos, mStackController.getStackPosition());
}
+ @Test
+ public void testMagnetToDismiss_dismiss() throws InterruptedException {
+ final Runnable after = Mockito.mock(Runnable.class);
+
+ // Magnet to dismiss, verify the stack is at the dismiss target and the callback was
+ // called.
+ mStackController.magnetToDismiss(100 /* velX */, 100 /* velY */, 1000 /* destY */, after);
+ waitForPropertyAnimations(DynamicAnimation.TRANSLATION_X, DynamicAnimation.TRANSLATION_Y);
+ verify(after).run();
+ assertEquals(1000, mViews.get(0).getTranslationY(), .1f);
+
+ // Dismiss the stack, verify that the callback was called.
+ final Runnable afterImplode = Mockito.mock(Runnable.class);
+ mStackController.implodeStack(afterImplode);
+ waitForPropertyAnimations(
+ DynamicAnimation.ALPHA, DynamicAnimation.SCALE_X, DynamicAnimation.SCALE_Y);
+ verify(after).run();
+ }
+
+ @Test
+ public void testMagnetToDismiss_demagnetizeThenDrag() throws InterruptedException {
+ final Runnable after = Mockito.mock(Runnable.class);
+
+ // Magnet to dismiss, verify the stack is at the dismiss target and the callback was
+ // called.
+ mStackController.magnetToDismiss(100 /* velX */, 100 /* velY */, 1000 /* destY */, after);
+ waitForPropertyAnimations(DynamicAnimation.TRANSLATION_X, DynamicAnimation.TRANSLATION_Y);
+ verify(after).run();
+
+ assertEquals(1000, mViews.get(0).getTranslationY(), .1f);
+
+ // Demagnetize towards (25, 25) and then send a touch event.
+ mStackController.demagnetizeFromDismissToPoint(25, 25, 0, 0);
+ waitForLayoutMessageQueue();
+ mStackController.moveStackFromTouch(20, 20);
+
+ // Since the stack is demagnetizing, it shouldn't be at the stack position yet.
+ assertNotEquals(20, mStackController.getStackPosition().x, 1f);
+ assertNotEquals(20, mStackController.getStackPosition().y, 1f);
+
+ waitForPropertyAnimations(DynamicAnimation.TRANSLATION_X, DynamicAnimation.TRANSLATION_Y);
+
+ // Once the animation is done it should end at the touch position coordinates.
+ assertEquals(20, mStackController.getStackPosition().x, 1f);
+ assertEquals(20, mStackController.getStackPosition().y, 1f);
+
+ mStackController.moveStackFromTouch(30, 30);
+
+ // Touches after the animation are done should change the stack position instantly.
+ assertEquals(30, mStackController.getStackPosition().x, 1f);
+ assertEquals(30, mStackController.getStackPosition().y, 1f);
+ }
+
/**
* Checks every child view to make sure it's stacked at the given coordinates, off to the left
* or right side depending on offset multiplier.
@@ -249,5 +305,13 @@ public class StackAnimationControllerTest extends PhysicsAnimationLayoutTestCase
super.flingThenSpringFirstBubbleWithStackFollowing(
property, vel, friction, spring, finalPosition));
}
+
+ @Override
+ protected void springFirstBubbleWithStackFollowing(DynamicAnimation.ViewProperty property,
+ SpringForce spring, float vel, float finalPosition) {
+ mMainThreadHandler.post(() ->
+ super.springFirstBubbleWithStackFollowing(
+ property, spring, vel, finalPosition));
+ }
}
}
diff --git a/packages/SystemUI/tests/src/com/android/systemui/statusbar/KeyguardIndicationControllerTest.java b/packages/SystemUI/tests/src/com/android/systemui/statusbar/KeyguardIndicationControllerTest.java
index 2858ba94a755..6d9a77c58227 100644
--- a/packages/SystemUI/tests/src/com/android/systemui/statusbar/KeyguardIndicationControllerTest.java
+++ b/packages/SystemUI/tests/src/com/android/systemui/statusbar/KeyguardIndicationControllerTest.java
@@ -257,7 +257,7 @@ public class KeyguardIndicationControllerTest extends SysuiTestCase {
when(mAccessibilityController.isAccessibilityEnabled()).thenReturn(true);
clickCaptor.getValue().onClick(mLockIcon);
- verify(mShadeController).showBouncer(eq(false));
+ verify(mShadeController).animateCollapsePanels(anyInt(), eq(true));
longClickCaptor.getValue().onLongClick(mLockIcon);
verify(mLockPatternUtils).requireCredentialEntry(anyInt());
diff --git a/packages/SystemUI/tests/src/com/android/systemui/statusbar/notification/row/ChannelEditorDialogControllerTest.kt b/packages/SystemUI/tests/src/com/android/systemui/statusbar/notification/row/ChannelEditorDialogControllerTest.kt
new file mode 100644
index 000000000000..76326303ff96
--- /dev/null
+++ b/packages/SystemUI/tests/src/com/android/systemui/statusbar/notification/row/ChannelEditorDialogControllerTest.kt
@@ -0,0 +1,190 @@
+/*
+ * Copyright (C) 2019 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License
+ */
+
+package com.android.systemui.statusbar.notification.row
+
+import android.app.INotificationManager
+import android.app.NotificationChannel
+import android.app.NotificationChannelGroup
+import android.app.NotificationManager.IMPORTANCE_DEFAULT
+import android.app.NotificationManager.IMPORTANCE_NONE
+import android.content.pm.ParceledListSlice
+import android.graphics.Color
+import android.graphics.drawable.ColorDrawable
+import android.print.PrintManager.PRINT_SPOOLER_PACKAGE_NAME
+import androidx.test.filters.SmallTest
+import android.testing.AndroidTestingRunner
+import android.testing.TestableLooper
+import android.view.View
+
+import com.android.systemui.SysuiTestCase
+
+import org.junit.Assert.assertEquals
+import org.junit.Before
+import org.junit.runner.RunWith
+import org.junit.Test
+import org.mockito.ArgumentMatchers.anyBoolean
+import org.mockito.ArgumentMatchers.eq
+import org.mockito.Mock
+import org.mockito.Mockito.times
+import org.mockito.Mockito.verify
+import org.mockito.Mockito.`when`
+import org.mockito.MockitoAnnotations
+
+@SmallTest
+@RunWith(AndroidTestingRunner::class)
+@TestableLooper.RunWithLooper
+class ChannelEditorDialogControllerTest : SysuiTestCase() {
+
+ private lateinit var controller: ChannelEditorDialogController
+ private lateinit var channel1: NotificationChannel
+ private lateinit var channel2: NotificationChannel
+ private lateinit var channelDefault: NotificationChannel
+ private lateinit var group: NotificationChannelGroup
+
+ private val appIcon = ColorDrawable(Color.MAGENTA)
+
+ @Mock
+ private lateinit var mockNoMan: INotificationManager
+
+ @Before
+ fun setup() {
+ MockitoAnnotations.initMocks(this)
+ controller = ChannelEditorDialogController(mContext, mockNoMan)
+
+ channel1 = NotificationChannel(TEST_CHANNEL, TEST_CHANNEL_NAME, IMPORTANCE_DEFAULT)
+ channel2 = NotificationChannel(TEST_CHANNEL2, TEST_CHANNEL_NAME2, IMPORTANCE_DEFAULT)
+ channelDefault = NotificationChannel(
+ NotificationChannel.DEFAULT_CHANNEL_ID, TEST_CHANNEL_NAME, IMPORTANCE_DEFAULT)
+
+ group = NotificationChannelGroup(TEST_GROUP_ID, TEST_GROUP_NAME)
+
+ `when`(mockNoMan.getNotificationChannelGroupsForPackage(
+ eq(TEST_PACKAGE_NAME), eq(TEST_UID), anyBoolean()))
+ .thenReturn(ParceledListSlice(listOf(group)))
+
+ `when`(mockNoMan.areNotificationsEnabledForPackage(eq(TEST_PACKAGE_NAME), eq(TEST_UID)))
+ .thenReturn(true)
+ }
+
+ @Test
+ fun testPrepareDialogForApp_noExtraChannels() {
+ group.channels = listOf(channel1, channel2)
+ controller.prepareDialogForApp(TEST_APP_NAME, TEST_PACKAGE_NAME, TEST_UID,
+ setOf(channel1, channel2), appIcon, clickListener)
+
+ assertEquals(2, controller.providedChannels.size)
+ }
+
+ @Test
+ fun testPrepareDialogForApp_onlyDefaultChannel() {
+ group.addChannel(channelDefault)
+
+ controller.prepareDialogForApp(TEST_APP_NAME, TEST_PACKAGE_NAME, TEST_UID,
+ setOf(channelDefault), appIcon, clickListener)
+
+ assertEquals("No channels should be shown when there is only the miscellaneous channel",
+ 0, controller.providedChannels.size)
+ }
+
+ @Test
+ fun testPrepareDialogForApp_noProvidedChannels_noException() {
+ group.channels = listOf()
+
+ controller.prepareDialogForApp(TEST_APP_NAME, TEST_PACKAGE_NAME, TEST_UID,
+ setOf(), appIcon, clickListener)
+ }
+
+ @Test
+ fun testPrepareDialogForApp_retrievesUpto4Channels() {
+ val channel3 = NotificationChannel("test_channel_3", "Test channel 3", IMPORTANCE_DEFAULT)
+ val channel4 = NotificationChannel("test_channel_4", "Test channel 4", IMPORTANCE_DEFAULT)
+
+ group.channels = listOf(channel1, channel2, channel3, channel4)
+
+ controller.prepareDialogForApp(TEST_APP_NAME, TEST_PACKAGE_NAME, TEST_UID,
+ setOf(channel1), appIcon, clickListener)
+
+ assertEquals("ChannelEditorDialog should fetch enough channels to show 4",
+ 4, controller.providedChannels.size)
+ }
+
+ @Test
+ fun testApply_demoteChannel() {
+ group.channels = listOf(channel1, channel2)
+ controller.prepareDialogForApp(TEST_APP_NAME, TEST_PACKAGE_NAME, TEST_UID,
+ setOf(channel1, channel2), appIcon, clickListener)
+
+ // propose an adjustment of channel1
+ controller.proposeEditForChannel(channel1, IMPORTANCE_NONE)
+
+ controller.apply()
+
+ assertEquals("Proposed edits should take effect after apply",
+ IMPORTANCE_NONE, channel1.importance)
+
+ // Channel 2 shouldn't have changed
+ assertEquals("Proposed edits should take effect after apply",
+ IMPORTANCE_DEFAULT, channel2.importance)
+ }
+
+ @Test
+ fun testApply_demoteApp() {
+ group.channels = listOf(channel1, channel2)
+ controller.prepareDialogForApp(TEST_APP_NAME, TEST_PACKAGE_NAME, TEST_UID,
+ setOf(channel1, channel2), appIcon, clickListener)
+
+ controller.appNotificationsEnabled = false
+ controller.apply()
+
+ verify(mockNoMan, times(1)).setNotificationsEnabledForPackage(
+ eq(TEST_PACKAGE_NAME), eq(TEST_UID), eq(false))
+ }
+
+ @Test
+ fun testApply_promoteApp() {
+ // App starts out disabled
+ `when`(mockNoMan.areNotificationsEnabledForPackage(eq(TEST_PACKAGE_NAME), eq(TEST_UID)))
+ .thenReturn(false)
+
+ controller.prepareDialogForApp(TEST_APP_NAME, TEST_PACKAGE_NAME, TEST_UID,
+ setOf(channel1, channel2), appIcon, clickListener)
+ controller.appNotificationsEnabled = true
+ controller.apply()
+
+ verify(mockNoMan, times(1)).setNotificationsEnabledForPackage(
+ eq(TEST_PACKAGE_NAME), eq(TEST_UID), eq(true))
+ }
+
+ private val clickListener = object : NotificationInfo.OnSettingsClickListener {
+ override fun onClick(v: View, c: NotificationChannel, appUid: Int) {
+ }
+ }
+
+ companion object {
+ const val TEST_APP_NAME = "Test App Name"
+ const val TEST_PACKAGE_NAME = "test_package"
+ const val TEST_SYSTEM_PACKAGE_NAME = PRINT_SPOOLER_PACKAGE_NAME
+ const val TEST_UID = 1
+ const val MULTIPLE_CHANNEL_COUNT = 2
+ const val TEST_CHANNEL = "test_channel"
+ const val TEST_CHANNEL_NAME = "Test Channel Name"
+ const val TEST_CHANNEL2 = "test_channel2"
+ const val TEST_CHANNEL_NAME2 = "Test Channel Name2"
+ const val TEST_GROUP_ID = "test_group_id"
+ const val TEST_GROUP_NAME = "Test Group Name"
+ }
+}
diff --git a/packages/SystemUI/tests/src/com/android/systemui/statusbar/notification/row/NotificationGutsManagerTest.java b/packages/SystemUI/tests/src/com/android/systemui/statusbar/notification/row/NotificationGutsManagerTest.java
index 5f0839dfc171..6376bd3e00e4 100644
--- a/packages/SystemUI/tests/src/com/android/systemui/statusbar/notification/row/NotificationGutsManagerTest.java
+++ b/packages/SystemUI/tests/src/com/android/systemui/statusbar/notification/row/NotificationGutsManagerTest.java
@@ -31,6 +31,7 @@ import static org.junit.Assert.fail;
import static org.mockito.ArgumentMatchers.any;
import static org.mockito.ArgumentMatchers.anyBoolean;
import static org.mockito.ArgumentMatchers.anyInt;
+import static org.mockito.ArgumentMatchers.anySet;
import static org.mockito.ArgumentMatchers.eq;
import static org.mockito.Mockito.doNothing;
import static org.mockito.Mockito.doReturn;
@@ -317,7 +318,7 @@ public class NotificationGutsManagerTest extends SysuiTestCase {
any(INotificationManager.class),
eq(statusBarNotification.getPackageName()),
any(NotificationChannel.class),
- anyInt(),
+ anySet(),
eq(statusBarNotification),
any(NotificationInfo.CheckSaveListener.class),
any(NotificationInfo.OnSettingsClickListener.class),
@@ -345,7 +346,7 @@ public class NotificationGutsManagerTest extends SysuiTestCase {
any(INotificationManager.class),
eq(statusBarNotification.getPackageName()),
any(NotificationChannel.class),
- anyInt(),
+ anySet(),
eq(statusBarNotification),
any(NotificationInfo.CheckSaveListener.class),
any(NotificationInfo.OnSettingsClickListener.class),
@@ -375,7 +376,7 @@ public class NotificationGutsManagerTest extends SysuiTestCase {
any(INotificationManager.class),
eq(statusBarNotification.getPackageName()),
any(NotificationChannel.class),
- anyInt(),
+ anySet(),
eq(statusBarNotification),
any(NotificationInfo.CheckSaveListener.class),
any(NotificationInfo.OnSettingsClickListener.class),
@@ -404,7 +405,7 @@ public class NotificationGutsManagerTest extends SysuiTestCase {
any(INotificationManager.class),
eq(statusBarNotification.getPackageName()),
any(NotificationChannel.class),
- anyInt(),
+ anySet(),
eq(statusBarNotification),
any(NotificationInfo.CheckSaveListener.class),
any(NotificationInfo.OnSettingsClickListener.class),
@@ -432,7 +433,7 @@ public class NotificationGutsManagerTest extends SysuiTestCase {
any(INotificationManager.class),
eq(statusBarNotification.getPackageName()),
any(NotificationChannel.class),
- anyInt(),
+ anySet(),
eq(statusBarNotification),
any(NotificationInfo.CheckSaveListener.class),
any(NotificationInfo.OnSettingsClickListener.class),
diff --git a/packages/SystemUI/tests/src/com/android/systemui/statusbar/notification/row/NotificationInfoTest.java b/packages/SystemUI/tests/src/com/android/systemui/statusbar/notification/row/NotificationInfoTest.java
index 7bd25808a9c5..06acc73ac48c 100644
--- a/packages/SystemUI/tests/src/com/android/systemui/statusbar/notification/row/NotificationInfoTest.java
+++ b/packages/SystemUI/tests/src/com/android/systemui/statusbar/notification/row/NotificationInfoTest.java
@@ -20,7 +20,6 @@ import static android.app.NotificationChannel.USER_LOCKED_IMPORTANCE;
import static android.app.NotificationManager.IMPORTANCE_DEFAULT;
import static android.app.NotificationManager.IMPORTANCE_LOW;
import static android.app.NotificationManager.IMPORTANCE_MIN;
-import static android.app.NotificationManager.IMPORTANCE_NONE;
import static android.app.NotificationManager.IMPORTANCE_UNSPECIFIED;
import static android.print.PrintManager.PRINT_SPOOLER_PACKAGE_NAME;
import static android.provider.Settings.Secure.NOTIFICATION_NEW_INTERRUPTION_MODEL;
@@ -54,7 +53,6 @@ import android.content.pm.ApplicationInfo;
import android.content.pm.PackageInfo;
import android.content.pm.PackageManager;
import android.graphics.drawable.Drawable;
-import android.metrics.LogMaker;
import android.os.IBinder;
import android.os.UserHandle;
import android.provider.Settings;
@@ -70,7 +68,6 @@ import android.widget.ImageView;
import android.widget.TextView;
import com.android.internal.logging.MetricsLogger;
-import com.android.internal.logging.nano.MetricsProto;
import com.android.internal.logging.nano.MetricsProto.MetricsEvent;
import com.android.systemui.Dependency;
import com.android.systemui.R;
@@ -86,6 +83,8 @@ import org.mockito.Mock;
import org.mockito.junit.MockitoJUnit;
import org.mockito.junit.MockitoRule;
+import java.util.HashSet;
+import java.util.Set;
import java.util.concurrent.CountDownLatch;
@SmallTest
@@ -103,6 +102,8 @@ public class NotificationInfoTest extends SysuiTestCase {
private NotificationInfo mNotificationInfo;
private NotificationChannel mNotificationChannel;
private NotificationChannel mDefaultNotificationChannel;
+ private Set<NotificationChannel> mNotificationChannelSet = new HashSet<>();
+ private Set<NotificationChannel> mDefaultNotificationChannelSet = new HashSet<>();
private StatusBarNotification mSbn;
@Rule
@@ -153,9 +154,11 @@ public class NotificationInfoTest extends SysuiTestCase {
// Some test channels.
mNotificationChannel = new NotificationChannel(
TEST_CHANNEL, TEST_CHANNEL_NAME, IMPORTANCE_LOW);
+ mNotificationChannelSet.add(mNotificationChannel);
mDefaultNotificationChannel = new NotificationChannel(
NotificationChannel.DEFAULT_CHANNEL_ID, TEST_CHANNEL_NAME,
IMPORTANCE_LOW);
+ mDefaultNotificationChannelSet.add(mDefaultNotificationChannel);
mSbn = new StatusBarNotification(TEST_PACKAGE_NAME, TEST_PACKAGE_NAME, 0, null, TEST_UID, 0,
new Notification(), UserHandle.CURRENT, null, 0);
@@ -191,7 +194,7 @@ public class NotificationInfoTest extends SysuiTestCase {
public void testBindNotification_SetsTextApplicationName() throws Exception {
when(mMockPackageManager.getApplicationLabel(any())).thenReturn("App Name");
mNotificationInfo.bindNotification(mMockPackageManager, mMockINotificationManager,
- TEST_PACKAGE_NAME, mNotificationChannel, 1, mSbn,
+ TEST_PACKAGE_NAME, mNotificationChannel, mNotificationChannelSet, mSbn,
null, null, null,
true, false,
IMPORTANCE_DEFAULT, true);
@@ -206,7 +209,8 @@ public class NotificationInfoTest extends SysuiTestCase {
when(mMockPackageManager.getApplicationIcon(any(ApplicationInfo.class)))
.thenReturn(iconDrawable);
mNotificationInfo.bindNotification(mMockPackageManager, mMockINotificationManager,
- TEST_PACKAGE_NAME, mNotificationChannel, 1, mSbn, null, null, null, true, false,
+ TEST_PACKAGE_NAME, mNotificationChannel, mNotificationChannelSet, mSbn,
+ null, null, null, true, false,
IMPORTANCE_DEFAULT, true);
final ImageView iconView = mNotificationInfo.findViewById(R.id.pkgicon);
assertEquals(iconDrawable, iconView.getDrawable());
@@ -215,7 +219,8 @@ public class NotificationInfoTest extends SysuiTestCase {
@Test
public void testBindNotification_noDelegate() throws Exception {
mNotificationInfo.bindNotification(mMockPackageManager, mMockINotificationManager,
- TEST_PACKAGE_NAME, mNotificationChannel, 1, mSbn, null, null, null, true, false,
+ TEST_PACKAGE_NAME, mNotificationChannel, mNotificationChannelSet, mSbn,
+ null, null, null, true, false,
IMPORTANCE_DEFAULT, true);
final TextView nameView = mNotificationInfo.findViewById(R.id.delegate_name);
assertEquals(GONE, nameView.getVisibility());
@@ -234,7 +239,8 @@ public class NotificationInfoTest extends SysuiTestCase {
when(mMockPackageManager.getApplicationLabel(any())).thenReturn("Other");
mNotificationInfo.bindNotification(mMockPackageManager, mMockINotificationManager,
- TEST_PACKAGE_NAME, mNotificationChannel, 1, mSbn, null, null, null, true, false,
+ TEST_PACKAGE_NAME, mNotificationChannel, mNotificationChannelSet, mSbn, null, null,
+ null, true, false,
IMPORTANCE_DEFAULT, true);
final TextView nameView = mNotificationInfo.findViewById(R.id.delegate_name);
assertEquals(VISIBLE, nameView.getVisibility());
@@ -246,7 +252,8 @@ public class NotificationInfoTest extends SysuiTestCase {
@Test
public void testBindNotification_GroupNameHiddenIfNoGroup() throws Exception {
mNotificationInfo.bindNotification(mMockPackageManager, mMockINotificationManager,
- TEST_PACKAGE_NAME, mNotificationChannel, 1, mSbn, null, null, null, true, false,
+ TEST_PACKAGE_NAME, mNotificationChannel, mNotificationChannelSet, mSbn, null, null,
+ null, true, false,
IMPORTANCE_DEFAULT, true);
final TextView groupNameView = mNotificationInfo.findViewById(R.id.group_name);
assertEquals(GONE, groupNameView.getVisibility());
@@ -261,7 +268,8 @@ public class NotificationInfoTest extends SysuiTestCase {
eq("test_group_id"), eq(TEST_PACKAGE_NAME), eq(TEST_UID)))
.thenReturn(notificationChannelGroup);
mNotificationInfo.bindNotification(mMockPackageManager, mMockINotificationManager,
- TEST_PACKAGE_NAME, mNotificationChannel, 1, mSbn, null, null, null, true, false,
+ TEST_PACKAGE_NAME, mNotificationChannel, mNotificationChannelSet, mSbn, null, null,
+ null, true, false,
IMPORTANCE_DEFAULT, true);
final TextView groupNameView = mNotificationInfo.findViewById(R.id.group_name);
assertEquals(View.VISIBLE, groupNameView.getVisibility());
@@ -271,7 +279,8 @@ public class NotificationInfoTest extends SysuiTestCase {
@Test
public void testBindNotification_SetsTextChannelName() throws Exception {
mNotificationInfo.bindNotification(mMockPackageManager, mMockINotificationManager,
- TEST_PACKAGE_NAME, mNotificationChannel, 1, mSbn, null, null, null, true, false,
+ TEST_PACKAGE_NAME, mNotificationChannel, mNotificationChannelSet, mSbn, null, null,
+ null, true, false,
IMPORTANCE_DEFAULT, true);
final TextView textView = mNotificationInfo.findViewById(R.id.channel_name);
assertEquals(TEST_CHANNEL_NAME, textView.getText());
@@ -280,8 +289,8 @@ public class NotificationInfoTest extends SysuiTestCase {
@Test
public void testBindNotification_DefaultChannelDoesNotUseChannelName() throws Exception {
mNotificationInfo.bindNotification(mMockPackageManager, mMockINotificationManager,
- TEST_PACKAGE_NAME, mDefaultNotificationChannel, 1, mSbn, null, null, null, true,
- false, IMPORTANCE_DEFAULT, true);
+ TEST_PACKAGE_NAME, mDefaultNotificationChannel, mDefaultNotificationChannelSet,
+ mSbn, null, null, null, true, false, IMPORTANCE_DEFAULT, true);
final TextView textView = mNotificationInfo.findViewById(R.id.channel_name);
assertEquals(GONE, textView.getVisibility());
}
@@ -293,7 +302,8 @@ public class NotificationInfoTest extends SysuiTestCase {
when(mMockINotificationManager.getNumNotificationChannelsForPackage(
eq(TEST_PACKAGE_NAME), eq(TEST_UID), anyBoolean())).thenReturn(10);
mNotificationInfo.bindNotification(mMockPackageManager, mMockINotificationManager,
- TEST_PACKAGE_NAME, mDefaultNotificationChannel, 1, mSbn, null, null, null, true,
+ TEST_PACKAGE_NAME, mDefaultNotificationChannel, mDefaultNotificationChannelSet,
+ mSbn, null, null, null, true,
false, IMPORTANCE_DEFAULT, true);
final TextView textView = mNotificationInfo.findViewById(R.id.channel_name);
assertEquals(VISIBLE, textView.getVisibility());
@@ -302,7 +312,8 @@ public class NotificationInfoTest extends SysuiTestCase {
@Test
public void testBindNotification_UnblockablePackageUsesChannelName() throws Exception {
mNotificationInfo.bindNotification(mMockPackageManager, mMockINotificationManager,
- TEST_PACKAGE_NAME, mNotificationChannel, 1, mSbn, null, null, null, true, true,
+ TEST_PACKAGE_NAME, mNotificationChannel, mNotificationChannelSet, mSbn, null, null,
+ null, true, true,
IMPORTANCE_DEFAULT, true);
final TextView textView = mNotificationInfo.findViewById(R.id.channel_name);
assertEquals(VISIBLE, textView.getVisibility());
@@ -311,7 +322,7 @@ public class NotificationInfoTest extends SysuiTestCase {
@Test
public void testBindNotification_BlockLink_BlockingHelper() throws Exception {
mNotificationInfo.bindNotification(mMockPackageManager, mMockINotificationManager,
- TEST_PACKAGE_NAME, mNotificationChannel, 1, mSbn, null, mock(
+ TEST_PACKAGE_NAME, mNotificationChannel, mNotificationChannelSet, mSbn, null, mock(
NotificationInfo.OnSettingsClickListener.class), null, true, false,
true /* isBlockingHelper */, IMPORTANCE_DEFAULT, true);
final View block =
@@ -326,7 +337,7 @@ public class NotificationInfoTest extends SysuiTestCase {
public void testBindNotification_SetsOnClickListenerForSettings() throws Exception {
final CountDownLatch latch = new CountDownLatch(1);
mNotificationInfo.bindNotification(mMockPackageManager, mMockINotificationManager,
- TEST_PACKAGE_NAME, mNotificationChannel, 1, mSbn, null,
+ TEST_PACKAGE_NAME, mNotificationChannel, mNotificationChannelSet, mSbn, null,
(View v, NotificationChannel c, int appUid) -> {
assertEquals(mNotificationChannel, c);
latch.countDown();
@@ -341,7 +352,8 @@ public class NotificationInfoTest extends SysuiTestCase {
@Test
public void testBindNotification_SettingsButtonInvisibleWhenNoClickListener() throws Exception {
mNotificationInfo.bindNotification(mMockPackageManager, mMockINotificationManager,
- TEST_PACKAGE_NAME, mNotificationChannel, 1, mSbn, null, null, null, true, false,
+ TEST_PACKAGE_NAME, mNotificationChannel, mNotificationChannelSet, mSbn, null, null,
+ null, true, false,
IMPORTANCE_DEFAULT, true);
final View settingsButton = mNotificationInfo.findViewById(R.id.info);
assertTrue(settingsButton.getVisibility() != View.VISIBLE);
@@ -351,7 +363,7 @@ public class NotificationInfoTest extends SysuiTestCase {
public void testBindNotification_SettingsButtonInvisibleWhenDeviceUnprovisioned()
throws Exception {
mNotificationInfo.bindNotification(mMockPackageManager, mMockINotificationManager,
- TEST_PACKAGE_NAME, mNotificationChannel, 1, mSbn, null,
+ TEST_PACKAGE_NAME, mNotificationChannel, mNotificationChannelSet, mSbn, null,
(View v, NotificationChannel c, int appUid) -> {
assertEquals(mNotificationChannel, c);
}, null, false, false, IMPORTANCE_DEFAULT, true);
@@ -362,10 +374,11 @@ public class NotificationInfoTest extends SysuiTestCase {
@Test
public void testBindNotification_SettingsButtonReappearsAfterSecondBind() throws Exception {
mNotificationInfo.bindNotification(mMockPackageManager, mMockINotificationManager,
- TEST_PACKAGE_NAME, mNotificationChannel, 1, mSbn, null, null, null, true, false,
+ TEST_PACKAGE_NAME, mNotificationChannel, mNotificationChannelSet, mSbn, null, null,
+ null, true, false,
IMPORTANCE_DEFAULT, true);
mNotificationInfo.bindNotification(mMockPackageManager, mMockINotificationManager,
- TEST_PACKAGE_NAME, mNotificationChannel, 1, mSbn, null,
+ TEST_PACKAGE_NAME, mNotificationChannel, mNotificationChannelSet, mSbn, null,
(View v, NotificationChannel c, int appUid) -> {
}, null, true, false, IMPORTANCE_DEFAULT, true);
final View settingsButton = mNotificationInfo.findViewById(R.id.info);
@@ -375,7 +388,7 @@ public class NotificationInfoTest extends SysuiTestCase {
@Test
public void testBindNotificationLogging_notBlockingHelper() throws Exception {
mNotificationInfo.bindNotification(mMockPackageManager, mMockINotificationManager,
- TEST_PACKAGE_NAME, mNotificationChannel, 1, mSbn,
+ TEST_PACKAGE_NAME, mNotificationChannel, mNotificationChannelSet, mSbn,
null, null, null,
true, false,
IMPORTANCE_DEFAULT, true);
@@ -389,7 +402,7 @@ public class NotificationInfoTest extends SysuiTestCase {
@Test
public void testBindNotificationLogging_BlockingHelper() throws Exception {
mNotificationInfo.bindNotification(mMockPackageManager, mMockINotificationManager,
- TEST_PACKAGE_NAME, mNotificationChannel, 1, mSbn,
+ TEST_PACKAGE_NAME, mNotificationChannel, mNotificationChannelSet, mSbn,
null, null, null,
false, true,
true,
@@ -404,7 +417,7 @@ public class NotificationInfoTest extends SysuiTestCase {
@Test
public void testLogBlockingHelperCounter_logsForBlockingHelper() throws Exception {
mNotificationInfo.bindNotification(mMockPackageManager, mMockINotificationManager,
- TEST_PACKAGE_NAME, mNotificationChannel, 1, mSbn,
+ TEST_PACKAGE_NAME, mNotificationChannel, mNotificationChannelSet, mSbn,
null, null, null,
false, true,
true,
@@ -417,7 +430,8 @@ public class NotificationInfoTest extends SysuiTestCase {
public void testOnClickListenerPassesNullChannelForBundle() throws Exception {
final CountDownLatch latch = new CountDownLatch(1);
mNotificationInfo.bindNotification(mMockPackageManager, mMockINotificationManager,
- TEST_PACKAGE_NAME, mNotificationChannel, MULTIPLE_CHANNEL_COUNT, mSbn, null,
+ TEST_PACKAGE_NAME, mNotificationChannel,
+ createMultipleChannelSet(MULTIPLE_CHANNEL_COUNT), mSbn, null,
(View v, NotificationChannel c, int appUid) -> {
assertEquals(null, c);
latch.countDown();
@@ -433,7 +447,8 @@ public class NotificationInfoTest extends SysuiTestCase {
public void testBindNotification_ChannelNameInvisibleWhenBundleFromDifferentChannels()
throws Exception {
mNotificationInfo.bindNotification(mMockPackageManager, mMockINotificationManager,
- TEST_PACKAGE_NAME, mNotificationChannel, MULTIPLE_CHANNEL_COUNT, mSbn, null, null,
+ TEST_PACKAGE_NAME, mNotificationChannel,
+ createMultipleChannelSet(MULTIPLE_CHANNEL_COUNT), mSbn, null, null,
null, true, false, IMPORTANCE_DEFAULT, true);
final TextView channelNameView =
mNotificationInfo.findViewById(R.id.channel_name);
@@ -444,7 +459,8 @@ public class NotificationInfoTest extends SysuiTestCase {
@UiThreadTest
public void testStopInvisibleIfBundleFromDifferentChannels() throws Exception {
mNotificationInfo.bindNotification(mMockPackageManager, mMockINotificationManager,
- TEST_PACKAGE_NAME, mNotificationChannel, MULTIPLE_CHANNEL_COUNT, mSbn, null, null,
+ TEST_PACKAGE_NAME, mNotificationChannel,
+ createMultipleChannelSet(MULTIPLE_CHANNEL_COUNT), mSbn, null, null,
null, true, false, IMPORTANCE_DEFAULT, true);
assertEquals(GONE, mNotificationInfo.findViewById(
R.id.interruptiveness_settings).getVisibility());
@@ -455,7 +471,8 @@ public class NotificationInfoTest extends SysuiTestCase {
@Test
public void testBindNotification_whenAppUnblockable() throws Exception {
mNotificationInfo.bindNotification(mMockPackageManager, mMockINotificationManager,
- TEST_PACKAGE_NAME, mNotificationChannel, 1, mSbn, null, null, null, true, true,
+ TEST_PACKAGE_NAME, mNotificationChannel, mNotificationChannelSet, mSbn, null, null,
+ null, true, true,
IMPORTANCE_DEFAULT, true);
final TextView view = mNotificationInfo.findViewById(R.id.non_configurable_text);
assertEquals(View.VISIBLE, view.getVisibility());
@@ -468,7 +485,8 @@ public class NotificationInfoTest extends SysuiTestCase {
@Test
public void testBindNotification_DoesNotUpdateNotificationChannel() throws Exception {
mNotificationInfo.bindNotification(mMockPackageManager, mMockINotificationManager,
- TEST_PACKAGE_NAME, mNotificationChannel, 1, mSbn, null, null, null, true, false,
+ TEST_PACKAGE_NAME, mNotificationChannel, mNotificationChannelSet, mSbn, null, null,
+ null, true, false,
IMPORTANCE_DEFAULT, true);
mTestableLooper.processAllMessages();
verify(mMockINotificationManager, never()).updateNotificationChannelForPackage(
@@ -479,7 +497,8 @@ public class NotificationInfoTest extends SysuiTestCase {
public void testDoesNotUpdateNotificationChannelAfterImportanceChanged() throws Exception {
mNotificationChannel.setImportance(IMPORTANCE_LOW);
mNotificationInfo.bindNotification(mMockPackageManager, mMockINotificationManager,
- TEST_PACKAGE_NAME, mNotificationChannel, 1, mSbn, null, null, null, true, false,
+ TEST_PACKAGE_NAME, mNotificationChannel, mNotificationChannelSet, mSbn, null, null,
+ null, true, false,
IMPORTANCE_LOW, false);
mNotificationInfo.findViewById(R.id.alert).performClick();
@@ -493,7 +512,8 @@ public class NotificationInfoTest extends SysuiTestCase {
throws Exception {
mNotificationChannel.setImportance(IMPORTANCE_DEFAULT);
mNotificationInfo.bindNotification(mMockPackageManager, mMockINotificationManager,
- TEST_PACKAGE_NAME, mNotificationChannel, 1, mSbn, null, null, null, true, false,
+ TEST_PACKAGE_NAME, mNotificationChannel, mNotificationChannelSet, mSbn, null, null,
+ null, true, false,
IMPORTANCE_DEFAULT, true);
mNotificationInfo.findViewById(R.id.silence).performClick();
@@ -507,7 +527,8 @@ public class NotificationInfoTest extends SysuiTestCase {
throws Exception {
int originalImportance = mNotificationChannel.getImportance();
mNotificationInfo.bindNotification(mMockPackageManager, mMockINotificationManager,
- TEST_PACKAGE_NAME, mNotificationChannel, 1, mSbn, null, null, null, true, false,
+ TEST_PACKAGE_NAME, mNotificationChannel, mNotificationChannelSet, mSbn, null, null,
+ null, true, false,
IMPORTANCE_DEFAULT, true);
mNotificationInfo.handleCloseControls(true, false);
@@ -522,7 +543,8 @@ public class NotificationInfoTest extends SysuiTestCase {
throws Exception {
mNotificationChannel.setImportance(IMPORTANCE_UNSPECIFIED);
mNotificationInfo.bindNotification(mMockPackageManager, mMockINotificationManager,
- TEST_PACKAGE_NAME, mNotificationChannel, 1, mSbn, null, null, null, true, false,
+ TEST_PACKAGE_NAME, mNotificationChannel, mNotificationChannelSet, mSbn, null, null,
+ null, true, false,
IMPORTANCE_UNSPECIFIED, true);
mNotificationInfo.handleCloseControls(true, false);
@@ -541,7 +563,8 @@ public class NotificationInfoTest extends SysuiTestCase {
mNotificationChannel.setImportance(IMPORTANCE_DEFAULT);
mNotificationInfo.bindNotification(mMockPackageManager, mMockINotificationManager,
TEST_PACKAGE_NAME, mNotificationChannel /* notificationChannel */,
- 10 /* numUniqueChannelsInRow */, mSbn, listener /* checkSaveListener */,
+ createMultipleChannelSet(10) /* numUniqueChannelsInRow */, mSbn,
+ listener /* checkSaveListener */,
null /* onSettingsClick */, null /* onAppSettingsClick */, true /* provisioned */,
false /* isNonblockable */, true /* isForBlockingHelper */,
IMPORTANCE_DEFAULT, true);
@@ -570,7 +593,8 @@ public class NotificationInfoTest extends SysuiTestCase {
mNotificationChannel.setImportance(IMPORTANCE_DEFAULT);
mNotificationInfo.bindNotification(mMockPackageManager, mMockINotificationManager,
TEST_PACKAGE_NAME, mNotificationChannel /* notificationChannel */,
- 10 /* numUniqueChannelsInRow */, mSbn, listener /* checkSaveListener */,
+ createMultipleChannelSet(10) /* numUniqueChannelsInRow */, mSbn,
+ listener /* checkSaveListener */,
null /* onSettingsClick */, null /* onAppSettingsClick */,
false /* isNonblockable */, true /* isForBlockingHelper */,
true, IMPORTANCE_DEFAULT, true);
@@ -589,7 +613,8 @@ public class NotificationInfoTest extends SysuiTestCase {
mNotificationChannel.setImportance(IMPORTANCE_DEFAULT);
mNotificationInfo.bindNotification(mMockPackageManager, mMockINotificationManager,
TEST_PACKAGE_NAME, mNotificationChannel /* notificationChannel */,
- 10 /* numUniqueChannelsInRow */, mSbn, listener /* checkSaveListener */,
+ createMultipleChannelSet(10) /* numUniqueChannelsInRow */, mSbn,
+ listener /* checkSaveListener */,
null /* onSettingsClick */, null /* onAppSettingsClick */,
true /* provisioned */,
false /* isNonblockable */, true /* isForBlockingHelper */,
@@ -608,7 +633,7 @@ public class NotificationInfoTest extends SysuiTestCase {
mMockINotificationManager,
TEST_PACKAGE_NAME,
mNotificationChannel,
- 1 /* numChannels */,
+ mNotificationChannelSet /* numChannels */,
mSbn,
null /* checkSaveListener */,
null /* onSettingsClick */,
@@ -635,7 +660,7 @@ public class NotificationInfoTest extends SysuiTestCase {
mMockINotificationManager,
TEST_PACKAGE_NAME,
mNotificationChannel,
- 1 /* numChannels */,
+ mNotificationChannelSet /* numChannels */,
mSbn,
null /* checkSaveListener */,
null /* onSettingsClick */,
@@ -664,7 +689,8 @@ public class NotificationInfoTest extends SysuiTestCase {
public void testKeepUpdatesNotificationChannel_blockingHelper() throws Exception {
mNotificationChannel.setImportance(IMPORTANCE_LOW);
mNotificationInfo.bindNotification(mMockPackageManager, mMockINotificationManager,
- TEST_PACKAGE_NAME, mNotificationChannel, 1, mSbn, null, null, null, true, true,
+ TEST_PACKAGE_NAME, mNotificationChannel, mNotificationChannelSet, mSbn, null, null,
+ null, true, true,
IMPORTANCE_LOW, false);
mNotificationInfo.findViewById(R.id.keep_showing).performClick();
@@ -683,7 +709,8 @@ public class NotificationInfoTest extends SysuiTestCase {
public void testNoActionsUpdatesNotificationChannel_blockingHelper() throws Exception {
mNotificationChannel.setImportance(IMPORTANCE_DEFAULT);
mNotificationInfo.bindNotification(mMockPackageManager, mMockINotificationManager,
- TEST_PACKAGE_NAME, mNotificationChannel, 1, mSbn, null, null, null, true, true,
+ TEST_PACKAGE_NAME, mNotificationChannel, mNotificationChannelSet, mSbn, null, null,
+ null, true, true,
IMPORTANCE_DEFAULT, true);
mNotificationInfo.handleCloseControls(true, false);
@@ -701,7 +728,8 @@ public class NotificationInfoTest extends SysuiTestCase {
public void testSilenceCallsUpdateNotificationChannel() throws Exception {
mNotificationChannel.setImportance(IMPORTANCE_DEFAULT);
mNotificationInfo.bindNotification(mMockPackageManager, mMockINotificationManager,
- TEST_PACKAGE_NAME, mNotificationChannel, 1, mSbn, null, null, null, true, false,
+ TEST_PACKAGE_NAME, mNotificationChannel, mNotificationChannelSet, mSbn, null, null,
+ null, true, false,
IMPORTANCE_DEFAULT, true);
mNotificationInfo.findViewById(R.id.silence).performClick();
@@ -722,7 +750,8 @@ public class NotificationInfoTest extends SysuiTestCase {
public void testUnSilenceCallsUpdateNotificationChannel() throws Exception {
mNotificationChannel.setImportance(IMPORTANCE_LOW);
mNotificationInfo.bindNotification(mMockPackageManager, mMockINotificationManager,
- TEST_PACKAGE_NAME, mNotificationChannel, 1, mSbn, null, null, null, true, false,
+ TEST_PACKAGE_NAME, mNotificationChannel, mNotificationChannelSet, mSbn, null, null,
+ null, true, false,
IMPORTANCE_LOW, false);
mNotificationInfo.findViewById(R.id.alert).performClick();
@@ -744,7 +773,8 @@ public class NotificationInfoTest extends SysuiTestCase {
throws Exception {
mNotificationChannel.setImportance(IMPORTANCE_UNSPECIFIED);
mNotificationInfo.bindNotification(mMockPackageManager, mMockINotificationManager,
- TEST_PACKAGE_NAME, mNotificationChannel, 1, mSbn, null, null, null, true, false,
+ TEST_PACKAGE_NAME, mNotificationChannel, mNotificationChannelSet, mSbn, null, null,
+ null, true, false,
IMPORTANCE_UNSPECIFIED, true);
mNotificationInfo.findViewById(R.id.silence).performClick();
@@ -766,7 +796,8 @@ public class NotificationInfoTest extends SysuiTestCase {
throws Exception {
mNotificationChannel.setImportance(IMPORTANCE_MIN);
mNotificationInfo.bindNotification(mMockPackageManager, mMockINotificationManager,
- TEST_PACKAGE_NAME, mNotificationChannel, 1, mSbn, null, null, null, true, false,
+ TEST_PACKAGE_NAME, mNotificationChannel, mNotificationChannelSet, mSbn, null, null,
+ null, true, false,
IMPORTANCE_MIN, false);
assertEquals(mContext.getString(R.string.inline_done_button),
@@ -782,7 +813,7 @@ public class NotificationInfoTest extends SysuiTestCase {
ArgumentCaptor.forClass(NotificationChannel.class);
verify(mMockINotificationManager, times(1)).updateNotificationChannelForPackage(
anyString(), eq(TEST_UID), updated.capture());
- assertTrue((updated.getValue().getUserLockedFields()& USER_LOCKED_IMPORTANCE) != 0);
+ assertTrue((updated.getValue().getUserLockedFields() & USER_LOCKED_IMPORTANCE) != 0);
assertEquals(IMPORTANCE_MIN, updated.getValue().getImportance());
}
@@ -791,7 +822,8 @@ public class NotificationInfoTest extends SysuiTestCase {
throws Exception {
mNotificationChannel.setImportance(IMPORTANCE_MIN);
mNotificationInfo.bindNotification(mMockPackageManager, mMockINotificationManager,
- TEST_PACKAGE_NAME, mNotificationChannel, 1, mSbn, null, null, null, true, false,
+ TEST_PACKAGE_NAME, mNotificationChannel, mNotificationChannelSet, mSbn, null, null,
+ null, true, false,
IMPORTANCE_MIN, false);
assertEquals(mContext.getString(R.string.inline_done_button),
@@ -807,7 +839,7 @@ public class NotificationInfoTest extends SysuiTestCase {
ArgumentCaptor.forClass(NotificationChannel.class);
verify(mMockINotificationManager, times(1)).updateNotificationChannelForPackage(
anyString(), eq(TEST_UID), updated.capture());
- assertTrue((updated.getValue().getUserLockedFields()& USER_LOCKED_IMPORTANCE) != 0);
+ assertTrue((updated.getValue().getUserLockedFields() & USER_LOCKED_IMPORTANCE) != 0);
assertEquals(IMPORTANCE_DEFAULT, updated.getValue().getImportance());
}
@@ -816,7 +848,8 @@ public class NotificationInfoTest extends SysuiTestCase {
throws Exception {
mNotificationChannel.setImportance(IMPORTANCE_LOW);
mNotificationInfo.bindNotification(mMockPackageManager, mMockINotificationManager,
- TEST_PACKAGE_NAME, mNotificationChannel, 1, mSbn, null, null, null, true, false,
+ TEST_PACKAGE_NAME, mNotificationChannel, mNotificationChannelSet, mSbn, null, null,
+ null, true, false,
IMPORTANCE_LOW, false);
assertEquals(mContext.getString(R.string.inline_done_button),
@@ -834,7 +867,8 @@ public class NotificationInfoTest extends SysuiTestCase {
throws Exception {
mNotificationChannel.setImportance(IMPORTANCE_LOW);
mNotificationInfo.bindNotification(mMockPackageManager, mMockINotificationManager,
- TEST_PACKAGE_NAME, mNotificationChannel, 1, mSbn, null, null, null, true, false,
+ TEST_PACKAGE_NAME, mNotificationChannel, mNotificationChannelSet, mSbn, null, null,
+ null, true, false,
IMPORTANCE_LOW, false);
mNotificationInfo.findViewById(R.id.alert).performClick();
@@ -855,7 +889,8 @@ public class NotificationInfoTest extends SysuiTestCase {
public void testCloseControlsDoesNotUpdateIfSaveIsFalse() throws Exception {
mNotificationChannel.setImportance(IMPORTANCE_LOW);
mNotificationInfo.bindNotification(mMockPackageManager, mMockINotificationManager,
- TEST_PACKAGE_NAME, mNotificationChannel, 1, mSbn, null, null, null, true, false,
+ TEST_PACKAGE_NAME, mNotificationChannel, mNotificationChannelSet, mSbn, null, null,
+ null, true, false,
IMPORTANCE_LOW, false);
mNotificationInfo.findViewById(R.id.alert).performClick();
@@ -871,7 +906,7 @@ public class NotificationInfoTest extends SysuiTestCase {
public void testCloseControlsUpdatesWhenCheckSaveListenerUsesCallback() throws Exception {
mNotificationChannel.setImportance(IMPORTANCE_LOW);
mNotificationInfo.bindNotification(mMockPackageManager, mMockINotificationManager,
- TEST_PACKAGE_NAME, mNotificationChannel, 1, mSbn,
+ TEST_PACKAGE_NAME, mNotificationChannel, mNotificationChannelSet, mSbn,
(Runnable saveImportance, StatusBarNotification sbn) -> {
saveImportance.run();
}, null, null, true, false, IMPORTANCE_LOW, false
@@ -894,7 +929,7 @@ public class NotificationInfoTest extends SysuiTestCase {
public void testCloseControls_withoutHittingApply() throws Exception {
mNotificationChannel.setImportance(IMPORTANCE_LOW);
mNotificationInfo.bindNotification(mMockPackageManager, mMockINotificationManager,
- TEST_PACKAGE_NAME, mNotificationChannel, 1, mSbn,
+ TEST_PACKAGE_NAME, mNotificationChannel, mNotificationChannelSet, mSbn,
(Runnable saveImportance, StatusBarNotification sbn) -> {
saveImportance.run();
}, null, null, true, false, IMPORTANCE_LOW, false
@@ -910,7 +945,7 @@ public class NotificationInfoTest extends SysuiTestCase {
assertFalse(mNotificationInfo.willBeRemoved());
mNotificationInfo.bindNotification(mMockPackageManager, mMockINotificationManager,
- TEST_PACKAGE_NAME, mNotificationChannel, 1, mSbn,
+ TEST_PACKAGE_NAME, mNotificationChannel, mNotificationChannelSet, mSbn,
(Runnable saveImportance, StatusBarNotification sbn) -> {
saveImportance.run();
}, null, null, true, false, IMPORTANCE_LOW, false
@@ -918,4 +953,21 @@ public class NotificationInfoTest extends SysuiTestCase {
assertFalse(mNotificationInfo.willBeRemoved());
}
+
+ private Set<NotificationChannel> createMultipleChannelSet(int howMany) {
+ Set<NotificationChannel> multiChannelSet = new HashSet<>();
+ for (int i = 0; i < howMany; i++) {
+ if (i == 0) {
+ multiChannelSet.add(mNotificationChannel);
+ continue;
+ }
+
+ NotificationChannel channel = new NotificationChannel(
+ TEST_CHANNEL, TEST_CHANNEL_NAME + i, IMPORTANCE_LOW);
+
+ multiChannelSet.add(channel);
+ }
+
+ return multiChannelSet;
+ }
}
diff --git a/packages/SystemUI/tests/src/com/android/systemui/statusbar/policy/BluetoothControllerImplTest.java b/packages/SystemUI/tests/src/com/android/systemui/statusbar/policy/BluetoothControllerImplTest.java
index 7f3c34e5eb1b..913654a62d62 100644
--- a/packages/SystemUI/tests/src/com/android/systemui/statusbar/policy/BluetoothControllerImplTest.java
+++ b/packages/SystemUI/tests/src/com/android/systemui/statusbar/policy/BluetoothControllerImplTest.java
@@ -17,7 +17,10 @@ package com.android.systemui.statusbar.policy;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertFalse;
import static org.junit.Assert.assertTrue;
+import static org.mockito.ArgumentMatchers.anyBoolean;
+import static org.mockito.Mockito.atLeastOnce;
import static org.mockito.Mockito.mock;
+import static org.mockito.Mockito.reset;
import static org.mockito.Mockito.verify;
import static org.mockito.Mockito.when;
@@ -198,4 +201,21 @@ public class BluetoothControllerImplTest extends SysuiTestCase {
assertFalse(mBluetoothControllerImpl.isBluetoothConnecting());
assertFalse(mBluetoothControllerImpl.isBluetoothConnected());
}
+
+ @Test
+ public void testOnACLConnectionStateChange_updatesBluetoothStateOnConnection() {
+ BluetoothController.Callback callback = mock(BluetoothController.Callback.class);
+ mBluetoothControllerImpl.addCallback(callback);
+
+ assertFalse(mBluetoothControllerImpl.isBluetoothConnected());
+ CachedBluetoothDevice device = mock(CachedBluetoothDevice.class);
+ mDevices.add(device);
+ when(device.isConnected()).thenReturn(true);
+ when(device.getMaxConnectionState()).thenReturn(BluetoothProfile.STATE_CONNECTED);
+ reset(callback);
+ mBluetoothControllerImpl.onAclConnectionStateChanged(device,
+ BluetoothProfile.STATE_CONNECTED);
+ assertTrue(mBluetoothControllerImpl.isBluetoothConnected());
+ verify(callback, atLeastOnce()).onBluetoothStateChange(anyBoolean());
+ }
}
diff --git a/proto/src/metrics_constants/metrics_constants.proto b/proto/src/metrics_constants/metrics_constants.proto
index e30e166a46b5..5fd14a37f23c 100644
--- a/proto/src/metrics_constants/metrics_constants.proto
+++ b/proto/src/metrics_constants/metrics_constants.proto
@@ -7284,6 +7284,15 @@ message MetricsEvent {
// type of response could not be determined
AUTOFILL_AUGMENTED_RESPONSE = 1724;
+ // ACTION: Settings > Initialize Search bar > Verify Slice > Invalid data
+ ACTION_VERIFY_SLICE_ERROR_INVALID_DATA = 1725;
+
+ // ACTION: Settings > Initialize Search bar > Verify Slice > Parsing error
+ ACTION_VERIFY_SLICE_PARSING_ERROR = 1726;
+
+ // ACTION: Settings > Initialize Search bar > Verify Slice > Other exception
+ ACTION_VERIFY_SLICE_OTHER_EXCEPTION = 1727;
+
// ---- Skipping ahead to avoid conflicts between master and release branches.
// OPEN: Settings > System > Gestures > Global Actions Panel
// CATEGORY: SETTINGS
diff --git a/services/autofill/java/com/android/server/autofill/AutofillManagerServiceImpl.java b/services/autofill/java/com/android/server/autofill/AutofillManagerServiceImpl.java
index e1a7974bccb2..1bd5201f5b26 100644
--- a/services/autofill/java/com/android/server/autofill/AutofillManagerServiceImpl.java
+++ b/services/autofill/java/com/android/server/autofill/AutofillManagerServiceImpl.java
@@ -20,8 +20,8 @@ import static android.service.autofill.FillRequest.FLAG_MANUAL_REQUEST;
import static android.view.autofill.AutofillManager.ACTION_START_SESSION;
import static android.view.autofill.AutofillManager.FLAG_ADD_CLIENT_ENABLED;
import static android.view.autofill.AutofillManager.FLAG_ADD_CLIENT_ENABLED_FOR_AUGMENTED_AUTOFILL_ONLY;
-import static android.view.autofill.AutofillManager.FLAG_SESSION_FOR_AUGMENTED_AUTOFILL_ONLY;
import static android.view.autofill.AutofillManager.NO_SESSION;
+import static android.view.autofill.AutofillManager.RECEIVER_FLAG_SESSION_FOR_AUGMENTED_AUTOFILL_ONLY;
import static com.android.server.autofill.Helper.sDebug;
import static com.android.server.autofill.Helper.sVerbose;
@@ -283,7 +283,7 @@ final class AutofillManagerServiceImpl
*
* @return {@code long} whose right-most 32 bits represent the session id (which is always
* non-negative), and the left-most contains extra flags (currently either {@code 0} or
- * {@link AutofillManager#FLAG_SESSION_FOR_AUGMENTED_AUTOFILL_ONLY}).
+ * {@link AutofillManager#RECEIVER_FLAG_SESSION_FOR_AUGMENTED_AUTOFILL_ONLY}).
*/
@GuardedBy("mLock")
long startSessionLocked(@NonNull IBinder activityToken, int taskId, int uid,
@@ -357,7 +357,8 @@ final class AutofillManagerServiceImpl
if (forAugmentedAutofillOnly) {
// Must embed the flag in the response, at the high-end side of the long.
// (session is always positive, so we don't have to worry about the signal bit)
- final long extraFlags = ((long) FLAG_SESSION_FOR_AUGMENTED_AUTOFILL_ONLY) << 32;
+ final long extraFlags =
+ ((long) RECEIVER_FLAG_SESSION_FOR_AUGMENTED_AUTOFILL_ONLY) << 32;
final long result = extraFlags | newSession.id;
return result;
} else {
diff --git a/services/autofill/java/com/android/server/autofill/Session.java b/services/autofill/java/com/android/server/autofill/Session.java
index 99e0714fa2a2..66b5437f0a7d 100644
--- a/services/autofill/java/com/android/server/autofill/Session.java
+++ b/services/autofill/java/com/android/server/autofill/Session.java
@@ -2407,7 +2407,8 @@ final class Session implements RemoteFillService.FillServiceCallbacks, ViewState
return;
}
- if (mAugmentedAutofillableIds != null && mAugmentedAutofillableIds.contains(id)) {
+ if ((flags & FLAG_MANUAL_REQUEST) == 0 && mAugmentedAutofillableIds != null
+ && mAugmentedAutofillableIds.contains(id)) {
// View was already reported when server could not handle a response, but it
// triggered augmented autofill
@@ -2538,7 +2539,7 @@ final class Session implements RemoteFillService.FillServiceCallbacks, ViewState
try {
if (mHasCallback) {
mClient.notifyNoFillUi(id, mCurrentViewId, sessionFinishedState);
- } else if (sessionFinishedState != 0) {
+ } else if (sessionFinishedState != AutofillManager.STATE_UNKNOWN) {
mClient.setSessionFinished(sessionFinishedState, autofillableIds);
}
} catch (RemoteException e) {
@@ -2693,6 +2694,11 @@ final class Session implements RemoteFillService.FillServiceCallbacks, ViewState
+ "it can be augmented. AutofillableIds: " + autofillableIds);
}
mAugmentedAutofillableIds = autofillableIds;
+ try {
+ mClient.setState(AutofillManager.SET_STATE_FLAG_FOR_AUTOFILL_ONLY);
+ } catch (RemoteException e) {
+ Slog.e(TAG, "Error setting client to autofill-only", e);
+ }
}
}
diff --git a/services/autofill/java/com/android/server/autofill/ui/FillUi.java b/services/autofill/java/com/android/server/autofill/ui/FillUi.java
index 7a65a536335f..dbd4d8c168ba 100644
--- a/services/autofill/java/com/android/server/autofill/ui/FillUi.java
+++ b/services/autofill/java/com/android/server/autofill/ui/FillUi.java
@@ -151,6 +151,7 @@ final class FillUi {
} else {
decor = (ViewGroup) inflater.inflate(R.layout.autofill_dataset_picker, null);
}
+ decor.setClipToOutline(true);
final TextView titleView = decor.findViewById(R.id.autofill_dataset_title);
if (titleView != null) {
titleView.setText(mContext.getString(R.string.autofill_window_title, serviceLabel));
diff --git a/services/core/java/com/android/server/IpSecService.java b/services/core/java/com/android/server/IpSecService.java
index 2055b64483d9..fe22dcda9683 100644
--- a/services/core/java/com/android/server/IpSecService.java
+++ b/services/core/java/com/android/server/IpSecService.java
@@ -30,6 +30,7 @@ import static com.android.internal.util.Preconditions.checkNotNull;
import android.annotation.NonNull;
import android.app.AppOpsManager;
import android.content.Context;
+import android.content.pm.PackageManager;
import android.net.IIpSecService;
import android.net.INetd;
import android.net.IpSecAlgorithm;
@@ -1276,7 +1277,7 @@ public class IpSecService extends IIpSecService.Stub {
public synchronized IpSecTunnelInterfaceResponse createTunnelInterface(
String localAddr, String remoteAddr, Network underlyingNetwork, IBinder binder,
String callingPackage) {
- enforceTunnelPermissions(callingPackage);
+ enforceTunnelFeatureAndPermissions(callingPackage);
checkNotNull(binder, "Null Binder passed to createTunnelInterface");
checkNotNull(underlyingNetwork, "No underlying network was specified");
checkInetAddress(localAddr);
@@ -1362,7 +1363,7 @@ public class IpSecService extends IIpSecService.Stub {
@Override
public synchronized void addAddressToTunnelInterface(
int tunnelResourceId, LinkAddress localAddr, String callingPackage) {
- enforceTunnelPermissions(callingPackage);
+ enforceTunnelFeatureAndPermissions(callingPackage);
UserRecord userRecord = mUserResourceTracker.getUserRecord(Binder.getCallingUid());
// Get tunnelInterface record; if no such interface is found, will throw
@@ -1391,7 +1392,7 @@ public class IpSecService extends IIpSecService.Stub {
@Override
public synchronized void removeAddressFromTunnelInterface(
int tunnelResourceId, LinkAddress localAddr, String callingPackage) {
- enforceTunnelPermissions(callingPackage);
+ enforceTunnelFeatureAndPermissions(callingPackage);
UserRecord userRecord = mUserResourceTracker.getUserRecord(Binder.getCallingUid());
// Get tunnelInterface record; if no such interface is found, will throw
@@ -1420,7 +1421,7 @@ public class IpSecService extends IIpSecService.Stub {
@Override
public synchronized void deleteTunnelInterface(
int resourceId, String callingPackage) throws RemoteException {
- enforceTunnelPermissions(callingPackage);
+ enforceTunnelFeatureAndPermissions(callingPackage);
UserRecord userRecord = mUserResourceTracker.getUserRecord(Binder.getCallingUid());
releaseResource(userRecord.mTunnelInterfaceRecords, resourceId);
}
@@ -1549,7 +1550,12 @@ public class IpSecService extends IIpSecService.Stub {
private static final String TUNNEL_OP = AppOpsManager.OPSTR_MANAGE_IPSEC_TUNNELS;
- private void enforceTunnelPermissions(String callingPackage) {
+ private void enforceTunnelFeatureAndPermissions(String callingPackage) {
+ if (!mContext.getPackageManager().hasSystemFeature(PackageManager.FEATURE_IPSEC_TUNNELS)) {
+ throw new UnsupportedOperationException(
+ "IPsec Tunnel Mode requires PackageManager.FEATURE_IPSEC_TUNNELS");
+ }
+
checkNotNull(callingPackage, "Null calling package cannot create IpSec tunnels");
switch (getAppOpsManager().noteOp(TUNNEL_OP, Binder.getCallingUid(), callingPackage)) {
case AppOpsManager.MODE_DEFAULT:
@@ -1621,7 +1627,7 @@ public class IpSecService extends IIpSecService.Stub {
IpSecConfig c, IBinder binder, String callingPackage) throws RemoteException {
checkNotNull(c);
if (c.getMode() == IpSecTransform.MODE_TUNNEL) {
- enforceTunnelPermissions(callingPackage);
+ enforceTunnelFeatureAndPermissions(callingPackage);
}
checkIpSecConfig(c);
checkNotNull(binder, "Null Binder passed to createTransform");
@@ -1729,7 +1735,7 @@ public class IpSecService extends IIpSecService.Stub {
public synchronized void applyTunnelModeTransform(
int tunnelResourceId, int direction,
int transformResourceId, String callingPackage) throws RemoteException {
- enforceTunnelPermissions(callingPackage);
+ enforceTunnelFeatureAndPermissions(callingPackage);
checkDirection(direction);
int callingUid = Binder.getCallingUid();
diff --git a/services/core/java/com/android/server/StorageManagerService.java b/services/core/java/com/android/server/StorageManagerService.java
index baec3ccd953f..c6461491b8cd 100644
--- a/services/core/java/com/android/server/StorageManagerService.java
+++ b/services/core/java/com/android/server/StorageManagerService.java
@@ -49,7 +49,6 @@ import static org.xmlpull.v1.XmlPullParser.START_TAG;
import android.Manifest;
import android.annotation.Nullable;
import android.app.ActivityManager;
-import android.app.ActivityManagerInternal;
import android.app.AppOpsManager;
import android.app.IActivityManager;
import android.app.KeyguardManager;
@@ -60,7 +59,6 @@ import android.content.ContentResolver;
import android.content.Context;
import android.content.Intent;
import android.content.IntentFilter;
-import android.content.pm.ApplicationInfo;
import android.content.pm.IPackageManager;
import android.content.pm.IPackageMoveObserver;
import android.content.pm.PackageManager;
@@ -98,7 +96,6 @@ import android.os.SystemClock;
import android.os.SystemProperties;
import android.os.UserHandle;
import android.os.UserManager;
-import android.os.UserManagerInternal;
import android.os.storage.DiskInfo;
import android.os.storage.IObbActionListener;
import android.os.storage.IStorageEventListener;
@@ -117,13 +114,11 @@ import android.sysprop.VoldProperties;
import android.text.TextUtils;
import android.text.format.DateUtils;
import android.util.ArrayMap;
-import android.util.ArraySet;
import android.util.AtomicFile;
import android.util.DataUnit;
import android.util.Log;
import android.util.Pair;
import android.util.Slog;
-import android.util.SparseArray;
import android.util.TimeUtils;
import android.util.Xml;
@@ -179,8 +174,6 @@ import java.util.concurrent.CopyOnWriteArrayList;
import java.util.concurrent.CountDownLatch;
import java.util.concurrent.TimeUnit;
import java.util.concurrent.TimeoutException;
-import java.util.regex.Matcher;
-import java.util.regex.Pattern;
import javax.crypto.SecretKey;
import javax.crypto.SecretKeyFactory;
@@ -350,9 +343,6 @@ class StorageManagerService extends IStorageManager.Stub
@GuardedBy("mLock")
private String mMoveTargetUuid;
- @GuardedBy("mPackagesLock")
- private final SparseArray<ArraySet<String>> mPackages = new SparseArray<>();
-
private volatile int mCurrentUserId = UserHandle.USER_SYSTEM;
/** Holding lock for AppFuse business */
@@ -469,14 +459,11 @@ class StorageManagerService extends IStorageManager.Stub
private volatile IVold mVold;
private volatile IStoraged mStoraged;
- private volatile boolean mSystemReady = false;
private volatile boolean mBootCompleted = false;
private volatile boolean mDaemonConnected = false;
private volatile boolean mSecureKeyguardShowing = true;
private PackageManagerInternal mPmInternal;
- private UserManagerInternal mUmInternal;
- private ActivityManagerInternal mAmInternal;
private IPackageManager mIPackageManager;
private IAppOpsService mIAppOpsService;
@@ -965,7 +952,7 @@ class StorageManagerService extends IStorageManager.Stub
mVold.onUserAdded(user.id, user.serialNumber);
}
for (int userId : systemUnlockedUsers) {
- sendUserStartedCallback(userId);
+ mVold.onUserStarted(userId);
mStoraged.onUserStarted(userId);
}
mVold.onSecureKeyguardStateChanged(mSecureKeyguardShowing);
@@ -983,7 +970,7 @@ class StorageManagerService extends IStorageManager.Stub
// staging area is ready so it's ready for zygote-forked apps to
// bind mount against.
try {
- sendUserStartedCallback(userId);
+ mVold.onUserStarted(userId);
mStoraged.onUserStarted(userId);
} catch (Exception e) {
Slog.wtf(TAG, e);
@@ -1016,53 +1003,12 @@ class StorageManagerService extends IStorageManager.Stub
Slog.wtf(TAG, e);
}
- synchronized (mPackagesLock) {
- mPackages.delete(userId);
- }
-
synchronized (mLock) {
mSystemUnlockedUsers = ArrayUtils.removeInt(mSystemUnlockedUsers, userId);
}
}
- private void sendUserStartedCallback(int userId) throws Exception {
- if (!ENABLE_ISOLATED_STORAGE) {
- mVold.onUserStarted(userId, EmptyArray.STRING, EmptyArray.INT, EmptyArray.STRING);
- }
-
- final String[] packages;
- final int[] appIds;
- final String[] sandboxIds;
- final SparseArray<String> sharedUserIds = mPmInternal.getAppsWithSharedUserIds();
- final List<ApplicationInfo> appInfos =
- mContext.getPackageManager().getInstalledApplicationsAsUser(
- PackageManager.MATCH_UNINSTALLED_PACKAGES, userId);
- synchronized (mPackagesLock) {
- final ArraySet<String> userPackages = new ArraySet<>();
- final ArrayMap<String, Integer> packageToAppId = new ArrayMap<>();
- for (int i = appInfos.size() - 1; i >= 0; --i) {
- final ApplicationInfo appInfo = appInfos.get(i);
- if (appInfo.isInstantApp()) {
- continue;
- }
- userPackages.add(appInfo.packageName);
- packageToAppId.put(appInfo.packageName, UserHandle.getAppId(appInfo.uid));
- }
- mPackages.put(userId, userPackages);
-
- packages = new String[userPackages.size()];
- appIds = new int[userPackages.size()];
- sandboxIds = new String[userPackages.size()];
- for (int i = userPackages.size() - 1; i >= 0; --i) {
- packages[i] = userPackages.valueAt(i);
- appIds[i] = packageToAppId.get(packages[i]);
- sandboxIds[i] = getSandboxId(packages[i], sharedUserIds.get(appIds[i]));
- }
- }
- mVold.onUserStarted(userId, packages, appIds, sandboxIds);
- }
-
- private boolean supportsBlockCheckpoint() throws RemoteException {
+ private boolean supportsBlockCheckpoint() throws RemoteException {
enforcePermission(android.Manifest.permission.MOUNT_FORMAT_FILESYSTEMS);
return mVold.supportsBlockCheckpoint();
}
@@ -1596,11 +1542,6 @@ class StorageManagerService extends IStorageManager.Stub
connect();
}
- private static String getSandboxId(String packageName, String sharedUserId) {
- return sharedUserId == null
- ? packageName : StorageManager.SHARED_SANDBOX_PREFIX + sharedUserId;
- }
-
private void connect() {
IBinder binder = ServiceManager.getService("storaged");
if (binder != null) {
@@ -1663,8 +1604,6 @@ class StorageManagerService extends IStorageManager.Stub
private void servicesReady() {
mPmInternal = LocalServices.getService(PackageManagerInternal.class);
- mUmInternal = LocalServices.getService(UserManagerInternal.class);
- mAmInternal = LocalServices.getService(ActivityManagerInternal.class);
mIPackageManager = IPackageManager.Stub.asInterface(
ServiceManager.getService("package"));
@@ -1694,7 +1633,6 @@ class StorageManagerService extends IStorageManager.Stub
LocalServices.getService(ActivityTaskManagerInternal.class)
.registerScreenObserver(this);
- mSystemReady = true;
mHandler.obtainMessage(H_SYSTEM_READY).sendToTarget();
}
@@ -2994,7 +2932,6 @@ class StorageManagerService extends IStorageManager.Stub
@Override
public void mkdirs(String callingPkg, String appPath) {
- final int callingPid = Binder.getCallingPid();
final int callingUid = Binder.getCallingUid();
final int userId = UserHandle.getUserId(callingUid);
final UserEnvironment userEnv = new UserEnvironment(userId);
@@ -3033,13 +2970,11 @@ class StorageManagerService extends IStorageManager.Stub
appPath = appPath + "/";
}
- final String systemPath = translateAppToSystem(appPath, callingPid, callingUid);
-
try {
- mVold.mkdirs(systemPath);
+ mVold.mkdirs(appPath);
return;
} catch (Exception e) {
- throw new IllegalStateException("Failed to prepare " + systemPath + ": " + e);
+ throw new IllegalStateException("Failed to prepare " + appPath + ": " + e);
}
}
@@ -3307,75 +3242,6 @@ class StorageManagerService extends IStorageManager.Stub
}
};
- private static final Pattern PATTERN_TRANSLATE = Pattern.compile(
- "(?i)^(/storage/[^/]+/(?:[0-9]+/)?)(.*)");
-
- @Override
- public String translateAppToSystem(String path, int pid, int uid) {
- return translateInternal(path, pid, uid, true);
- }
-
- @Override
- public String translateSystemToApp(String path, int pid, int uid) {
- return translateInternal(path, pid, uid, false);
- }
-
- private String translateInternal(String path, int pid, int uid, boolean toSystem) {
- if (true) return path;
-
- if (path.contains("/../")) {
- throw new SecurityException("Shady looking path " + path);
- }
-
- final int mountMode = mAmInternal.getStorageMountMode(pid, uid);
- if (mountMode == Zygote.MOUNT_EXTERNAL_FULL
- || mountMode == Zygote.MOUNT_EXTERNAL_LEGACY) {
- return path;
- }
-
- final Matcher m = PATTERN_TRANSLATE.matcher(path);
- if (m.matches()) {
- final String device = m.group(1);
- final String devicePath = m.group(2);
-
- if (mountMode == Zygote.MOUNT_EXTERNAL_INSTALLER
- && devicePath.startsWith("Android/obb/")) {
- return path;
- }
-
- // Does path belong to any packages belonging to this UID? If so,
- // they get to go straight through to legacy paths.
- final String[] pkgs = mContext.getPackageManager().getPackagesForUid(uid);
- for (String pkg : pkgs) {
- if (devicePath.startsWith("Android/data/" + pkg + "/") ||
- devicePath.startsWith("Android/media/" + pkg + "/") ||
- devicePath.startsWith("Android/obb/" + pkg + "/")) {
- return path;
- }
- }
-
- final String sharedUserId = mPmInternal.getSharedUserIdForPackage(pkgs[0]);
- final String sandboxId = getSandboxId(pkgs[0], sharedUserId);
-
- if (toSystem) {
- // Everything else goes into sandbox.
- return device + "Android/sandbox/" + sandboxId + "/" + devicePath;
- } else {
- // Does path belong to this sandbox? If so, leave sandbox.
- final String sandboxPrefix = "Android/sandbox/" + sandboxId + "/";
- if (devicePath.startsWith(sandboxPrefix)) {
- return device + devicePath.substring(sandboxPrefix.length());
- }
-
- // Path isn't valid inside sandbox!
- throw new SecurityException(
- "Path " + path + " isn't valid inside sandbox " + sandboxId);
- }
- }
-
- return path;
- }
-
private void addObbStateLocked(ObbState obbState) throws RemoteException {
final IBinder binder = obbState.getBinder();
List<ObbState> obbStates = mObbMounts.get(binder);
@@ -4048,55 +3914,5 @@ class StorageManagerService extends IStorageManager.Stub
}
return true;
}
-
- @Override
- public void prepareSandboxForApp(String packageName, int appId, String sharedUserId,
- int userId) {
- final String sandboxId;
- synchronized (mPackagesLock) {
- final ArraySet<String> userPackages = mPackages.get(userId);
- // If userPackages is empty, it means the user is not started yet, so no need to
- // do anything now.
- if (userPackages == null || userPackages.contains(packageName)) {
- return;
- }
- userPackages.add(packageName);
- sandboxId = StorageManagerService.this.getSandboxId(packageName, sharedUserId);
- }
-
- try {
- mVold.prepareSandboxForApp(packageName, appId, sandboxId, userId);
- } catch (Exception e) {
- Slog.wtf(TAG, e);
- }
- }
-
- @Override
- public void destroySandboxForApp(String packageName, String sharedUserId, int userId) {
- if (!ENABLE_ISOLATED_STORAGE) {
- return;
- }
- final String sandboxId = StorageManagerService.this.getSandboxId(
- packageName, sharedUserId);
- synchronized (mPackagesLock) {
- final ArraySet<String> userPackages = mPackages.get(userId);
- // If the userPackages is null, it means the user is not started but we still
- // need to delete the sandbox data though.
- if (userPackages != null) {
- userPackages.remove(packageName);
- }
- }
- try {
- mVold.destroySandboxForApp(packageName, sandboxId, userId);
- } catch (Exception e) {
- Slog.wtf(TAG, e);
- }
- }
-
- @Override
- public String getSandboxId(String packageName) {
- return StorageManagerService.this.getSandboxId(packageName,
- mPmInternal.getSharedUserIdForPackage(packageName));
- }
}
}
diff --git a/services/core/java/com/android/server/am/ActiveServices.java b/services/core/java/com/android/server/am/ActiveServices.java
index df92106ae0d0..90266f12a5dd 100644
--- a/services/core/java/com/android/server/am/ActiveServices.java
+++ b/services/core/java/com/android/server/am/ActiveServices.java
@@ -634,28 +634,13 @@ public final class ActiveServices {
}
if (allowBackgroundActivityStarts) {
- r.setHasStartedWhitelistingBgActivityStarts(true);
- scheduleCleanUpHasStartedWhitelistingBgActivityStartsLocked(r);
+ r.whitelistBgActivityStartsOnServiceStart();
}
ComponentName cmp = startServiceInnerLocked(smap, service, r, callerFg, addToStarting);
return cmp;
}
- private void scheduleCleanUpHasStartedWhitelistingBgActivityStartsLocked(ServiceRecord r) {
- // if there's a request pending from the past, drop it before scheduling a new one
- if (r.startedWhitelistingBgActivityStartsCleanUp == null) {
- r.startedWhitelistingBgActivityStartsCleanUp = () -> {
- synchronized(mAm) {
- r.setHasStartedWhitelistingBgActivityStarts(false);
- }
- };
- }
- mAm.mHandler.removeCallbacks(r.startedWhitelistingBgActivityStartsCleanUp);
- mAm.mHandler.postDelayed(r.startedWhitelistingBgActivityStartsCleanUp,
- mAm.mConstants.SERVICE_BG_ACTIVITY_START_TIMEOUT);
- }
-
private boolean requestStartTargetPermissionsReviewIfNeededLocked(ServiceRecord r,
String callingPackage, int callingUid, Intent service, boolean callerFg,
final int userId) {
diff --git a/services/core/java/com/android/server/am/ActivityManagerService.java b/services/core/java/com/android/server/am/ActivityManagerService.java
index 4d0d3d2dc578..d8f5937d3cdd 100644
--- a/services/core/java/com/android/server/am/ActivityManagerService.java
+++ b/services/core/java/com/android/server/am/ActivityManagerService.java
@@ -274,6 +274,7 @@ import android.os.storage.IStorageManager;
import android.os.storage.StorageManager;
import android.provider.DeviceConfig;
import android.provider.Settings;
+import android.server.ServerProtoEnums;
import android.sysprop.VoldProperties;
import android.text.TextUtils;
import android.text.format.DateUtils;
@@ -9056,7 +9057,9 @@ public class ActivityManagerService extends IActivityManager.Stub
? StatsLog.APP_CRASH_OCCURRED__FOREGROUND_STATE__FOREGROUND
: StatsLog.APP_CRASH_OCCURRED__FOREGROUND_STATE__BACKGROUND)
: StatsLog.APP_CRASH_OCCURRED__FOREGROUND_STATE__UNKNOWN,
- (r != null) ? r.getProcessClassEnum() : 0
+ processName.equals("system_server") ? ServerProtoEnums.SYSTEM_SERVER
+ : (r != null) ? r.getProcessClassEnum()
+ : ServerProtoEnums.ERROR_SOURCE_UNKNOWN
);
final int relaunchReason = r == null ? RELAUNCH_REASON_NONE
@@ -17369,7 +17372,7 @@ public class ActivityManagerService extends IActivityManager.Stub
@Override
public int stopUser(final int userId, boolean force, final IStopUserCallback callback) {
- return mUserController.stopUser(userId, force, callback);
+ return mUserController.stopUser(userId, force, callback, null /* keyEvictedCallback */);
}
@Override
diff --git a/services/core/java/com/android/server/am/ProcessList.java b/services/core/java/com/android/server/am/ProcessList.java
index 32516b1c4618..696697eddf25 100644
--- a/services/core/java/com/android/server/am/ProcessList.java
+++ b/services/core/java/com/android/server/am/ProcessList.java
@@ -1810,11 +1810,6 @@ public final class ProcessList {
String seInfo, String requiredAbi, String instructionSet, String invokeWith,
long startTime) {
try {
- final String[] packageNames = mService.mContext.getPackageManager()
- .getPackagesForUid(uid);
- final StorageManagerInternal storageManagerInternal =
- LocalServices.getService(StorageManagerInternal.class);
- final String sandboxId = storageManagerInternal.getSandboxId(app.info.packageName);
final boolean useSystemGraphicsDriver = shouldUseSystemGraphicsDriver(mService.mContext,
mService.mCoreSettingsObserver.getCoreSettingsLocked(), app.info);
Trace.traceBegin(Trace.TRACE_TAG_ACTIVITY_MANAGER, "Start proc: " +
@@ -1826,7 +1821,6 @@ public final class ProcessList {
app.processName, uid, uid, gids, runtimeFlags, mountExternal,
app.info.targetSdkVersion, seInfo, requiredAbi, instructionSet,
app.info.dataDir, null, app.info.packageName,
- packageNames, sandboxId,
useSystemGraphicsDriver,
new String[] {PROC_START_SEQ_IDENT + app.startSeq});
} else if (hostingRecord.usesAppZygote()) {
@@ -1836,15 +1830,13 @@ public final class ProcessList {
app.processName, uid, uid, gids, runtimeFlags, mountExternal,
app.info.targetSdkVersion, seInfo, requiredAbi, instructionSet,
app.info.dataDir, null, app.info.packageName,
- packageNames, sandboxId, /*useUsapPool=*/ false,
- useSystemGraphicsDriver,
+ /*useUsapPool=*/ false, useSystemGraphicsDriver,
new String[] {PROC_START_SEQ_IDENT + app.startSeq});
} else {
startResult = Process.start(entryPoint,
app.processName, uid, uid, gids, runtimeFlags, mountExternal,
app.info.targetSdkVersion, seInfo, requiredAbi, instructionSet,
app.info.dataDir, invokeWith, app.info.packageName,
- packageNames, sandboxId,
useSystemGraphicsDriver,
new String[] {PROC_START_SEQ_IDENT + app.startSeq});
}
diff --git a/services/core/java/com/android/server/am/ServiceRecord.java b/services/core/java/com/android/server/am/ServiceRecord.java
index 0426ec1d9771..2f1b22ec9a67 100644
--- a/services/core/java/com/android/server/am/ServiceRecord.java
+++ b/services/core/java/com/android/server/am/ServiceRecord.java
@@ -135,7 +135,8 @@ final class ServiceRecord extends Binder implements ComponentName.WithComponentN
// allowBackgroundActivityStarts=true to startServiceLocked()?
private boolean mHasStartedWhitelistingBgActivityStarts;
// used to clean up the state of hasStartedWhitelistingBgActivityStarts after a timeout
- Runnable startedWhitelistingBgActivityStartsCleanUp;
+ private Runnable mStartedWhitelistingBgActivityStartsCleanUp;
+ private ProcessRecord mAppForStartedWhitelistingBgActivityStarts;
String stringName; // caching of toString
@@ -541,14 +542,35 @@ final class ServiceRecord extends Binder implements ComponentName.WithComponentN
public void setProcess(ProcessRecord _proc) {
if (_proc != null) {
+ // We're starting a new process for this service, but a previous one is whitelisted.
+ // Remove that whitelisting now (unless the new process is the same as the previous one,
+ // which is a common case).
+ if (mAppForStartedWhitelistingBgActivityStarts != null) {
+ if (mAppForStartedWhitelistingBgActivityStarts != _proc) {
+ mAppForStartedWhitelistingBgActivityStarts
+ .removeAllowBackgroundActivityStartsToken(this);
+ ams.mHandler.removeCallbacks(mStartedWhitelistingBgActivityStartsCleanUp);
+ }
+ mAppForStartedWhitelistingBgActivityStarts = null;
+ }
+ if (mHasStartedWhitelistingBgActivityStarts) {
+ // Make sure the cleanup callback knows about the new process.
+ mAppForStartedWhitelistingBgActivityStarts = _proc;
+ }
if (mHasStartedWhitelistingBgActivityStarts
|| mHasBindingWhitelistingBgActivityStarts) {
_proc.addAllowBackgroundActivityStartsToken(this);
} else {
_proc.removeAllowBackgroundActivityStartsToken(this);
}
- } else if (app != null) {
- app.removeAllowBackgroundActivityStartsToken(this);
+ }
+ if (app != null && app != _proc) {
+ // If the old app is whitelisted because of a service start, leave it whitelisted until
+ // the cleanup callback runs. Otherwise we can remove it from the whitelist immediately
+ // (it can't be bound now).
+ if (!mHasStartedWhitelistingBgActivityStarts) {
+ app.removeAllowBackgroundActivityStartsToken(this);
+ }
app.updateBoundClientUids();
}
app = _proc;
@@ -616,10 +638,7 @@ final class ServiceRecord extends Binder implements ComponentName.WithComponentN
break;
}
}
- if (mHasBindingWhitelistingBgActivityStarts != hasWhitelistingBinding) {
- mHasBindingWhitelistingBgActivityStarts = hasWhitelistingBinding;
- updateParentProcessBgActivityStartsWhitelistingToken();
- }
+ setHasBindingWhitelistingBgActivityStarts(hasWhitelistingBinding);
}
void setHasBindingWhitelistingBgActivityStarts(boolean newValue) {
@@ -629,7 +648,42 @@ final class ServiceRecord extends Binder implements ComponentName.WithComponentN
}
}
- void setHasStartedWhitelistingBgActivityStarts(boolean newValue) {
+ /**
+ * Called when the service is started with allowBackgroundActivityStarts set. We whitelist
+ * it for background activity starts, setting up a callback to remove the whitelisting after a
+ * timeout. Note that the whitelisting persists for the process even if the service is
+ * subsequently stopped.
+ */
+ void whitelistBgActivityStartsOnServiceStart() {
+ setHasStartedWhitelistingBgActivityStarts(true);
+
+ // This callback is stateless, so we create it once when we first need it.
+ if (mStartedWhitelistingBgActivityStartsCleanUp == null) {
+ mStartedWhitelistingBgActivityStartsCleanUp = () -> {
+ synchronized (ams) {
+ if (app == mAppForStartedWhitelistingBgActivityStarts) {
+ // The process we whitelisted is still running the service. We remove
+ // the started whitelisting, but it may still be whitelisted via bound
+ // connections.
+ setHasStartedWhitelistingBgActivityStarts(false);
+ } else if (mAppForStartedWhitelistingBgActivityStarts != null) {
+ // The process we whitelisted is not running the service. It therefore
+ // can't be bound so we can unconditionally remove the whitelist.
+ mAppForStartedWhitelistingBgActivityStarts
+ .removeAllowBackgroundActivityStartsToken(ServiceRecord.this);
+ }
+ mAppForStartedWhitelistingBgActivityStarts = null;
+ }
+ };
+ }
+
+ // if there's a request pending from the past, drop it before scheduling a new one
+ ams.mHandler.removeCallbacks(mStartedWhitelistingBgActivityStartsCleanUp);
+ ams.mHandler.postDelayed(mStartedWhitelistingBgActivityStartsCleanUp,
+ ams.mConstants.SERVICE_BG_ACTIVITY_START_TIMEOUT);
+ }
+
+ private void setHasStartedWhitelistingBgActivityStarts(boolean newValue) {
if (mHasStartedWhitelistingBgActivityStarts != newValue) {
mHasStartedWhitelistingBgActivityStarts = newValue;
updateParentProcessBgActivityStartsWhitelistingToken();
@@ -650,7 +704,7 @@ final class ServiceRecord extends Binder implements ComponentName.WithComponentN
return;
}
if (mHasStartedWhitelistingBgActivityStarts || mHasBindingWhitelistingBgActivityStarts) {
- // if the token is already there it's safe to "re-add it" - we're deadling with
+ // if the token is already there it's safe to "re-add it" - we're dealing with
// a set of Binder objects
app.addAllowBackgroundActivityStartsToken(this);
} else {
diff --git a/services/core/java/com/android/server/am/UserController.java b/services/core/java/com/android/server/am/UserController.java
index 01a3a6fb25d1..2399d0525cc4 100644
--- a/services/core/java/com/android/server/am/UserController.java
+++ b/services/core/java/com/android/server/am/UserController.java
@@ -98,6 +98,7 @@ import com.android.internal.widget.LockPatternUtils;
import com.android.server.FgThread;
import com.android.server.LocalServices;
import com.android.server.SystemServiceManager;
+import com.android.server.am.UserState.KeyEvictedCallback;
import com.android.server.pm.UserManagerService;
import com.android.server.wm.ActivityTaskManagerInternal;
import com.android.server.wm.WindowManagerService;
@@ -319,7 +320,7 @@ class UserController implements Handler.Callback {
// Owner/System user and current user can't be stopped
continue;
}
- if (stopUsersLU(userId, false, null) == USER_OP_SUCCESS) {
+ if (stopUsersLU(userId, false, null, null) == USER_OP_SUCCESS) {
iterator.remove();
}
}
@@ -586,19 +587,18 @@ class UserController implements Handler.Callback {
}
int restartUser(final int userId, final boolean foreground) {
- return stopUser(userId, /* force */ true, new IStopUserCallback.Stub() {
+ return stopUser(userId, /* force */ true, null, new KeyEvictedCallback() {
@Override
- public void userStopped(final int userId) {
+ public void keyEvicted(@UserIdInt int userId) {
// Post to the same handler that this callback is called from to ensure the user
// cleanup is complete before restarting.
- mHandler.post(() -> startUser(userId, foreground));
+ mHandler.post(() -> UserController.this.startUser(userId, foreground));
}
- @Override
- public void userStopAborted(final int userId) {}
});
}
- int stopUser(final int userId, final boolean force, final IStopUserCallback callback) {
+ int stopUser(final int userId, final boolean force, final IStopUserCallback stopUserCallback,
+ KeyEvictedCallback keyEvictedCallback) {
if (mInjector.checkCallingPermission(INTERACT_ACROSS_USERS_FULL)
!= PackageManager.PERMISSION_GRANTED) {
String msg = "Permission Denial: switchUser() from pid="
@@ -613,7 +613,7 @@ class UserController implements Handler.Callback {
}
enforceShellRestriction(UserManager.DISALLOW_DEBUGGING_FEATURES, userId);
synchronized (mLock) {
- return stopUsersLU(userId, force, callback);
+ return stopUsersLU(userId, force, stopUserCallback, keyEvictedCallback);
}
}
@@ -622,7 +622,8 @@ class UserController implements Handler.Callback {
* {@link #getUsersToStopLU(int)} to determine the list of users that should be stopped.
*/
@GuardedBy("mLock")
- private int stopUsersLU(final int userId, boolean force, final IStopUserCallback callback) {
+ private int stopUsersLU(final int userId, boolean force,
+ final IStopUserCallback stopUserCallback, KeyEvictedCallback keyEvictedCallback) {
if (userId == UserHandle.USER_SYSTEM) {
return USER_OP_ERROR_IS_SYSTEM;
}
@@ -640,7 +641,7 @@ class UserController implements Handler.Callback {
if (force) {
Slog.i(TAG,
"Force stop user " + userId + ". Related users will not be stopped");
- stopSingleUserLU(userId, callback);
+ stopSingleUserLU(userId, stopUserCallback, keyEvictedCallback);
return USER_OP_SUCCESS;
}
return USER_OP_ERROR_RELATED_USERS_CANNOT_STOP;
@@ -648,22 +649,25 @@ class UserController implements Handler.Callback {
}
if (DEBUG_MU) Slog.i(TAG, "stopUsersLocked usersToStop=" + Arrays.toString(usersToStop));
for (int userIdToStop : usersToStop) {
- stopSingleUserLU(userIdToStop, userIdToStop == userId ? callback : null);
+ stopSingleUserLU(userIdToStop,
+ userIdToStop == userId ? stopUserCallback : null,
+ userIdToStop == userId ? keyEvictedCallback : null);
}
return USER_OP_SUCCESS;
}
@GuardedBy("mLock")
- private void stopSingleUserLU(final int userId, final IStopUserCallback callback) {
+ private void stopSingleUserLU(final int userId, final IStopUserCallback stopUserCallback,
+ KeyEvictedCallback keyEvictedCallback) {
if (DEBUG_MU) Slog.i(TAG, "stopSingleUserLocked userId=" + userId);
final UserState uss = mStartedUsers.get(userId);
if (uss == null) {
// User is not started, nothing to do... but we do need to
// callback if requested.
- if (callback != null) {
+ if (stopUserCallback != null) {
mHandler.post(() -> {
try {
- callback.userStopped(userId);
+ stopUserCallback.userStopped(userId);
} catch (RemoteException e) {
}
});
@@ -671,8 +675,11 @@ class UserController implements Handler.Callback {
return;
}
- if (callback != null) {
- uss.mStopCallbacks.add(callback);
+ if (stopUserCallback != null) {
+ uss.mStopCallbacks.add(stopUserCallback);
+ }
+ if (keyEvictedCallback != null) {
+ uss.mKeyEvictedCallbacks.add(keyEvictedCallback);
}
if (uss.state != UserState.STATE_STOPPING
@@ -753,10 +760,12 @@ class UserController implements Handler.Callback {
final int userId = uss.mHandle.getIdentifier();
final boolean stopped;
boolean lockUser = true;
- ArrayList<IStopUserCallback> callbacks;
+ final ArrayList<IStopUserCallback> stopCallbacks;
+ final ArrayList<KeyEvictedCallback> keyEvictedCallbacks;
int userIdToLock = userId;
synchronized (mLock) {
- callbacks = new ArrayList<>(uss.mStopCallbacks);
+ stopCallbacks = new ArrayList<>(uss.mStopCallbacks);
+ keyEvictedCallbacks = new ArrayList<>(uss.mKeyEvictedCallbacks);
if (mStartedUsers.get(userId) != uss || uss.state != UserState.STATE_SHUTDOWN) {
stopped = false;
} else {
@@ -779,11 +788,11 @@ class UserController implements Handler.Callback {
forceStopUser(userId, "finish user");
}
- for (int i = 0; i < callbacks.size(); i++) {
+ for (final IStopUserCallback callback : stopCallbacks) {
try {
- if (stopped) callbacks.get(i).userStopped(userId);
- else callbacks.get(i).userStopAborted(userId);
- } catch (RemoteException e) {
+ if (stopped) callback.userStopped(userId);
+ else callback.userStopAborted(userId);
+ } catch (RemoteException ignored) {
}
}
@@ -814,6 +823,11 @@ class UserController implements Handler.Callback {
} catch (RemoteException re) {
throw re.rethrowAsRuntimeException();
}
+ if (userIdToLockF == userId) {
+ for (final KeyEvictedCallback callback : keyEvictedCallbacks) {
+ callback.keyEvicted(userId);
+ }
+ }
});
}
}
@@ -912,7 +926,7 @@ class UserController implements Handler.Callback {
if (userInfo.isGuest() || userInfo.isEphemeral()) {
// This is a user to be stopped.
synchronized (mLock) {
- stopUsersLU(oldUserId, true, null);
+ stopUsersLU(oldUserId, true, null, null);
}
}
}
@@ -1392,7 +1406,7 @@ class UserController implements Handler.Callback {
synchronized (mLock) {
if (DEBUG_MU) Slog.i(TAG, "stopBackgroundUsersIfEnforced stopping " + oldUserId
+ " and related users");
- stopUsersLU(oldUserId, false, null);
+ stopUsersLU(oldUserId, false, null, null);
}
}
diff --git a/services/core/java/com/android/server/am/UserState.java b/services/core/java/com/android/server/am/UserState.java
index 4f5c59ce0634..f51b3c68559b 100644
--- a/services/core/java/com/android/server/am/UserState.java
+++ b/services/core/java/com/android/server/am/UserState.java
@@ -19,6 +19,7 @@ package com.android.server.am;
import static com.android.server.am.ActivityManagerDebugConfig.TAG_AM;
import static com.android.server.am.ActivityManagerDebugConfig.TAG_WITH_CLASS_NAME;
+import android.annotation.UserIdInt;
import android.app.IStopUserCallback;
import android.os.Trace;
import android.os.UserHandle;
@@ -48,15 +49,21 @@ public final class UserState {
public final static int STATE_SHUTDOWN = 5;
public final UserHandle mHandle;
- public final ArrayList<IStopUserCallback> mStopCallbacks
- = new ArrayList<IStopUserCallback>();
+ public final ArrayList<IStopUserCallback> mStopCallbacks = new ArrayList<>();
public final ProgressReporter mUnlockProgress;
+ public final ArrayList<KeyEvictedCallback> mKeyEvictedCallbacks = new ArrayList<>();
public int state = STATE_BOOTING;
public int lastState = STATE_BOOTING;
public boolean switching;
public boolean tokenProvided;
+ /** Callback for key eviction. */
+ public interface KeyEvictedCallback {
+ /** Invoked when the key is evicted. */
+ void keyEvicted(@UserIdInt int userId);
+ }
+
/**
* The last time that a provider was reported to usage stats as being brought to important
* foreground procstate.
diff --git a/services/core/java/com/android/server/appop/AppOpsService.java b/services/core/java/com/android/server/appop/AppOpsService.java
index d04aa8931dca..82a9168724bc 100644
--- a/services/core/java/com/android/server/appop/AppOpsService.java
+++ b/services/core/java/com/android/server/appop/AppOpsService.java
@@ -3559,8 +3559,6 @@ public class AppOpsService extends IAppOpsService.Stub {
pw.println(" Limit output to data associated with the given package name.");
pw.println(" --watchers");
pw.println(" Only output the watcher sections.");
- pw.println(" --history");
- pw.println(" Output the historical data.");
}
private void dumpStatesLocked(@NonNull PrintWriter pw, @NonNull Op op,
@@ -3696,8 +3694,6 @@ public class AppOpsService extends IAppOpsService.Stub {
}
} else if ("--watchers".equals(arg)) {
dumpWatchers = true;
- } else if ("--history".equals(arg)) {
- dumpHistory = true;
} else if (arg.length() > 0 && arg.charAt(0) == '-'){
pw.println("Unknown option: " + arg);
return;
diff --git a/services/core/java/com/android/server/attention/AttentionManagerService.java b/services/core/java/com/android/server/attention/AttentionManagerService.java
index 032af258dbd9..7605ccb5aeda 100644
--- a/services/core/java/com/android/server/attention/AttentionManagerService.java
+++ b/services/core/java/com/android/server/attention/AttentionManagerService.java
@@ -374,8 +374,15 @@ public class AttentionManagerService extends SystemService {
private void dumpInternal(IndentingPrintWriter ipw) {
ipw.println("Attention Manager Service (dumpsys attention) state:\n");
- ipw.printPair("context", mContext);
- ipw.println();
+ ipw.println("AttentionServicePackageName=" + getServiceConfigPackage(mContext));
+ ipw.println("Resolved component:");
+ if (mComponentName != null) {
+ ipw.increaseIndent();
+ ipw.println("Component=" + mComponentName.getPackageName());
+ ipw.println("Class=" + mComponentName.getClassName());
+ ipw.decreaseIndent();
+ }
+
synchronized (mLock) {
int size = mUserStates.size();
ipw.print("Number user states: ");
@@ -511,10 +518,24 @@ public class AttentionManagerService extends SystemService {
}
private void dump(IndentingPrintWriter pw) {
- pw.printPair("context", mContext);
- pw.printPair("userId", mUserId);
+ pw.println("userId=" + mUserId);
synchronized (mLock) {
- pw.printPair("binding", mBinding);
+ pw.println("binding=" + mBinding);
+ pw.println("current attention check:");
+ if (mCurrentAttentionCheck != null) {
+ pw.increaseIndent();
+ pw.println("is dispatched=" + mCurrentAttentionCheck.mIsDispatched);
+ pw.println("is fulfilled:=" + mCurrentAttentionCheck.mIsFulfilled);
+ pw.decreaseIndent();
+ }
+ pw.println("attention check cache:");
+ if (mAttentionCheckCache != null) {
+ pw.increaseIndent();
+ pw.println("last computed=" + mAttentionCheckCache.mLastComputed);
+ pw.println("timestamp=" + mAttentionCheckCache.mTimestamp);
+ pw.println("result=" + mAttentionCheckCache.mResult);
+ pw.decreaseIndent();
+ }
}
}
diff --git a/services/core/java/com/android/server/audio/AudioService.java b/services/core/java/com/android/server/audio/AudioService.java
index ad5f4e6e33c2..bec064495798 100644
--- a/services/core/java/com/android/server/audio/AudioService.java
+++ b/services/core/java/com/android/server/audio/AudioService.java
@@ -96,6 +96,7 @@ import android.media.audiopolicy.AudioProductStrategy;
import android.media.audiopolicy.AudioVolumeGroup;
import android.media.audiopolicy.IAudioPolicyCallback;
import android.media.projection.IMediaProjection;
+import android.media.projection.IMediaProjectionCallback;
import android.media.projection.IMediaProjectionManager;
import android.net.Uri;
import android.os.Binder;
@@ -6705,13 +6706,13 @@ public class AudioService extends IAudioService.Stub
String regId = null;
synchronized (mAudioPolicies) {
+ if (mAudioPolicies.containsKey(pcb.asBinder())) {
+ Slog.e(TAG, "Cannot re-register policy");
+ return null;
+ }
try {
- if (mAudioPolicies.containsKey(pcb.asBinder())) {
- Slog.e(TAG, "Cannot re-register policy");
- return null;
- }
AudioPolicyProxy app = new AudioPolicyProxy(policyConfig, pcb, hasFocusListener,
- isFocusPolicy, isTestFocusPolicy, isVolumeController);
+ isFocusPolicy, isTestFocusPolicy, isVolumeController, projection);
pcb.asBinder().linkToDeath(app, 0/*flags*/);
regId = app.getRegistrationId();
mAudioPolicies.put(pcb.asBinder(), app);
@@ -6720,6 +6721,9 @@ public class AudioService extends IAudioService.Stub
Slog.w(TAG, "Audio policy registration failed, could not link to " + pcb +
" binder death", e);
return null;
+ } catch (IllegalStateException e) {
+ Slog.w(TAG, "Audio policy registration failed for binder " + pcb, e);
+ return null;
}
}
return regId;
@@ -6884,9 +6888,9 @@ public class AudioService extends IAudioService.Stub
if (app == null){
return AudioManager.ERROR;
}
- app.addMixes(policyConfig.getMixes());
+ return app.addMixes(policyConfig.getMixes()) == AudioSystem.SUCCESS
+ ? AudioManager.SUCCESS : AudioManager.ERROR;
}
- return AudioManager.SUCCESS;
}
public int removeMixForPolicy(AudioPolicyConfig policyConfig, IAudioPolicyCallback pcb) {
@@ -6898,9 +6902,9 @@ public class AudioService extends IAudioService.Stub
if (app == null) {
return AudioManager.ERROR;
}
- app.removeMixes(policyConfig.getMixes());
+ return app.removeMixes(policyConfig.getMixes()) == AudioSystem.SUCCESS
+ ? AudioManager.SUCCESS : AudioManager.ERROR;
}
- return AudioManager.SUCCESS;
}
/** see AudioPolicy.setUidDeviceAffinity() */
@@ -7071,6 +7075,13 @@ public class AudioService extends IAudioService.Stub
mRecordMonitor.recorderEvent(riid, event);
}
+ /**
+ * Stop tracking the recorder
+ */
+ public void releaseRecorder(int riid) {
+ mRecordMonitor.releaseRecorder(riid);
+ }
+
public void disableRingtoneSync(final int userId) {
final int callingUserId = UserHandle.getCallingUserId();
if (callingUserId != userId) {
@@ -7158,6 +7169,15 @@ public class AudioService extends IAudioService.Stub
final boolean mIsVolumeController;
final HashMap<Integer, AudioDeviceArray> mUidDeviceAffinities =
new HashMap<Integer, AudioDeviceArray>();
+
+ final IMediaProjection mProjection;
+ private final class UnregisterOnStopCallback extends IMediaProjectionCallback.Stub {
+ public void onStop() {
+ unregisterAudioPolicyAsync(mPolicyCallback);
+ }
+ };
+ UnregisterOnStopCallback mProjectionCallback;
+
/**
* Audio focus ducking behavior for an audio policy.
* This variable reflects the value that was successfully set in
@@ -7171,12 +7191,13 @@ public class AudioService extends IAudioService.Stub
AudioPolicyProxy(AudioPolicyConfig config, IAudioPolicyCallback token,
boolean hasFocusListener, boolean isFocusPolicy, boolean isTestFocusPolicy,
- boolean isVolumeController) {
+ boolean isVolumeController, IMediaProjection projection) {
super(config);
setRegistration(new String(config.hashCode() + ":ap:" + mAudioPolicyCounter++));
mPolicyCallback = token;
mHasFocusListener = hasFocusListener;
mIsVolumeController = isVolumeController;
+ mProjection = projection;
if (mHasFocusListener) {
mMediaFocusControl.addFocusFollower(mPolicyCallback);
// can only ever be true if there is a focus listener
@@ -7189,7 +7210,21 @@ public class AudioService extends IAudioService.Stub
if (mIsVolumeController) {
setExtVolumeController(mPolicyCallback);
}
- connectMixes();
+ if (mProjection != null) {
+ mProjectionCallback = new UnregisterOnStopCallback();
+ try {
+ mProjection.registerCallback(mProjectionCallback);
+ } catch (RemoteException e) {
+ release();
+ throw new IllegalStateException("MediaProjection callback registration failed, "
+ + "could not link to " + projection + " binder death", e);
+ }
+ }
+ int status = connectMixes();
+ if (status != AudioSystem.SUCCESS) {
+ release();
+ throw new IllegalStateException("Could not connect mix, error: " + status);
+ }
}
public void binderDied() {
@@ -7219,6 +7254,13 @@ public class AudioService extends IAudioService.Stub
if (mHasFocusListener) {
mMediaFocusControl.removeFocusFollower(mPolicyCallback);
}
+ if (mProjectionCallback != null) {
+ try {
+ mProjection.unregisterCallback(mProjectionCallback);
+ } catch (RemoteException e) {
+ Log.e(TAG, "Fail to unregister Audiopolicy callback from MediaProjection");
+ }
+ }
final long identity = Binder.clearCallingIdentity();
AudioSystem.registerPolicyMixes(mMixes, false);
Binder.restoreCallingIdentity(identity);
@@ -7253,28 +7295,29 @@ public class AudioService extends IAudioService.Stub
return true;
}
- void addMixes(@NonNull ArrayList<AudioMix> mixes) {
+ int addMixes(@NonNull ArrayList<AudioMix> mixes) {
// TODO optimize to not have to unregister the mixes already in place
synchronized (mMixes) {
AudioSystem.registerPolicyMixes(mMixes, false);
this.add(mixes);
- AudioSystem.registerPolicyMixes(mMixes, true);
+ return AudioSystem.registerPolicyMixes(mMixes, true);
}
}
- void removeMixes(@NonNull ArrayList<AudioMix> mixes) {
+ int removeMixes(@NonNull ArrayList<AudioMix> mixes) {
// TODO optimize to not have to unregister the mixes already in place
synchronized (mMixes) {
AudioSystem.registerPolicyMixes(mMixes, false);
this.remove(mixes);
- AudioSystem.registerPolicyMixes(mMixes, true);
+ return AudioSystem.registerPolicyMixes(mMixes, true);
}
}
- void connectMixes() {
+ int connectMixes() {
final long identity = Binder.clearCallingIdentity();
- AudioSystem.registerPolicyMixes(mMixes, true);
+ int status = AudioSystem.registerPolicyMixes(mMixes, true);
Binder.restoreCallingIdentity(identity);
+ return status;
}
int setUidDeviceAffinities(int uid, @NonNull int[] types, @NonNull String[] addresses) {
@@ -7313,6 +7356,20 @@ public class AudioService extends IAudioService.Stub
Log.e(TAG, "AudioSystem. removeUidDeviceAffinities failed");
return AudioManager.ERROR;
}
+
+ /** @return human readable debug informations summarizing the state of the object. */
+ public String toLogFriendlyString() {
+ String textDump = super.toLogFriendlyString();
+ textDump += " Proxy:\n";
+ textDump += " is focus policy= " + mIsFocusPolicy + "\n";
+ if (mIsFocusPolicy) {
+ textDump += " focus duck behaviour= " + mFocusDuckBehavior + "\n";
+ textDump += " is test focus policy= " + mIsTestFocusPolicy + "\n";
+ textDump += " has focus listener= " + mHasFocusListener + "\n";
+ }
+ textDump += " media projection= " + mProjection + "\n";
+ return textDump;
+ }
};
//======================
diff --git a/services/core/java/com/android/server/audio/RecordingActivityMonitor.java b/services/core/java/com/android/server/audio/RecordingActivityMonitor.java
index 69d1ea76c1e3..5d31dbe93cf9 100644
--- a/services/core/java/com/android/server/audio/RecordingActivityMonitor.java
+++ b/services/core/java/com/android/server/audio/RecordingActivityMonitor.java
@@ -176,8 +176,11 @@ public final class RecordingActivityMonitor implements AudioSystem.AudioRecordin
dispatchCallbacks(updateSnapshot(configEvent, riid, null));
}
- void unregisterRecorder(int riid) {
- dispatchCallbacks(updateSnapshot(AudioManager.RECORD_CONFIG_EVENT_DEATH, riid, null));
+ /**
+ * Stop tracking the recorder
+ */
+ public void releaseRecorder(int riid) {
+ dispatchCallbacks(updateSnapshot(AudioManager.RECORD_CONFIG_EVENT_RELEASE, riid, null));
}
private void dispatchCallbacks(List<AudioRecordingConfiguration> configs) {
@@ -246,7 +249,7 @@ public final class RecordingActivityMonitor implements AudioSystem.AudioRecordin
if (state.isActiveConfiguration()) {
configChanged = true;
sEventLogger.log(new RecordingEvent(
- AudioManager.RECORD_CONFIG_EVENT_DEATH,
+ AudioManager.RECORD_CONFIG_EVENT_RELEASE,
state.getRiid(), state.getConfig()));
}
it.remove();
@@ -396,7 +399,7 @@ public final class RecordingActivityMonitor implements AudioSystem.AudioRecordin
switch (event) {
case AudioManager.RECORD_CONFIG_EVENT_START:
configChanged = state.setActive(true);
- if (config != null) { // ??? Can remove ???
+ if (config != null) {
configChanged = state.setConfig(config) || configChanged;
}
break;
@@ -412,7 +415,7 @@ public final class RecordingActivityMonitor implements AudioSystem.AudioRecordin
mRecordStates.remove(stateIndex);
}
break;
- case AudioManager.RECORD_CONFIG_EVENT_DEATH:
+ case AudioManager.RECORD_CONFIG_EVENT_RELEASE:
configChanged = state.isActiveConfiguration();
mRecordStates.remove(stateIndex);
break;
@@ -504,7 +507,7 @@ public final class RecordingActivityMonitor implements AudioSystem.AudioRecordin
}
public void binderDied() {
- sMonitor.unregisterRecorder(mRiid);
+ sMonitor.releaseRecorder(mRiid);
}
boolean init() {
@@ -553,8 +556,8 @@ public final class RecordingActivityMonitor implements AudioSystem.AudioRecordin
return "update";
case AudioManager.RECORD_CONFIG_EVENT_STOP:
return "stop";
- case AudioManager.RECORD_CONFIG_EVENT_DEATH:
- return "death";
+ case AudioManager.RECORD_CONFIG_EVENT_RELEASE:
+ return "release";
default:
return "unknown (" + recEvent + ")";
}
diff --git a/services/core/java/com/android/server/display/BrightnessMappingStrategy.java b/services/core/java/com/android/server/display/BrightnessMappingStrategy.java
index 9fce644d6c4b..171cc5abdb97 100644
--- a/services/core/java/com/android/server/display/BrightnessMappingStrategy.java
+++ b/services/core/java/com/android/server/display/BrightnessMappingStrategy.java
@@ -778,6 +778,7 @@ public abstract class BrightnessMappingStrategy {
pw.println(" mAutoBrightnessAdjustment=" + mAutoBrightnessAdjustment);
pw.println(" mUserLux=" + mUserLux);
pw.println(" mUserBrightness=" + mUserBrightness);
+ pw.println(" mDefaultConfig=" + mDefaultConfig);
}
private void computeSpline() {
diff --git a/services/core/java/com/android/server/location/GnssLocationProvider.java b/services/core/java/com/android/server/location/GnssLocationProvider.java
index 5f1f20294bc1..26884a0afd25 100644
--- a/services/core/java/com/android/server/location/GnssLocationProvider.java
+++ b/services/core/java/com/android/server/location/GnssLocationProvider.java
@@ -311,8 +311,9 @@ public class GnssLocationProvider extends AbstractLocationProvider implements
private final ExponentialBackOff mPsdsBackOff = new ExponentialBackOff(RETRY_INTERVAL,
MAX_RETRY_INTERVAL);
- // true if we are enabled, protected by this
- private boolean mEnabled;
+ // True if we are enabled
+ @GuardedBy("mLock")
+ private boolean mGpsEnabled;
private boolean mShutdown;
@@ -406,6 +407,7 @@ public class GnssLocationProvider extends AbstractLocationProvider implements
private final static String WAKELOCK_KEY = "GnssLocationProvider";
private final PowerManager.WakeLock mWakeLock;
private static final String DOWNLOAD_EXTRA_WAKELOCK_KEY = "GnssLocationProviderPsdsDownload";
+ @GuardedBy("mLock")
private final PowerManager.WakeLock mDownloadPsdsWakeLock;
// Alarms
@@ -517,29 +519,27 @@ public class GnssLocationProvider extends AbstractLocationProvider implements
boolean isKeepLppProfile = false;
if (!TextUtils.isEmpty(mccMnc)) {
if (DEBUG) Log.d(TAG, "SIM MCC/MNC is available: " + mccMnc);
- synchronized (mLock) {
- if (configManager != null) {
- PersistableBundle b = configManager.getConfig();
- if (b != null) {
- isKeepLppProfile =
- b.getBoolean(CarrierConfigManager.Gps.KEY_PERSIST_LPP_MODE_BOOL);
- }
+ if (configManager != null) {
+ PersistableBundle b = configManager.getConfig();
+ if (b != null) {
+ isKeepLppProfile =
+ b.getBoolean(CarrierConfigManager.Gps.KEY_PERSIST_LPP_MODE_BOOL);
}
- if (isKeepLppProfile) {
- // load current properties for the carrier
- mGnssConfiguration.loadPropertiesFromCarrierConfig();
- String lpp_profile = mGnssConfiguration.getLppProfile();
- // set the persist property LPP_PROFILE for the value
- if (lpp_profile != null) {
- SystemProperties.set(GnssConfiguration.LPP_PROFILE, lpp_profile);
- }
- } else {
- // reset the persist property
- SystemProperties.set(GnssConfiguration.LPP_PROFILE, "");
+ }
+ if (isKeepLppProfile) {
+ // load current properties for the carrier
+ mGnssConfiguration.loadPropertiesFromCarrierConfig();
+ String lpp_profile = mGnssConfiguration.getLppProfile();
+ // set the persist property LPP_PROFILE for the value
+ if (lpp_profile != null) {
+ SystemProperties.set(GnssConfiguration.LPP_PROFILE, lpp_profile);
}
- reloadGpsProperties();
- mNIHandler.setSuplEsEnabled(mSuplEsEnabled);
+ } else {
+ // reset the persist property
+ SystemProperties.set(GnssConfiguration.LPP_PROFILE, "");
}
+ reloadGpsProperties();
+ mNIHandler.setSuplEsEnabled(mSuplEsEnabled);
} else {
if (DEBUG) Log.d(TAG, "SIM MCC/MNC is still not available");
}
@@ -636,14 +636,14 @@ public class GnssLocationProvider extends AbstractLocationProvider implements
@Override
protected boolean isGpsEnabled() {
- return isEnabled();
+ return GnssLocationProvider.this.isGpsEnabled();
}
};
mGnssMeasurementsProvider = new GnssMeasurementsProvider(mContext, mHandler) {
@Override
protected boolean isGpsEnabled() {
- return isEnabled();
+ return GnssLocationProvider.this.isGpsEnabled();
}
};
@@ -652,7 +652,7 @@ public class GnssLocationProvider extends AbstractLocationProvider implements
mGnssNavigationMessageProvider = new GnssNavigationMessageProvider(mContext, mHandler) {
@Override
protected boolean isGpsEnabled() {
- return isEnabled();
+ return GnssLocationProvider.this.isGpsEnabled();
}
};
@@ -829,8 +829,10 @@ public class GnssLocationProvider extends AbstractLocationProvider implements
}
mDownloadPsdsDataPending = STATE_DOWNLOADING;
- // hold wake lock while task runs
- mDownloadPsdsWakeLock.acquire(DOWNLOAD_PSDS_DATA_TIMEOUT_MS);
+ synchronized (mLock) {
+ // hold wake lock while task runs
+ mDownloadPsdsWakeLock.acquire(DOWNLOAD_PSDS_DATA_TIMEOUT_MS);
+ }
Log.i(TAG, "WakeLock acquired by handleDownloadPsdsData()");
AsyncTask.THREAD_POOL_EXECUTOR.execute(() -> {
GpsPsdsDownloader psdsDownloader = new GpsPsdsDownloader(
@@ -913,14 +915,19 @@ public class GnssLocationProvider extends AbstractLocationProvider implements
return GPS_POSITION_MODE_STANDALONE;
}
- @GuardedBy("mLock")
- private void handleEnableLocked() {
- if (DEBUG) Log.d(TAG, "handleEnableLocked");
+ private void setGpsEnabled(boolean enabled) {
+ synchronized (mLock) {
+ mGpsEnabled = enabled;
+ }
+ }
+
+ private void handleEnable() {
+ if (DEBUG) Log.d(TAG, "handleEnable");
boolean inited = native_init();
if (inited) {
- mEnabled = true;
+ setGpsEnabled(true);
mSupportsPsds = native_supports_psds();
// TODO: remove the following native calls if we can make sure they are redundant.
@@ -937,26 +944,25 @@ public class GnssLocationProvider extends AbstractLocationProvider implements
mGnssNavigationMessageProvider.onGpsEnabledChanged();
mGnssBatchingProvider.enable();
if (mGnssVisibilityControl != null) {
- mGnssVisibilityControl.onGpsEnabledChanged(mEnabled);
+ mGnssVisibilityControl.onGpsEnabledChanged(/* isEnabled= */true);
}
} else {
- mEnabled = false;
+ setGpsEnabled(false);
Log.w(TAG, "Failed to enable location provider");
}
}
- @GuardedBy("mLock")
- private void handleDisableLocked() {
- if (DEBUG) Log.d(TAG, "handleDisableLocked");
+ private void handleDisable() {
+ if (DEBUG) Log.d(TAG, "handleDisable");
- mEnabled = false;
+ setGpsEnabled(false);
updateClientUids(new WorkSource());
stopNavigating();
mAlarmManager.cancel(mWakeupIntent);
mAlarmManager.cancel(mTimeoutIntent);
if (mGnssVisibilityControl != null) {
- mGnssVisibilityControl.onGpsEnabledChanged(mEnabled);
+ mGnssVisibilityControl.onGpsEnabledChanged(/* isEnabled= */ false);
}
mGnssBatchingProvider.disable();
// do this before releasing wakelock
@@ -967,35 +973,33 @@ public class GnssLocationProvider extends AbstractLocationProvider implements
}
private void updateEnabled() {
- synchronized (mLock) {
- // Generally follow location setting
- boolean enabled = mContext.getSystemService(LocationManager.class).isLocationEnabled();
+ // Generally follow location setting
+ boolean enabled = mContext.getSystemService(LocationManager.class).isLocationEnabled();
- // ... but disable if PowerManager overrides
- enabled &= !mDisableGpsForPowerManager;
+ // ... but disable if PowerManager overrides
+ enabled &= !mDisableGpsForPowerManager;
- // .. but enable anyway, if there's an active settings-ignored request (e.g. ELS)
- enabled |= (mProviderRequest != null && mProviderRequest.reportLocation
- && mProviderRequest.locationSettingsIgnored);
+ // .. but enable anyway, if there's an active settings-ignored request (e.g. ELS)
+ enabled |= (mProviderRequest != null && mProviderRequest.reportLocation
+ && mProviderRequest.locationSettingsIgnored);
- // ... and, finally, disable anyway, if device is being shut down
- enabled &= !mShutdown;
+ // ... and, finally, disable anyway, if device is being shut down
+ enabled &= !mShutdown;
- if (enabled == mEnabled) {
- return;
- }
+ if (enabled == isGpsEnabled()) {
+ return;
+ }
- if (enabled) {
- handleEnableLocked();
- } else {
- handleDisableLocked();
- }
+ if (enabled) {
+ handleEnable();
+ } else {
+ handleDisable();
}
}
- public boolean isEnabled() {
+ private boolean isGpsEnabled() {
synchronized (mLock) {
- return mEnabled;
+ return mGpsEnabled;
}
}
@@ -1036,7 +1040,7 @@ public class GnssLocationProvider extends AbstractLocationProvider implements
}
if (DEBUG) Log.d(TAG, "setRequest " + mProviderRequest);
- if (mProviderRequest.reportLocation && isEnabled()) {
+ if (mProviderRequest.reportLocation && isGpsEnabled()) {
// update client uids
updateClientUids(mWorkSource);
@@ -1598,10 +1602,9 @@ public class GnssLocationProvider extends AbstractLocationProvider implements
if (DEBUG) Log.d(TAG, "reportGnssServiceDied");
mHandler.post(() -> {
setupNativeGnssService(/* reinitializeGnssServiceHandle = */ true);
- if (isEnabled()) {
- synchronized (mLock) {
- mEnabled = false;
- }
+ if (isGpsEnabled()) {
+ setGpsEnabled(false);
+
updateEnabled();
// resend configuration into the restarted HAL service.
@@ -1809,7 +1812,7 @@ public class GnssLocationProvider extends AbstractLocationProvider implements
/* requestorIdEncoding= */ 0,
/* textEncoding= */ 0,
mSuplEsEnabled,
- isEnabled(),
+ isGpsEnabled(),
userResponse);
return true;
@@ -1875,7 +1878,7 @@ public class GnssLocationProvider extends AbstractLocationProvider implements
notification.requestorIdEncoding,
notification.textEncoding,
mSuplEsEnabled,
- isEnabled(),
+ isGpsEnabled(),
/* userResponse= */ 0);
}
@@ -2055,7 +2058,7 @@ public class GnssLocationProvider extends AbstractLocationProvider implements
setupNativeGnssService(/* reinitializeGnssServiceHandle = */ false);
if (native_is_gnss_visibility_control_supported()) {
- mGnssVisibilityControl = new GnssVisibilityControl(mContext, mLooper);
+ mGnssVisibilityControl = new GnssVisibilityControl(mContext, mLooper, mNIHandler);
}
// load default GPS configuration
diff --git a/services/core/java/com/android/server/location/GnssVisibilityControl.java b/services/core/java/com/android/server/location/GnssVisibilityControl.java
index c3626d2373ea..860138675529 100644
--- a/services/core/java/com/android/server/location/GnssVisibilityControl.java
+++ b/services/core/java/com/android/server/location/GnssVisibilityControl.java
@@ -33,6 +33,9 @@ import android.util.ArrayMap;
import android.util.Log;
import android.util.StatsLog;
+import com.android.internal.R;
+import com.android.internal.location.GpsNetInitiatedHandler;
+
import java.util.Arrays;
import java.util.List;
import java.util.Map;
@@ -65,6 +68,7 @@ class GnssVisibilityControl {
private final Handler mHandler;
private final Context mContext;
+ private final GpsNetInitiatedHandler mNiHandler;
private boolean mIsGpsEnabled;
@@ -76,11 +80,12 @@ class GnssVisibilityControl {
private PackageManager.OnPermissionsChangedListener mOnPermissionsChangedListener =
uid -> runOnHandler(() -> handlePermissionsChanged(uid));
- GnssVisibilityControl(Context context, Looper looper) {
+ GnssVisibilityControl(Context context, Looper looper, GpsNetInitiatedHandler niHandler) {
mContext = context;
PowerManager powerManager = (PowerManager) context.getSystemService(Context.POWER_SERVICE);
mWakeLock = powerManager.newWakeLock(PowerManager.PARTIAL_WAKE_LOCK, WAKELOCK_KEY);
mHandler = new Handler(looper);
+ mNiHandler = niHandler;
mAppOps = mContext.getSystemService(AppOpsManager.class);
mPackageManager = mContext.getPackageManager();
@@ -250,6 +255,9 @@ class GnssVisibilityControl {
private static final byte NFW_RESPONSE_TYPE_ACCEPTED_NO_LOCATION_PROVIDED = 1;
private static final byte NFW_RESPONSE_TYPE_ACCEPTED_LOCATION_PROVIDED = 2;
+ // This must match with NfwProtocolStack enum in IGnssVisibilityControlCallback.hal.
+ private static final byte NFW_PROTOCOL_STACK_SUPL = 1;
+
private final String mProxyAppPackageName;
private final byte mProtocolStack;
private final String mOtherProtocolStackName;
@@ -299,6 +307,10 @@ class GnssVisibilityControl {
return mResponseType != NfwNotification.NFW_RESPONSE_TYPE_REJECTED;
}
+ private boolean isLocationProvided() {
+ return mResponseType == NfwNotification.NFW_RESPONSE_TYPE_ACCEPTED_LOCATION_PROVIDED;
+ }
+
private boolean isRequestAttributedToProxyApp() {
return !TextUtils.isEmpty(mProxyAppPackageName);
}
@@ -306,6 +318,10 @@ class GnssVisibilityControl {
private boolean isEmergencyRequestNotification() {
return mInEmergencyMode && !isRequestAttributedToProxyApp();
}
+
+ private boolean isRequestTypeSupl() {
+ return mProtocolStack == NFW_PROTOCOL_STACK_SUPL;
+ }
}
private void handlePermissionsChanged(int uid) {
@@ -430,16 +446,15 @@ class GnssVisibilityControl {
return;
}
- Log.e(TAG, "ProxyAppPackageName field is not set. AppOps service not notified "
- + "for non-framework location access notification: " + nfwNotification);
+ Log.e(TAG, "ProxyAppPackageName field is not set. AppOps service not notified"
+ + " for notification: " + nfwNotification);
return;
}
if (isLocationPermissionEnabled == null) {
- Log.w(TAG, "Could not find proxy app with name: " + proxyAppPkgName + " in the "
- + "value specified for config parameter: "
- + GnssConfiguration.CONFIG_NFW_PROXY_APPS + ". AppOps service not notified "
- + "for non-framework location access notification: " + nfwNotification);
+ Log.w(TAG, "Could not find proxy app " + proxyAppPkgName + " in the value specified for"
+ + " config parameter: " + GnssConfiguration.CONFIG_NFW_PROXY_APPS
+ + ". AppOps service not notified for notification: " + nfwNotification);
return;
}
@@ -447,8 +462,7 @@ class GnssVisibilityControl {
final ApplicationInfo proxyAppInfo = getProxyAppInfo(proxyAppPkgName);
if (proxyAppInfo == null) {
Log.e(TAG, "Proxy app " + proxyAppPkgName + " is not found. AppOps service not "
- + "notified for non-framework location access notification: "
- + nfwNotification);
+ + "notified for notification: " + nfwNotification);
return;
}
@@ -465,13 +479,40 @@ class GnssVisibilityControl {
}
private void handleEmergencyNfwNotification(NfwNotification nfwNotification) {
- boolean isPermissionMismatched =
- (nfwNotification.mResponseType == NfwNotification.NFW_RESPONSE_TYPE_REJECTED);
- if (isPermissionMismatched) {
+ boolean isPermissionMismatched = false;
+ if (!nfwNotification.isRequestAccepted()) {
Log.e(TAG, "Emergency non-framework location request incorrectly rejected."
+ " Notification: " + nfwNotification);
+ isPermissionMismatched = true;
+ }
+
+ if (!mNiHandler.getInEmergency()) {
+ Log.w(TAG, "Emergency state mismatch. Device currently not in user initiated emergency"
+ + " session. Notification: " + nfwNotification);
+ isPermissionMismatched = true;
}
+
logEvent(nfwNotification, isPermissionMismatched);
+
+ if (nfwNotification.isLocationProvided()) {
+ // Emulate deprecated IGnssNi.hal user notification of emergency NI requests.
+ GpsNetInitiatedHandler.GpsNiNotification notification =
+ new GpsNetInitiatedHandler.GpsNiNotification();
+ notification.notificationId = 0;
+ notification.niType = nfwNotification.isRequestTypeSupl()
+ ? GpsNetInitiatedHandler.GPS_NI_TYPE_EMERGENCY_SUPL
+ : GpsNetInitiatedHandler.GPS_NI_TYPE_UMTS_CTRL_PLANE;
+ notification.needNotify = true;
+ notification.needVerify = false;
+ notification.privacyOverride = false;
+ notification.timeout = 0;
+ notification.defaultResponse = GpsNetInitiatedHandler.GPS_NI_RESPONSE_NORESP;
+ notification.requestorId = nfwNotification.mRequestorId;
+ notification.requestorIdEncoding = GpsNetInitiatedHandler.GPS_ENC_NONE;
+ notification.text = mContext.getString(R.string.global_action_emergency);
+ notification.textEncoding = GpsNetInitiatedHandler.GPS_ENC_NONE;
+ mNiHandler.setNiNotification(notification);
+ }
}
private void logEvent(NfwNotification notification, boolean isPermissionMismatched) {
diff --git a/services/core/java/com/android/server/media/MediaSessionRecord.java b/services/core/java/com/android/server/media/MediaSessionRecord.java
index a8c16c769b91..e2087e6ca822 100644
--- a/services/core/java/com/android/server/media/MediaSessionRecord.java
+++ b/services/core/java/com/android/server/media/MediaSessionRecord.java
@@ -19,12 +19,12 @@ package com.android.server.media;
import android.app.PendingIntent;
import android.content.Context;
import android.content.Intent;
+import android.content.pm.ParceledListSlice;
import android.media.AudioAttributes;
import android.media.AudioManager;
import android.media.AudioManagerInternal;
import android.media.AudioSystem;
import android.media.MediaMetadata;
-import android.media.MediaParceledListSlice;
import android.media.Rating;
import android.media.VolumeProvider;
import android.media.session.ISession;
@@ -84,7 +84,7 @@ public class MediaSessionRecord implements IBinder.DeathRecipient {
private final MediaSession.Token mSessionToken;
private final SessionStub mSession;
private final SessionCb mSessionCb;
- private final MediaSessionService.ServiceImpl mService;
+ private final MediaSessionService mService;
private final Context mContext;
private final Object mLock = new Object();
@@ -125,7 +125,7 @@ public class MediaSessionRecord implements IBinder.DeathRecipient {
public MediaSessionRecord(int ownerPid, int ownerUid, int userId, String ownerPackageName,
ISessionCallback cb, String tag, Bundle sessionInfo,
- MediaSessionService.ServiceImpl service, Looper handlerLooper) {
+ MediaSessionService service, Looper handlerLooper) {
mOwnerPid = ownerPid;
mOwnerUid = ownerUid;
mUserId = userId;
@@ -612,7 +612,7 @@ public class MediaSessionRecord implements IBinder.DeathRecipient {
ISessionControllerCallbackHolder holder = mControllerCallbackHolders.get(i);
try {
holder.mCallback.onQueueChanged(mQueue == null ? null :
- new MediaParceledListSlice<>(mQueue));
+ new ParceledListSlice<>(mQueue));
} catch (DeadObjectException e) {
mControllerCallbackHolders.remove(i);
logCallbackException("Removing dead callback in pushQueueUpdate", holder, e);
@@ -904,7 +904,7 @@ public class MediaSessionRecord implements IBinder.DeathRecipient {
}
@Override
- public void setQueue(MediaParceledListSlice queue) throws RemoteException {
+ public void setQueue(ParceledListSlice queue) throws RemoteException {
synchronized (mLock) {
mQueue = queue == null ? null : (List<QueueItem>) queue.getList();
}
@@ -1469,9 +1469,9 @@ public class MediaSessionRecord implements IBinder.DeathRecipient {
}
@Override
- public MediaParceledListSlice getQueue() {
+ public ParceledListSlice getQueue() {
synchronized (mLock) {
- return mQueue == null ? null : new MediaParceledListSlice<>(mQueue);
+ return mQueue == null ? null : new ParceledListSlice<>(mQueue);
}
}
diff --git a/services/core/java/com/android/server/media/MediaSessionService.java b/services/core/java/com/android/server/media/MediaSessionService.java
index d20ed8c11009..adc15611c438 100644
--- a/services/core/java/com/android/server/media/MediaSessionService.java
+++ b/services/core/java/com/android/server/media/MediaSessionService.java
@@ -16,15 +16,81 @@
package com.android.server.media;
+import static android.os.UserHandle.USER_ALL;
+
+import android.annotation.Nullable;
+import android.app.ActivityManager;
+import android.app.INotificationManager;
+import android.app.KeyguardManager;
+import android.app.PendingIntent;
+import android.app.PendingIntent.CanceledException;
+import android.content.ActivityNotFoundException;
+import android.content.BroadcastReceiver;
+import android.content.ComponentName;
+import android.content.ContentResolver;
import android.content.Context;
+import android.content.Intent;
+import android.content.pm.ActivityInfo;
+import android.content.pm.PackageManager;
+import android.content.pm.PackageManager.NameNotFoundException;
+import android.content.pm.ParceledListSlice;
+import android.content.pm.ServiceInfo;
+import android.content.pm.UserInfo;
+import android.database.ContentObserver;
+import android.media.AudioManager;
+import android.media.AudioManagerInternal;
+import android.media.AudioPlaybackConfiguration;
+import android.media.AudioSystem;
+import android.media.IAudioService;
+import android.media.IRemoteVolumeController;
+import android.media.MediaController2;
+import android.media.Session2CommandGroup;
import android.media.Session2Token;
+import android.media.session.IActiveSessionsListener;
+import android.media.session.ICallback;
+import android.media.session.IOnMediaKeyListener;
+import android.media.session.IOnVolumeKeyLongPressListener;
+import android.media.session.ISession;
+import android.media.session.ISession2TokensListener;
+import android.media.session.ISessionCallback;
+import android.media.session.ISessionManager;
+import android.media.session.MediaSession;
+import android.media.session.MediaSessionManager;
+import android.net.Uri;
+import android.os.Binder;
+import android.os.Bundle;
+import android.os.Handler;
+import android.os.HandlerExecutor;
import android.os.IBinder;
+import android.os.Message;
+import android.os.PowerManager;
+import android.os.Process;
+import android.os.RemoteCallbackList;
+import android.os.RemoteException;
+import android.os.ResultReceiver;
+import android.os.ServiceManager;
+import android.os.UserHandle;
+import android.os.UserManager;
+import android.provider.Settings;
+import android.speech.RecognizerIntent;
+import android.text.TextUtils;
import android.util.Log;
+import android.util.Slog;
+import android.util.SparseArray;
+import android.util.SparseIntArray;
+import android.view.KeyEvent;
+import android.view.ViewConfiguration;
+import com.android.internal.annotations.GuardedBy;
+import com.android.internal.util.DumpUtils;
+import com.android.server.LocalServices;
import com.android.server.SystemService;
import com.android.server.Watchdog;
import com.android.server.Watchdog.Monitor;
+import java.io.FileDescriptor;
+import java.io.PrintWriter;
+import java.util.ArrayList;
import java.util.List;
/**
@@ -33,124 +99,2168 @@ import java.util.List;
public class MediaSessionService extends SystemService implements Monitor {
private static final String TAG = "MediaSessionService";
static final boolean DEBUG = Log.isLoggable(TAG, Log.DEBUG);
+ // Leave log for key event always.
+ private static final boolean DEBUG_KEY_EVENT = true;
+
+ private static final int WAKELOCK_TIMEOUT = 5000;
+ private static final int MEDIA_KEY_LISTENER_TIMEOUT = 1000;
+
+ private final Context mContext;
+ private final SessionManagerImpl mSessionManagerImpl;
+ private final MessageHandler mHandler = new MessageHandler();
+ private final PowerManager.WakeLock mMediaEventWakeLock;
+ private final int mLongPressTimeout;
+ private final INotificationManager mNotificationManager;
+ private final Object mLock = new Object();
+ // Keeps the full user id for each user.
+ @GuardedBy("mLock")
+ private final SparseIntArray mFullUserIds = new SparseIntArray();
+ @GuardedBy("mLock")
+ private final SparseArray<FullUserRecord> mUserRecords = new SparseArray<FullUserRecord>();
+ @GuardedBy("mLock")
+ private final ArrayList<SessionsListenerRecord> mSessionsListeners =
+ new ArrayList<SessionsListenerRecord>();
+ // Map user id as index to list of Session2Tokens
+ // TODO: Keep session2 info in MediaSessionStack for prioritizing both session1 and session2 in
+ // one place.
+ @GuardedBy("mLock")
+ private final SparseArray<List<Session2Token>> mSession2TokensPerUser = new SparseArray<>();
+ @GuardedBy("mLock")
+ private final List<Session2TokensListenerRecord> mSession2TokensListenerRecords =
+ new ArrayList<>();
- private final ServiceImpl mImpl;
+ private KeyguardManager mKeyguardManager;
+ private IAudioService mAudioService;
+ private AudioManagerInternal mAudioManagerInternal;
+ private ActivityManager mActivityManager;
+ private ContentResolver mContentResolver;
+ private SettingsObserver mSettingsObserver;
+ private boolean mHasFeatureLeanback;
+
+ // The FullUserRecord of the current users. (i.e. The foreground user that isn't a profile)
+ // It's always not null after the MediaSessionService is started.
+ private FullUserRecord mCurrentFullUserRecord;
+ private MediaSessionRecord mGlobalPrioritySession;
+ private AudioPlayerStateMonitor mAudioPlayerStateMonitor;
+
+ // Used to notify System UI and Settings when remote volume was changed.
+ @GuardedBy("mLock")
+ final RemoteCallbackList<IRemoteVolumeController> mRemoteVolumeControllers =
+ new RemoteCallbackList<>();
public MediaSessionService(Context context) {
super(context);
- mImpl = new MediaSessionServiceImpl(context);
+ mContext = context;
+ mSessionManagerImpl = new SessionManagerImpl();
+ PowerManager pm = (PowerManager) context.getSystemService(Context.POWER_SERVICE);
+ mMediaEventWakeLock = pm.newWakeLock(PowerManager.PARTIAL_WAKE_LOCK, "handleMediaEvent");
+ mLongPressTimeout = ViewConfiguration.getLongPressTimeout();
+ mNotificationManager = INotificationManager.Stub.asInterface(
+ ServiceManager.getService(Context.NOTIFICATION_SERVICE));
}
@Override
public void onStart() {
- publishBinderService(Context.MEDIA_SESSION_SERVICE, mImpl.getServiceBinder());
+ publishBinderService(Context.MEDIA_SESSION_SERVICE, mSessionManagerImpl);
Watchdog.getInstance().addMonitor(this);
+ mKeyguardManager = (KeyguardManager) mContext.getSystemService(Context.KEYGUARD_SERVICE);
+ mAudioService = getAudioService();
+ mAudioManagerInternal = LocalServices.getService(AudioManagerInternal.class);
+ mActivityManager =
+ (ActivityManager) mContext.getSystemService(Context.ACTIVITY_SERVICE);
+ mAudioPlayerStateMonitor = AudioPlayerStateMonitor.getInstance(mContext);
+ mAudioPlayerStateMonitor.registerListener(
+ (config, isRemoved) -> {
+ if (config.getPlayerType()
+ == AudioPlaybackConfiguration.PLAYER_TYPE_JAM_SOUNDPOOL) {
+ return;
+ }
+ synchronized (mLock) {
+ FullUserRecord user = getFullUserRecordLocked(
+ UserHandle.getUserId(config.getClientUid()));
+ if (user != null) {
+ user.mPriorityStack.updateMediaButtonSessionIfNeeded();
+ }
+ }
+ }, null /* handler */);
+ mContentResolver = mContext.getContentResolver();
+ mSettingsObserver = new SettingsObserver();
+ mSettingsObserver.observe();
+ mHasFeatureLeanback = mContext.getPackageManager().hasSystemFeature(
+ PackageManager.FEATURE_LEANBACK);
+ updateUser();
+ }
+
+ private IAudioService getAudioService() {
+ IBinder b = ServiceManager.getService(Context.AUDIO_SERVICE);
+ return IAudioService.Stub.asInterface(b);
+ }
+
+ private boolean isGlobalPriorityActiveLocked() {
+ return mGlobalPrioritySession != null && mGlobalPrioritySession.isActive();
+ }
+
+ void updateSession(MediaSessionRecord record) {
+ synchronized (mLock) {
+ FullUserRecord user = getFullUserRecordLocked(record.getUserId());
+ if (user == null) {
+ Log.w(TAG, "Unknown session updated. Ignoring.");
+ return;
+ }
+ if ((record.getFlags() & MediaSession.FLAG_EXCLUSIVE_GLOBAL_PRIORITY) != 0) {
+ if (DEBUG_KEY_EVENT) {
+ Log.d(TAG, "Global priority session is updated, active=" + record.isActive());
+ }
+ user.pushAddressedPlayerChangedLocked();
+ } else {
+ if (!user.mPriorityStack.contains(record)) {
+ Log.w(TAG, "Unknown session updated. Ignoring.");
+ return;
+ }
+ user.mPriorityStack.onSessionStateChange(record);
+ }
+ mHandler.postSessionsChanged(record.getUserId());
+ }
+ }
+
+ void setGlobalPrioritySession(MediaSessionRecord record) {
+ synchronized (mLock) {
+ FullUserRecord user = getFullUserRecordLocked(record.getUserId());
+ if (mGlobalPrioritySession != record) {
+ Log.d(TAG, "Global priority session is changed from " + mGlobalPrioritySession
+ + " to " + record);
+ mGlobalPrioritySession = record;
+ if (user != null && user.mPriorityStack.contains(record)) {
+ // Handle the global priority session separately.
+ // Otherwise, it can be the media button session regardless of the active state
+ // because it or other system components might have been the lastly played media
+ // app.
+ user.mPriorityStack.removeSession(record);
+ }
+ }
+ }
+ }
+
+ private List<MediaSessionRecord> getActiveSessionsLocked(int userId) {
+ List<MediaSessionRecord> records = new ArrayList<>();
+ if (userId == USER_ALL) {
+ int size = mUserRecords.size();
+ for (int i = 0; i < size; i++) {
+ records.addAll(mUserRecords.valueAt(i).mPriorityStack.getActiveSessions(userId));
+ }
+ } else {
+ FullUserRecord user = getFullUserRecordLocked(userId);
+ if (user == null) {
+ Log.w(TAG, "getSessions failed. Unknown user " + userId);
+ return records;
+ }
+ records.addAll(user.mPriorityStack.getActiveSessions(userId));
+ }
+
+ // Return global priority session at the first whenever it's asked.
+ if (isGlobalPriorityActiveLocked()
+ && (userId == USER_ALL || userId == mGlobalPrioritySession.getUserId())) {
+ records.add(0, mGlobalPrioritySession);
+ }
+ return records;
+ }
+
+ List<Session2Token> getSession2TokensLocked(int userId) {
+ List<Session2Token> list = new ArrayList<>();
+ if (userId == USER_ALL) {
+ for (int i = 0; i < mSession2TokensPerUser.size(); i++) {
+ list.addAll(mSession2TokensPerUser.valueAt(i));
+ }
+ } else {
+ list.addAll(mSession2TokensPerUser.get(userId));
+ }
+ return list;
+ }
+
+ /**
+ * Tells the System UI and Settings app that volume has changed on an active remote session.
+ */
+ public void notifyRemoteVolumeChanged(int flags, MediaSessionRecord session) {
+ if (!session.isActive()) {
+ return;
+ }
+ synchronized (mLock) {
+ int size = mRemoteVolumeControllers.beginBroadcast();
+ MediaSession.Token token = session.getSessionToken();
+ for (int i = size - 1; i >= 0; i--) {
+ try {
+ IRemoteVolumeController cb = mRemoteVolumeControllers.getBroadcastItem(i);
+ cb.remoteVolumeChanged(token, flags);
+ } catch (Exception e) {
+ Log.w(TAG, "Error sending volume change.", e);
+ }
+ }
+ mRemoteVolumeControllers.finishBroadcast();
+ }
+ }
+
+ void onSessionPlaystateChanged(MediaSessionRecord record, int oldState, int newState) {
+ synchronized (mLock) {
+ FullUserRecord user = getFullUserRecordLocked(record.getUserId());
+ if (user == null || !user.mPriorityStack.contains(record)) {
+ Log.d(TAG, "Unknown session changed playback state. Ignoring.");
+ return;
+ }
+ user.mPriorityStack.onPlaystateChanged(record, oldState, newState);
+ }
+ }
- mImpl.onStart();
+ void onSessionPlaybackTypeChanged(MediaSessionRecord record) {
+ synchronized (mLock) {
+ FullUserRecord user = getFullUserRecordLocked(record.getUserId());
+ if (user == null || !user.mPriorityStack.contains(record)) {
+ Log.d(TAG, "Unknown session changed playback type. Ignoring.");
+ return;
+ }
+ pushRemoteVolumeUpdateLocked(record.getUserId());
+ }
}
@Override
public void onStartUser(int userId) {
- mImpl.onStartUser(userId);
+ if (DEBUG) Log.d(TAG, "onStartUser: " + userId);
+ updateUser();
}
@Override
public void onSwitchUser(int userId) {
- mImpl.onSwitchUser(userId);
+ if (DEBUG) Log.d(TAG, "onSwitchUser: " + userId);
+ updateUser();
}
// Called when the user with the userId is removed.
@Override
public void onStopUser(int userId) {
- mImpl.onStopUser(userId);
+ if (DEBUG) Log.d(TAG, "onStopUser: " + userId);
+ synchronized (mLock) {
+ // TODO: Also handle removing user in updateUser() because adding/switching user is
+ // handled in updateUser().
+ FullUserRecord user = getFullUserRecordLocked(userId);
+ if (user != null) {
+ if (user.mFullUserId == userId) {
+ user.destroySessionsForUserLocked(USER_ALL);
+ mUserRecords.remove(userId);
+ } else {
+ user.destroySessionsForUserLocked(userId);
+ }
+ }
+ mSession2TokensPerUser.remove(userId);
+ updateUser();
+ }
}
@Override
public void monitor() {
- mImpl.monitor();
+ synchronized (mLock) {
+ // Check for deadlock
+ }
}
- /**
- * Updates session.
- */
- public void updateSession(MediaSessionRecord record) {
- mImpl.updateSession(record);
+ protected void enforcePhoneStatePermission(int pid, int uid) {
+ if (mContext.checkPermission(android.Manifest.permission.MODIFY_PHONE_STATE, pid, uid)
+ != PackageManager.PERMISSION_GRANTED) {
+ throw new SecurityException("Must hold the MODIFY_PHONE_STATE permission.");
+ }
}
- /**
- * Sets global priority session.
+ void sessionDied(MediaSessionRecord session) {
+ synchronized (mLock) {
+ destroySessionLocked(session);
+ }
+ }
+
+ void destroySession(MediaSessionRecord session) {
+ synchronized (mLock) {
+ destroySessionLocked(session);
+ }
+ }
+
+ private void updateUser() {
+ synchronized (mLock) {
+ UserManager manager = (UserManager) mContext.getSystemService(Context.USER_SERVICE);
+ mFullUserIds.clear();
+ List<UserInfo> allUsers = manager.getUsers();
+ if (allUsers != null) {
+ for (UserInfo userInfo : allUsers) {
+ if (userInfo.isManagedProfile()) {
+ mFullUserIds.put(userInfo.id, userInfo.profileGroupId);
+ } else {
+ mFullUserIds.put(userInfo.id, userInfo.id);
+ if (mUserRecords.get(userInfo.id) == null) {
+ mUserRecords.put(userInfo.id, new FullUserRecord(userInfo.id));
+ }
+ }
+ if (mSession2TokensPerUser.get(userInfo.id) == null) {
+ mSession2TokensPerUser.put(userInfo.id, new ArrayList<>());
+ }
+ }
+ }
+ // Ensure that the current full user exists.
+ int currentFullUserId = ActivityManager.getCurrentUser();
+ mCurrentFullUserRecord = mUserRecords.get(currentFullUserId);
+ if (mCurrentFullUserRecord == null) {
+ Log.w(TAG, "Cannot find FullUserInfo for the current user " + currentFullUserId);
+ mCurrentFullUserRecord = new FullUserRecord(currentFullUserId);
+ mUserRecords.put(currentFullUserId, mCurrentFullUserRecord);
+ if (mSession2TokensPerUser.get(currentFullUserId) == null) {
+ mSession2TokensPerUser.put(currentFullUserId, new ArrayList<>());
+ }
+ }
+ mFullUserIds.put(currentFullUserId, currentFullUserId);
+ }
+ }
+
+ private void updateActiveSessionListeners() {
+ synchronized (mLock) {
+ for (int i = mSessionsListeners.size() - 1; i >= 0; i--) {
+ SessionsListenerRecord listener = mSessionsListeners.get(i);
+ try {
+ enforceMediaPermissions(listener.componentName, listener.pid, listener.uid,
+ listener.userId);
+ } catch (SecurityException e) {
+ Log.i(TAG, "ActiveSessionsListener " + listener.componentName
+ + " is no longer authorized. Disconnecting.");
+ mSessionsListeners.remove(i);
+ try {
+ listener.listener
+ .onActiveSessionsChanged(new ArrayList<MediaSession.Token>());
+ } catch (Exception e1) {
+ // ignore
+ }
+ }
+ }
+ }
+ }
+
+ /*
+ * When a session is removed several things need to happen.
+ * 1. We need to remove it from the relevant user.
+ * 2. We need to remove it from the priority stack.
+ * 3. We need to remove it from all sessions.
+ * 4. If this is the system priority session we need to clear it.
+ * 5. We need to unlink to death from the cb binder
+ * 6. We need to tell the session to do any final cleanup (onDestroy)
*/
- public void setGlobalPrioritySession(MediaSessionRecord record) {
- mImpl.setGlobalPrioritySession(record);
+ private void destroySessionLocked(MediaSessionRecord session) {
+ if (DEBUG) {
+ Log.d(TAG, "Destroying " + session);
+ }
+ FullUserRecord user = getFullUserRecordLocked(session.getUserId());
+ if (mGlobalPrioritySession == session) {
+ mGlobalPrioritySession = null;
+ if (session.isActive() && user != null) {
+ user.pushAddressedPlayerChangedLocked();
+ }
+ } else {
+ if (user != null) {
+ user.mPriorityStack.removeSession(session);
+ }
+ }
+
+ try {
+ session.getCallback().asBinder().unlinkToDeath(session, 0);
+ } catch (Exception e) {
+ // ignore exceptions while destroying a session.
+ }
+ session.onDestroy();
+ mHandler.postSessionsChanged(session.getUserId());
}
- List<Session2Token> getSession2TokensLocked(int userId) {
- return mImpl.getSession2TokensLocked(userId);
+ private void enforcePackageName(String packageName, int uid) {
+ if (TextUtils.isEmpty(packageName)) {
+ throw new IllegalArgumentException("packageName may not be empty");
+ }
+ String[] packages = mContext.getPackageManager().getPackagesForUid(uid);
+ final int packageCount = packages.length;
+ for (int i = 0; i < packageCount; i++) {
+ if (packageName.equals(packages[i])) {
+ return;
+ }
+ }
+ throw new IllegalArgumentException("packageName is not owned by the calling process");
}
/**
- * Tells the system UI that volume has changed on an active remote session.
+ * Checks a caller's authorization to register an IRemoteControlDisplay.
+ * Authorization is granted if one of the following is true:
+ * <ul>
+ * <li>the caller has android.Manifest.permission.MEDIA_CONTENT_CONTROL
+ * permission</li>
+ * <li>the caller's listener is one of the enabled notification listeners
+ * for the caller's user</li>
+ * </ul>
*/
- public void notifyRemoteVolumeChanged(int flags, MediaSessionRecord session) {
- mImpl.notifyRemoteVolumeChanged(flags, session);
+ private void enforceMediaPermissions(ComponentName compName, int pid, int uid,
+ int resolvedUserId) {
+ if (hasStatusBarServicePermission(pid, uid)) return;
+ if (mContext
+ .checkPermission(android.Manifest.permission.MEDIA_CONTENT_CONTROL, pid, uid)
+ != PackageManager.PERMISSION_GRANTED
+ && !isEnabledNotificationListener(compName, UserHandle.getUserId(uid),
+ resolvedUserId)) {
+ throw new SecurityException("Missing permission to control media.");
+ }
+ }
+
+ private boolean hasStatusBarServicePermission(int pid, int uid) {
+ return mContext.checkPermission(android.Manifest.permission.STATUS_BAR_SERVICE,
+ pid, uid) == PackageManager.PERMISSION_GRANTED;
+ }
+
+ private void enforceStatusBarServicePermission(String action, int pid, int uid) {
+ if (!hasStatusBarServicePermission(pid, uid)) {
+ throw new SecurityException("Only System UI and Settings may " + action);
+ }
}
/**
- * Called when session playstate is changed.
+ * This checks if the component is an enabled notification listener for the
+ * specified user. Enabled components may only operate on behalf of the user
+ * they're running as.
+ *
+ * @param compName The component that is enabled.
+ * @param userId The user id of the caller.
+ * @param forUserId The user id they're making the request on behalf of.
+ * @return True if the component is enabled, false otherwise
*/
- public void onSessionPlaystateChanged(MediaSessionRecord record, int oldState, int newState) {
- mImpl.onSessionPlaystateChanged(record, oldState, newState);
+ private boolean isEnabledNotificationListener(ComponentName compName, int userId,
+ int forUserId) {
+ if (userId != forUserId) {
+ // You may not access another user's content as an enabled listener.
+ return false;
+ }
+ if (DEBUG) {
+ Log.d(TAG, "Checking if enabled notification listener " + compName);
+ }
+ if (compName != null) {
+ try {
+ return mNotificationManager.isNotificationListenerAccessGrantedForUser(
+ compName, userId);
+ } catch (RemoteException e) {
+ Log.w(TAG, "Dead NotificationManager in isEnabledNotificationListener", e);
+ }
+ }
+ return false;
}
- /**
- * Called when session playback type is changed.
+ private MediaSessionRecord createSessionInternal(int callerPid, int callerUid, int userId,
+ String callerPackageName, ISessionCallback cb, String tag, Bundle sessionInfo)
+ throws RemoteException {
+ synchronized (mLock) {
+ return createSessionLocked(callerPid, callerUid, userId, callerPackageName, cb,
+ tag, sessionInfo);
+ }
+ }
+
+ /*
+ * When a session is created the following things need to happen.
+ * 1. Its callback binder needs a link to death
+ * 2. It needs to be added to all sessions.
+ * 3. It needs to be added to the priority stack.
+ * 4. It needs to be added to the relevant user record.
*/
- public void onSessionPlaybackTypeChanged(MediaSessionRecord record) {
- mImpl.onSessionPlaybackTypeChanged(record);
+ private MediaSessionRecord createSessionLocked(int callerPid, int callerUid, int userId,
+ String callerPackageName, ISessionCallback cb, String tag, Bundle sessionInfo) {
+ FullUserRecord user = getFullUserRecordLocked(userId);
+ if (user == null) {
+ Log.w(TAG, "Request from invalid user: " + userId + ", pkg=" + callerPackageName);
+ throw new RuntimeException("Session request from invalid user.");
+ }
+
+ final MediaSessionRecord session = new MediaSessionRecord(callerPid, callerUid, userId,
+ callerPackageName, cb, tag, sessionInfo, this, mHandler.getLooper());
+ try {
+ cb.asBinder().linkToDeath(session, 0);
+ } catch (RemoteException e) {
+ throw new RuntimeException("Media Session owner died prematurely.", e);
+ }
+
+ user.mPriorityStack.addSession(session);
+ mHandler.postSessionsChanged(userId);
+
+ if (DEBUG) {
+ Log.d(TAG, "Created session for " + callerPackageName + " with tag " + tag);
+ }
+ return session;
}
- protected void enforcePhoneStatePermission(int pid, int uid) {
- mImpl.enforcePhoneStatePermission(pid, uid);
+ private int findIndexOfSessionsListenerLocked(IActiveSessionsListener listener) {
+ for (int i = mSessionsListeners.size() - 1; i >= 0; i--) {
+ if (mSessionsListeners.get(i).listener.asBinder() == listener.asBinder()) {
+ return i;
+ }
+ }
+ return -1;
}
- void sessionDied(MediaSessionRecord session) {
- mImpl.sessionDied(session);
+ private int findIndexOfSession2TokensListenerLocked(ISession2TokensListener listener) {
+ for (int i = mSession2TokensListenerRecords.size() - 1; i >= 0; i--) {
+ if (mSession2TokensListenerRecords.get(i).listener.asBinder() == listener.asBinder()) {
+ return i;
+ }
+ }
+ return -1;
}
- void destroySession(MediaSessionRecord session) {
- mImpl.destroySession(session);
+ private void pushSessionsChanged(int userId) {
+ synchronized (mLock) {
+ FullUserRecord user = getFullUserRecordLocked(userId);
+ if (user == null) {
+ Log.w(TAG, "pushSessionsChanged failed. No user with id=" + userId);
+ return;
+ }
+ List<MediaSessionRecord> records = getActiveSessionsLocked(userId);
+ int size = records.size();
+ ArrayList<MediaSession.Token> tokens = new ArrayList<MediaSession.Token>();
+ for (int i = 0; i < size; i++) {
+ tokens.add(records.get(i).getSessionToken());
+ }
+ pushRemoteVolumeUpdateLocked(userId);
+ for (int i = mSessionsListeners.size() - 1; i >= 0; i--) {
+ SessionsListenerRecord record = mSessionsListeners.get(i);
+ if (record.userId == USER_ALL || record.userId == userId) {
+ try {
+ record.listener.onActiveSessionsChanged(tokens);
+ } catch (RemoteException e) {
+ Log.w(TAG, "Dead ActiveSessionsListener in pushSessionsChanged, removing",
+ e);
+ mSessionsListeners.remove(i);
+ }
+ }
+ }
+ }
+ }
+
+ private void pushRemoteVolumeUpdateLocked(int userId) {
+ FullUserRecord user = getFullUserRecordLocked(userId);
+ if (user == null) {
+ Log.w(TAG, "pushRemoteVolumeUpdateLocked failed. No user with id=" + userId);
+ return;
+ }
+
+ synchronized (mLock) {
+ int size = mRemoteVolumeControllers.beginBroadcast();
+ MediaSessionRecord record = user.mPriorityStack.getDefaultRemoteSession(userId);
+ MediaSession.Token token = record == null ? null : record.getSessionToken();
+
+ for (int i = size - 1; i >= 0; i--) {
+ try {
+ IRemoteVolumeController cb = mRemoteVolumeControllers.getBroadcastItem(i);
+ cb.updateRemoteController(token);
+ } catch (Exception e) {
+ Log.w(TAG, "Error sending default remote volume.", e);
+ }
+ }
+ mRemoteVolumeControllers.finishBroadcast();
+ }
}
void pushSession2TokensChangedLocked(int userId) {
- mImpl.pushSession2TokensChangedLocked(userId);
+ List<Session2Token> allSession2Tokens = getSession2TokensLocked(USER_ALL);
+ List<Session2Token> session2Tokens = getSession2TokensLocked(userId);
+
+ for (int i = mSession2TokensListenerRecords.size() - 1; i >= 0; i--) {
+ Session2TokensListenerRecord listenerRecord = mSession2TokensListenerRecords.get(i);
+ try {
+ if (listenerRecord.userId == USER_ALL) {
+ listenerRecord.listener.onSession2TokensChanged(allSession2Tokens);
+ } else if (listenerRecord.userId == userId) {
+ listenerRecord.listener.onSession2TokensChanged(session2Tokens);
+ }
+ } catch (RemoteException e) {
+ Log.w(TAG, "Failed to notify Session2Token change. Removing listener.", e);
+ mSession2TokensListenerRecords.remove(i);
+ }
+ }
}
/**
- * Called when media button receiver changed.
+ * Called when the media button receiver for the {@code record} is changed.
+ *
+ * @param record the media session whose media button receiver is updated.
*/
public void onMediaButtonReceiverChanged(MediaSessionRecord record) {
- mImpl.onMediaButtonReceiverChanged(record);
- }
-
- abstract static class ServiceImpl {
- public abstract void onStart();
- public abstract void notifyRemoteVolumeChanged(int flags, MediaSessionRecord session);
- public abstract void onSessionPlaystateChanged(
- MediaSessionRecord record, int oldState, int newState);
- public abstract void onSessionPlaybackTypeChanged(MediaSessionRecord record);
- public abstract void onStartUser(int userId);
- public abstract void onSwitchUser(int userId);
- public abstract void monitor();
- public abstract void onMediaButtonReceiverChanged(MediaSessionRecord record);
- protected abstract void enforcePhoneStatePermission(int pid, int uid);
- abstract void updateSession(MediaSessionRecord record);
- abstract void setGlobalPrioritySession(MediaSessionRecord record);
- abstract List<Session2Token> getSession2TokensLocked(int userId);
- abstract void onStopUser(int userId);
- abstract void sessionDied(MediaSessionRecord session);
- abstract void destroySession(MediaSessionRecord session);
- abstract void pushSession2TokensChangedLocked(int userId);
- abstract Context getContext();
- abstract IBinder getServiceBinder();
+ synchronized (mLock) {
+ FullUserRecord user = getFullUserRecordLocked(record.getUserId());
+ MediaSessionRecord mediaButtonSession =
+ user.mPriorityStack.getMediaButtonSession();
+ if (record == mediaButtonSession) {
+ user.rememberMediaButtonReceiverLocked(mediaButtonSession);
+ }
+ }
+ }
+
+ private String getCallingPackageName(int uid) {
+ String[] packages = mContext.getPackageManager().getPackagesForUid(uid);
+ if (packages != null && packages.length > 0) {
+ return packages[0];
+ }
+ return "";
+ }
+
+ private void dispatchVolumeKeyLongPressLocked(KeyEvent keyEvent) {
+ if (mCurrentFullUserRecord.mOnVolumeKeyLongPressListener == null) {
+ return;
+ }
+ try {
+ mCurrentFullUserRecord.mOnVolumeKeyLongPressListener.onVolumeKeyLongPress(keyEvent);
+ } catch (RemoteException e) {
+ Log.w(TAG, "Failed to send " + keyEvent + " to volume key long-press listener");
+ }
+ }
+
+ private FullUserRecord getFullUserRecordLocked(int userId) {
+ int fullUserId = mFullUserIds.get(userId, -1);
+ if (fullUserId < 0) {
+ return null;
+ }
+ return mUserRecords.get(fullUserId);
+ }
+
+ private MediaSessionRecord getMediaSessionRecordLocked(MediaSession.Token sessionToken) {
+ FullUserRecord user = getFullUserRecordLocked(UserHandle.getUserId(sessionToken.getUid()));
+ if (user != null) {
+ return user.mPriorityStack.getMediaSessionRecord(sessionToken);
+ }
+ return null;
+ }
+
+ /**
+ * Information about a full user and its corresponding managed profiles.
+ *
+ * <p>Since the full user runs together with its managed profiles, a user wouldn't differentiate
+ * them when he/she presses a media/volume button. So keeping media sessions for them in one
+ * place makes more sense and increases the readability.</p>
+ * <p>The contents of this object is guarded by {@link #mLock}.
+ */
+ final class FullUserRecord implements MediaSessionStack.OnMediaButtonSessionChangedListener {
+ public static final int COMPONENT_TYPE_INVALID = 0;
+ public static final int COMPONENT_TYPE_BROADCAST = 1;
+ public static final int COMPONENT_TYPE_ACTIVITY = 2;
+ public static final int COMPONENT_TYPE_SERVICE = 3;
+ private static final String COMPONENT_NAME_USER_ID_DELIM = ",";
+
+ private final int mFullUserId;
+ private final MediaSessionStack mPriorityStack;
+ private PendingIntent mLastMediaButtonReceiver;
+ private ComponentName mRestoredMediaButtonReceiver;
+ private int mRestoredMediaButtonReceiverComponentType;
+ private int mRestoredMediaButtonReceiverUserId;
+
+ private IOnVolumeKeyLongPressListener mOnVolumeKeyLongPressListener;
+ private int mOnVolumeKeyLongPressListenerUid;
+ private KeyEvent mInitialDownVolumeKeyEvent;
+ private int mInitialDownVolumeStream;
+ private boolean mInitialDownMusicOnly;
+
+ private IOnMediaKeyListener mOnMediaKeyListener;
+ private int mOnMediaKeyListenerUid;
+ private ICallback mCallback;
+
+ FullUserRecord(int fullUserId) {
+ mFullUserId = fullUserId;
+ mPriorityStack = new MediaSessionStack(mAudioPlayerStateMonitor, this);
+ // Restore the remembered media button receiver before the boot.
+ String mediaButtonReceiverInfo = Settings.Secure.getStringForUser(mContentResolver,
+ Settings.System.MEDIA_BUTTON_RECEIVER, mFullUserId);
+ if (mediaButtonReceiverInfo == null) {
+ return;
+ }
+ String[] tokens = mediaButtonReceiverInfo.split(COMPONENT_NAME_USER_ID_DELIM);
+ if (tokens == null || (tokens.length != 2 && tokens.length != 3)) {
+ return;
+ }
+ mRestoredMediaButtonReceiver = ComponentName.unflattenFromString(tokens[0]);
+ mRestoredMediaButtonReceiverUserId = Integer.parseInt(tokens[1]);
+ if (tokens.length == 3) {
+ mRestoredMediaButtonReceiverComponentType = Integer.parseInt(tokens[2]);
+ } else {
+ mRestoredMediaButtonReceiverComponentType =
+ getComponentType(mRestoredMediaButtonReceiver);
+ }
+ }
+
+ public void destroySessionsForUserLocked(int userId) {
+ List<MediaSessionRecord> sessions = mPriorityStack.getPriorityList(false, userId);
+ for (MediaSessionRecord session : sessions) {
+ destroySessionLocked(session);
+ }
+ }
+
+ public void dumpLocked(PrintWriter pw, String prefix) {
+ pw.print(prefix + "Record for full_user=" + mFullUserId);
+ // Dump managed profile user ids associated with this user.
+ int size = mFullUserIds.size();
+ for (int i = 0; i < size; i++) {
+ if (mFullUserIds.keyAt(i) != mFullUserIds.valueAt(i)
+ && mFullUserIds.valueAt(i) == mFullUserId) {
+ pw.print(", profile_user=" + mFullUserIds.keyAt(i));
+ }
+ }
+ pw.println();
+ String indent = prefix + " ";
+ pw.println(indent + "Volume key long-press listener: " + mOnVolumeKeyLongPressListener);
+ pw.println(indent + "Volume key long-press listener package: "
+ + getCallingPackageName(mOnVolumeKeyLongPressListenerUid));
+ pw.println(indent + "Media key listener: " + mOnMediaKeyListener);
+ pw.println(indent + "Media key listener package: "
+ + getCallingPackageName(mOnMediaKeyListenerUid));
+ pw.println(indent + "Callback: " + mCallback);
+ pw.println(indent + "Last MediaButtonReceiver: " + mLastMediaButtonReceiver);
+ pw.println(indent + "Restored MediaButtonReceiver: " + mRestoredMediaButtonReceiver);
+ pw.println(indent + "Restored MediaButtonReceiverComponentType: "
+ + mRestoredMediaButtonReceiverComponentType);
+ mPriorityStack.dump(pw, indent);
+ pw.println(indent + "Session2Tokens:");
+ for (int i = 0; i < mSession2TokensPerUser.size(); i++) {
+ List<Session2Token> list = mSession2TokensPerUser.valueAt(i);
+ if (list == null || list.size() == 0) {
+ continue;
+ }
+ for (Session2Token token : list) {
+ pw.println(indent + " " + token);
+ }
+ }
+ }
+
+ @Override
+ public void onMediaButtonSessionChanged(MediaSessionRecord oldMediaButtonSession,
+ MediaSessionRecord newMediaButtonSession) {
+ if (DEBUG_KEY_EVENT) {
+ Log.d(TAG, "Media button session is changed to " + newMediaButtonSession);
+ }
+ synchronized (mLock) {
+ if (oldMediaButtonSession != null) {
+ mHandler.postSessionsChanged(oldMediaButtonSession.getUserId());
+ }
+ if (newMediaButtonSession != null) {
+ rememberMediaButtonReceiverLocked(newMediaButtonSession);
+ mHandler.postSessionsChanged(newMediaButtonSession.getUserId());
+ }
+ pushAddressedPlayerChangedLocked();
+ }
+ }
+
+ // Remember media button receiver and keep it in the persistent storage.
+ public void rememberMediaButtonReceiverLocked(MediaSessionRecord record) {
+ PendingIntent receiver = record.getMediaButtonReceiver();
+ mLastMediaButtonReceiver = receiver;
+ mRestoredMediaButtonReceiver = null;
+ mRestoredMediaButtonReceiverComponentType = COMPONENT_TYPE_INVALID;
+
+ String mediaButtonReceiverInfo = "";
+ if (receiver != null) {
+ ComponentName component = receiver.getIntent().getComponent();
+ if (component != null
+ && record.getPackageName().equals(component.getPackageName())) {
+ String componentName = component.flattenToString();
+ int componentType = getComponentType(component);
+ mediaButtonReceiverInfo = String.join(COMPONENT_NAME_USER_ID_DELIM,
+ componentName, String.valueOf(record.getUserId()),
+ String.valueOf(componentType));
+ }
+ }
+ Settings.Secure.putStringForUser(mContentResolver,
+ Settings.System.MEDIA_BUTTON_RECEIVER, mediaButtonReceiverInfo,
+ mFullUserId);
+ }
+
+ private void pushAddressedPlayerChangedLocked() {
+ if (mCallback == null) {
+ return;
+ }
+ try {
+ MediaSessionRecord mediaButtonSession = getMediaButtonSessionLocked();
+ if (mediaButtonSession != null) {
+ mCallback.onAddressedPlayerChangedToMediaSession(
+ mediaButtonSession.getSessionToken());
+ } else if (mCurrentFullUserRecord.mLastMediaButtonReceiver != null) {
+ mCallback.onAddressedPlayerChangedToMediaButtonReceiver(
+ mCurrentFullUserRecord.mLastMediaButtonReceiver
+ .getIntent().getComponent());
+ } else if (mCurrentFullUserRecord.mRestoredMediaButtonReceiver != null) {
+ mCallback.onAddressedPlayerChangedToMediaButtonReceiver(
+ mCurrentFullUserRecord.mRestoredMediaButtonReceiver);
+ }
+ } catch (RemoteException e) {
+ Log.w(TAG, "Failed to pushAddressedPlayerChangedLocked", e);
+ }
+ }
+
+ private MediaSessionRecord getMediaButtonSessionLocked() {
+ return isGlobalPriorityActiveLocked()
+ ? mGlobalPrioritySession : mPriorityStack.getMediaButtonSession();
+ }
+
+ private int getComponentType(@Nullable ComponentName componentName) {
+ if (componentName == null) {
+ return COMPONENT_TYPE_INVALID;
+ }
+ PackageManager pm = mContext.getPackageManager();
+ try {
+ ActivityInfo activityInfo = pm.getActivityInfo(componentName,
+ PackageManager.MATCH_DIRECT_BOOT_AWARE
+ | PackageManager.MATCH_DIRECT_BOOT_UNAWARE
+ | PackageManager.GET_ACTIVITIES);
+ if (activityInfo != null) {
+ return COMPONENT_TYPE_ACTIVITY;
+ }
+ } catch (NameNotFoundException e) {
+ }
+ try {
+ ServiceInfo serviceInfo = pm.getServiceInfo(componentName,
+ PackageManager.MATCH_DIRECT_BOOT_AWARE
+ | PackageManager.MATCH_DIRECT_BOOT_UNAWARE
+ | PackageManager.GET_SERVICES);
+ if (serviceInfo != null) {
+ return COMPONENT_TYPE_SERVICE;
+ }
+ } catch (NameNotFoundException e) {
+ }
+ // Pick legacy behavior for BroadcastReceiver or unknown.
+ return COMPONENT_TYPE_BROADCAST;
+ }
+ }
+
+ final class SessionsListenerRecord implements IBinder.DeathRecipient {
+ public final IActiveSessionsListener listener;
+ public final ComponentName componentName;
+ public final int userId;
+ public final int pid;
+ public final int uid;
+
+ SessionsListenerRecord(IActiveSessionsListener listener,
+ ComponentName componentName,
+ int userId, int pid, int uid) {
+ this.listener = listener;
+ this.componentName = componentName;
+ this.userId = userId;
+ this.pid = pid;
+ this.uid = uid;
+ }
+
+ @Override
+ public void binderDied() {
+ synchronized (mLock) {
+ mSessionsListeners.remove(this);
+ }
+ }
+ }
+
+ final class Session2TokensListenerRecord implements IBinder.DeathRecipient {
+ public final ISession2TokensListener listener;
+ public final int userId;
+
+ Session2TokensListenerRecord(ISession2TokensListener listener,
+ int userId) {
+ this.listener = listener;
+ this.userId = userId;
+ }
+
+ @Override
+ public void binderDied() {
+ synchronized (mLock) {
+ mSession2TokensListenerRecords.remove(this);
+ }
+ }
+ }
+
+ final class SettingsObserver extends ContentObserver {
+ private final Uri mSecureSettingsUri = Settings.Secure.getUriFor(
+ Settings.Secure.ENABLED_NOTIFICATION_LISTENERS);
+
+ private SettingsObserver() {
+ super(null);
+ }
+
+ private void observe() {
+ mContentResolver.registerContentObserver(mSecureSettingsUri,
+ false, this, USER_ALL);
+ }
+
+ @Override
+ public void onChange(boolean selfChange, Uri uri) {
+ updateActiveSessionListeners();
+ }
+ }
+
+ class SessionManagerImpl extends ISessionManager.Stub {
+ private static final String EXTRA_WAKELOCK_ACQUIRED =
+ "android.media.AudioService.WAKELOCK_ACQUIRED";
+ private static final int WAKELOCK_RELEASE_ON_FINISHED = 1980; // magic number
+
+ private boolean mVoiceButtonDown = false;
+ private boolean mVoiceButtonHandled = false;
+
+ @Override
+ public ISession createSession(String packageName, ISessionCallback cb, String tag,
+ Bundle sessionInfo, int userId) throws RemoteException {
+ final int pid = Binder.getCallingPid();
+ final int uid = Binder.getCallingUid();
+ final long token = Binder.clearCallingIdentity();
+ try {
+ enforcePackageName(packageName, uid);
+ int resolvedUserId = ActivityManager.handleIncomingUser(pid, uid, userId,
+ false /* allowAll */, true /* requireFull */, "createSession", packageName);
+ if (cb == null) {
+ throw new IllegalArgumentException("Controller callback cannot be null");
+ }
+ return createSessionInternal(pid, uid, resolvedUserId, packageName, cb, tag,
+ sessionInfo).getSessionBinder();
+ } finally {
+ Binder.restoreCallingIdentity(token);
+ }
+ }
+
+ @Override
+ public void notifySession2Created(Session2Token sessionToken) throws RemoteException {
+ final int pid = Binder.getCallingPid();
+ final int uid = Binder.getCallingUid();
+ final long token = Binder.clearCallingIdentity();
+ try {
+ if (DEBUG) {
+ Log.d(TAG, "Session2 is created " + sessionToken);
+ }
+ if (uid != sessionToken.getUid()) {
+ throw new SecurityException("Unexpected Session2Token's UID, expected=" + uid
+ + " but actually=" + sessionToken.getUid());
+ }
+ Controller2Callback callback = new Controller2Callback(sessionToken);
+ // Note: It's safe not to keep controller here because it wouldn't be GC'ed until
+ // it's closed.
+ // TODO: Keep controller as well for better readability
+ // because the GC behavior isn't straightforward.
+ MediaController2 controller = new MediaController2.Builder(mContext, sessionToken)
+ .setControllerCallback(new HandlerExecutor(mHandler), callback)
+ .build();
+ } finally {
+ Binder.restoreCallingIdentity(token);
+ }
+ }
+
+ @Override
+ public List<MediaSession.Token> getSessions(ComponentName componentName, int userId) {
+ final int pid = Binder.getCallingPid();
+ final int uid = Binder.getCallingUid();
+ final long token = Binder.clearCallingIdentity();
+
+ try {
+ int resolvedUserId = verifySessionsRequest(componentName, userId, pid, uid);
+ ArrayList<MediaSession.Token> tokens = new ArrayList<>();
+ synchronized (mLock) {
+ List<MediaSessionRecord> records = getActiveSessionsLocked(resolvedUserId);
+ for (MediaSessionRecord record : records) {
+ tokens.add(record.getSessionToken());
+ }
+ }
+ return tokens;
+ } finally {
+ Binder.restoreCallingIdentity(token);
+ }
+ }
+
+ @Override
+ public ParceledListSlice getSession2Tokens(int userId) {
+ final int pid = Binder.getCallingPid();
+ final int uid = Binder.getCallingUid();
+ final long token = Binder.clearCallingIdentity();
+
+ try {
+ // Check that they can make calls on behalf of the user and
+ // get the final user id
+ int resolvedUserId = ActivityManager.handleIncomingUser(pid, uid, userId,
+ true /* allowAll */, true /* requireFull */, "getSession2Tokens",
+ null /* optional packageName */);
+ List<Session2Token> result;
+ synchronized (mLock) {
+ result = getSession2TokensLocked(resolvedUserId);
+ }
+ return new ParceledListSlice(result);
+ } finally {
+ Binder.restoreCallingIdentity(token);
+ }
+ }
+
+ @Override
+ public void addSessionsListener(IActiveSessionsListener listener,
+ ComponentName componentName, int userId) throws RemoteException {
+ final int pid = Binder.getCallingPid();
+ final int uid = Binder.getCallingUid();
+ final long token = Binder.clearCallingIdentity();
+
+ try {
+ int resolvedUserId = verifySessionsRequest(componentName, userId, pid, uid);
+ synchronized (mLock) {
+ int index = findIndexOfSessionsListenerLocked(listener);
+ if (index != -1) {
+ Log.w(TAG, "ActiveSessionsListener is already added, ignoring");
+ return;
+ }
+ SessionsListenerRecord record = new SessionsListenerRecord(listener,
+ componentName, resolvedUserId, pid, uid);
+ try {
+ listener.asBinder().linkToDeath(record, 0);
+ } catch (RemoteException e) {
+ Log.e(TAG, "ActiveSessionsListener is dead, ignoring it", e);
+ return;
+ }
+ mSessionsListeners.add(record);
+ }
+ } finally {
+ Binder.restoreCallingIdentity(token);
+ }
+ }
+
+ @Override
+ public void removeSessionsListener(IActiveSessionsListener listener)
+ throws RemoteException {
+ synchronized (mLock) {
+ int index = findIndexOfSessionsListenerLocked(listener);
+ if (index != -1) {
+ SessionsListenerRecord record = mSessionsListeners.remove(index);
+ try {
+ record.listener.asBinder().unlinkToDeath(record, 0);
+ } catch (Exception e) {
+ // ignore exceptions, the record is being removed
+ }
+ }
+ }
+ }
+
+ @Override
+ public void addSession2TokensListener(ISession2TokensListener listener,
+ int userId) {
+ final int pid = Binder.getCallingPid();
+ final int uid = Binder.getCallingUid();
+ final long token = Binder.clearCallingIdentity();
+
+ try {
+ // Check that they can make calls on behalf of the user and get the final user id.
+ int resolvedUserId = ActivityManager.handleIncomingUser(pid, uid, userId,
+ true /* allowAll */, true /* requireFull */, "addSession2TokensListener",
+ null /* optional packageName */);
+ synchronized (mLock) {
+ int index = findIndexOfSession2TokensListenerLocked(listener);
+ if (index >= 0) {
+ Log.w(TAG, "addSession2TokensListener is already added, ignoring");
+ return;
+ }
+ mSession2TokensListenerRecords.add(
+ new Session2TokensListenerRecord(listener, resolvedUserId));
+ }
+ } finally {
+ Binder.restoreCallingIdentity(token);
+ }
+ }
+
+ @Override
+ public void removeSession2TokensListener(ISession2TokensListener listener) {
+ final int pid = Binder.getCallingPid();
+ final int uid = Binder.getCallingUid();
+ final long token = Binder.clearCallingIdentity();
+
+ try {
+ synchronized (mLock) {
+ int index = findIndexOfSession2TokensListenerLocked(listener);
+ if (index >= 0) {
+ Session2TokensListenerRecord listenerRecord =
+ mSession2TokensListenerRecords.remove(index);
+ try {
+ listenerRecord.listener.asBinder().unlinkToDeath(listenerRecord, 0);
+ } catch (Exception e) {
+ // Ignore exception.
+ }
+ }
+ }
+ } finally {
+ Binder.restoreCallingIdentity(token);
+ }
+ }
+
+ /**
+ * Handles the dispatching of the media button events to one of the
+ * registered listeners, or if there was none, broadcast an
+ * ACTION_MEDIA_BUTTON intent to the rest of the system.
+ *
+ * @param packageName The caller package
+ * @param asSystemService {@code true} if the event sent to the session as if it was come
+ * from the system service instead of the app process. This helps sessions to
+ * distinguish between the key injection by the app and key events from the
+ * hardware devices. Should be used only when the volume key events aren't handled
+ * by foreground activity. {@code false} otherwise to tell session about the real
+ * caller.
+ * @param keyEvent a non-null KeyEvent whose key code is one of the
+ * supported media buttons
+ * @param needWakeLock true if a PARTIAL_WAKE_LOCK needs to be held
+ * while this key event is dispatched.
+ */
+ @Override
+ public void dispatchMediaKeyEvent(String packageName, boolean asSystemService,
+ KeyEvent keyEvent, boolean needWakeLock) {
+ if (keyEvent == null || !KeyEvent.isMediaSessionKey(keyEvent.getKeyCode())) {
+ Log.w(TAG, "Attempted to dispatch null or non-media key event.");
+ return;
+ }
+
+ final int pid = Binder.getCallingPid();
+ final int uid = Binder.getCallingUid();
+ final long token = Binder.clearCallingIdentity();
+ try {
+ if (DEBUG) {
+ Log.d(TAG, "dispatchMediaKeyEvent, pkg=" + packageName + " pid=" + pid
+ + ", uid=" + uid + ", asSystem=" + asSystemService + ", event="
+ + keyEvent);
+ }
+ if (!isUserSetupComplete()) {
+ // Global media key handling can have the side-effect of starting new
+ // activities which is undesirable while setup is in progress.
+ Slog.i(TAG, "Not dispatching media key event because user "
+ + "setup is in progress.");
+ return;
+ }
+
+ synchronized (mLock) {
+ boolean isGlobalPriorityActive = isGlobalPriorityActiveLocked();
+ if (isGlobalPriorityActive && uid != Process.SYSTEM_UID) {
+ // Prevent dispatching key event through reflection while the global
+ // priority session is active.
+ Slog.i(TAG, "Only the system can dispatch media key event "
+ + "to the global priority session.");
+ return;
+ }
+ if (!isGlobalPriorityActive) {
+ if (mCurrentFullUserRecord.mOnMediaKeyListener != null) {
+ if (DEBUG_KEY_EVENT) {
+ Log.d(TAG, "Send " + keyEvent + " to the media key listener");
+ }
+ try {
+ mCurrentFullUserRecord.mOnMediaKeyListener.onMediaKey(keyEvent,
+ new MediaKeyListenerResultReceiver(packageName, pid, uid,
+ asSystemService, keyEvent, needWakeLock));
+ return;
+ } catch (RemoteException e) {
+ Log.w(TAG, "Failed to send " + keyEvent
+ + " to the media key listener");
+ }
+ }
+ }
+ if (!isGlobalPriorityActive && isVoiceKey(keyEvent.getKeyCode())) {
+ handleVoiceKeyEventLocked(packageName, pid, uid, asSystemService, keyEvent,
+ needWakeLock);
+ } else {
+ dispatchMediaKeyEventLocked(packageName, pid, uid, asSystemService,
+ keyEvent, needWakeLock);
+ }
+ }
+ } finally {
+ Binder.restoreCallingIdentity(token);
+ }
+ }
+
+ @Override
+ public boolean dispatchMediaKeyEventToSessionAsSystemService(String packageName,
+ MediaSession.Token sessionToken, KeyEvent keyEvent) {
+ final int pid = Binder.getCallingPid();
+ final int uid = Binder.getCallingUid();
+ final long token = Binder.clearCallingIdentity();
+ try {
+ synchronized (mLock) {
+ MediaSessionRecord record = getMediaSessionRecordLocked(sessionToken);
+ if (record == null) {
+ if (DEBUG) {
+ Log.d(TAG, "Failed to find session to dispatch key event.");
+ }
+ return false;
+ }
+ if (DEBUG) {
+ Log.d(TAG, "dispatchMediaKeyEventToSessionAsSystemService, pkg="
+ + packageName + ", pid=" + pid + ", uid=" + uid + ", sessionToken="
+ + sessionToken + ", event=" + keyEvent + ", session=" + record);
+ }
+ return record.sendMediaButton(packageName, pid, uid, true /* asSystemService */,
+ keyEvent, 0, null);
+ }
+ } finally {
+ Binder.restoreCallingIdentity(token);
+ }
+ }
+
+ @Override
+ public void setCallback(ICallback callback) {
+ final int pid = Binder.getCallingPid();
+ final int uid = Binder.getCallingUid();
+ final long token = Binder.clearCallingIdentity();
+ try {
+ if (!UserHandle.isSameApp(uid, Process.BLUETOOTH_UID)) {
+ throw new SecurityException("Only Bluetooth service processes can set"
+ + " Callback");
+ }
+ synchronized (mLock) {
+ int userId = UserHandle.getUserId(uid);
+ FullUserRecord user = getFullUserRecordLocked(userId);
+ if (user == null || user.mFullUserId != userId) {
+ Log.w(TAG, "Only the full user can set the callback"
+ + ", userId=" + userId);
+ return;
+ }
+ user.mCallback = callback;
+ Log.d(TAG, "The callback " + user.mCallback
+ + " is set by " + getCallingPackageName(uid));
+ if (user.mCallback == null) {
+ return;
+ }
+ try {
+ user.mCallback.asBinder().linkToDeath(
+ new IBinder.DeathRecipient() {
+ @Override
+ public void binderDied() {
+ synchronized (mLock) {
+ user.mCallback = null;
+ }
+ }
+ }, 0);
+ user.pushAddressedPlayerChangedLocked();
+ } catch (RemoteException e) {
+ Log.w(TAG, "Failed to set callback", e);
+ user.mCallback = null;
+ }
+ }
+ } finally {
+ Binder.restoreCallingIdentity(token);
+ }
+ }
+
+ @Override
+ public void setOnVolumeKeyLongPressListener(IOnVolumeKeyLongPressListener listener) {
+ final int pid = Binder.getCallingPid();
+ final int uid = Binder.getCallingUid();
+ final long token = Binder.clearCallingIdentity();
+ try {
+ // Enforce SET_VOLUME_KEY_LONG_PRESS_LISTENER permission.
+ if (mContext.checkPermission(
+ android.Manifest.permission.SET_VOLUME_KEY_LONG_PRESS_LISTENER, pid, uid)
+ != PackageManager.PERMISSION_GRANTED) {
+ throw new SecurityException("Must hold the SET_VOLUME_KEY_LONG_PRESS_LISTENER"
+ + " permission.");
+ }
+
+ synchronized (mLock) {
+ int userId = UserHandle.getUserId(uid);
+ FullUserRecord user = getFullUserRecordLocked(userId);
+ if (user == null || user.mFullUserId != userId) {
+ Log.w(TAG, "Only the full user can set the volume key long-press listener"
+ + ", userId=" + userId);
+ return;
+ }
+ if (user.mOnVolumeKeyLongPressListener != null
+ && user.mOnVolumeKeyLongPressListenerUid != uid) {
+ Log.w(TAG, "The volume key long-press listener cannot be reset"
+ + " by another app , mOnVolumeKeyLongPressListener="
+ + user.mOnVolumeKeyLongPressListenerUid
+ + ", uid=" + uid);
+ return;
+ }
+
+ user.mOnVolumeKeyLongPressListener = listener;
+ user.mOnVolumeKeyLongPressListenerUid = uid;
+
+ Log.d(TAG, "The volume key long-press listener "
+ + listener + " is set by " + getCallingPackageName(uid));
+
+ if (user.mOnVolumeKeyLongPressListener != null) {
+ try {
+ user.mOnVolumeKeyLongPressListener.asBinder().linkToDeath(
+ new IBinder.DeathRecipient() {
+ @Override
+ public void binderDied() {
+ synchronized (mLock) {
+ user.mOnVolumeKeyLongPressListener = null;
+ }
+ }
+ }, 0);
+ } catch (RemoteException e) {
+ Log.w(TAG, "Failed to set death recipient "
+ + user.mOnVolumeKeyLongPressListener);
+ user.mOnVolumeKeyLongPressListener = null;
+ }
+ }
+ }
+ } finally {
+ Binder.restoreCallingIdentity(token);
+ }
+ }
+
+ @Override
+ public void setOnMediaKeyListener(IOnMediaKeyListener listener) {
+ final int pid = Binder.getCallingPid();
+ final int uid = Binder.getCallingUid();
+ final long token = Binder.clearCallingIdentity();
+ try {
+ // Enforce SET_MEDIA_KEY_LISTENER permission.
+ if (mContext.checkPermission(
+ android.Manifest.permission.SET_MEDIA_KEY_LISTENER, pid, uid)
+ != PackageManager.PERMISSION_GRANTED) {
+ throw new SecurityException("Must hold the SET_MEDIA_KEY_LISTENER permission.");
+ }
+
+ synchronized (mLock) {
+ int userId = UserHandle.getUserId(uid);
+ FullUserRecord user = getFullUserRecordLocked(userId);
+ if (user == null || user.mFullUserId != userId) {
+ Log.w(TAG, "Only the full user can set the media key listener"
+ + ", userId=" + userId);
+ return;
+ }
+ if (user.mOnMediaKeyListener != null && user.mOnMediaKeyListenerUid != uid) {
+ Log.w(TAG, "The media key listener cannot be reset by another app. "
+ + ", mOnMediaKeyListenerUid=" + user.mOnMediaKeyListenerUid
+ + ", uid=" + uid);
+ return;
+ }
+
+ user.mOnMediaKeyListener = listener;
+ user.mOnMediaKeyListenerUid = uid;
+
+ Log.d(TAG, "The media key listener " + user.mOnMediaKeyListener
+ + " is set by " + getCallingPackageName(uid));
+
+ if (user.mOnMediaKeyListener != null) {
+ try {
+ user.mOnMediaKeyListener.asBinder().linkToDeath(
+ new IBinder.DeathRecipient() {
+ @Override
+ public void binderDied() {
+ synchronized (mLock) {
+ user.mOnMediaKeyListener = null;
+ }
+ }
+ }, 0);
+ } catch (RemoteException e) {
+ Log.w(TAG, "Failed to set death recipient " + user.mOnMediaKeyListener);
+ user.mOnMediaKeyListener = null;
+ }
+ }
+ }
+ } finally {
+ Binder.restoreCallingIdentity(token);
+ }
+ }
+
+ /**
+ * Handles the dispatching of the volume button events to one of the
+ * registered listeners. If there's a volume key long-press listener and
+ * there's no active global priority session, long-pressess will be sent to the
+ * long-press listener instead of adjusting volume.
+ *
+ * @param packageName The caller's package name, obtained by Context#getPackageName()
+ * @param opPackageName The caller's op package name, obtained by Context#getOpPackageName()
+ * @param asSystemService {@code true} if the event sent to the session as if it was come
+ * from the system service instead of the app process. This helps sessions to
+ * distinguish between the key injection by the app and key events from the
+ * hardware devices. Should be used only when the volume key events aren't handled
+ * by foreground activity. {@code false} otherwise to tell session about the real
+ * caller.
+ * @param keyEvent a non-null KeyEvent whose key code is one of the
+ * {@link KeyEvent#KEYCODE_VOLUME_UP},
+ * {@link KeyEvent#KEYCODE_VOLUME_DOWN},
+ * or {@link KeyEvent#KEYCODE_VOLUME_MUTE}.
+ * @param stream stream type to adjust volume.
+ * @param musicOnly true if both UI nor haptic feedback aren't needed when adjust volume.
+ */
+ @Override
+ public void dispatchVolumeKeyEvent(String packageName, String opPackageName,
+ boolean asSystemService, KeyEvent keyEvent, int stream, boolean musicOnly) {
+ if (keyEvent == null
+ || (keyEvent.getKeyCode() != KeyEvent.KEYCODE_VOLUME_UP
+ && keyEvent.getKeyCode() != KeyEvent.KEYCODE_VOLUME_DOWN
+ && keyEvent.getKeyCode() != KeyEvent.KEYCODE_VOLUME_MUTE)) {
+ Log.w(TAG, "Attempted to dispatch null or non-volume key event.");
+ return;
+ }
+
+ final int pid = Binder.getCallingPid();
+ final int uid = Binder.getCallingUid();
+ final long token = Binder.clearCallingIdentity();
+
+ if (DEBUG_KEY_EVENT) {
+ Log.d(TAG, "dispatchVolumeKeyEvent, pkg=" + packageName
+ + ", opPkg=" + opPackageName + ", pid=" + pid + ", uid=" + uid
+ + ", asSystem=" + asSystemService + ", event=" + keyEvent
+ + ", stream=" + stream + ", musicOnly=" + musicOnly);
+ }
+
+ try {
+ synchronized (mLock) {
+ if (isGlobalPriorityActiveLocked()
+ || mCurrentFullUserRecord.mOnVolumeKeyLongPressListener == null) {
+ dispatchVolumeKeyEventLocked(packageName, opPackageName, pid, uid,
+ asSystemService, keyEvent, stream, musicOnly);
+ } else {
+ // TODO: Consider the case when both volume up and down keys are pressed
+ // at the same time.
+ if (keyEvent.getAction() == KeyEvent.ACTION_DOWN) {
+ if (keyEvent.getRepeatCount() == 0) {
+ // Keeps the copy of the KeyEvent because it can be reused.
+ mCurrentFullUserRecord.mInitialDownVolumeKeyEvent =
+ KeyEvent.obtain(keyEvent);
+ mCurrentFullUserRecord.mInitialDownVolumeStream = stream;
+ mCurrentFullUserRecord.mInitialDownMusicOnly = musicOnly;
+ mHandler.sendMessageDelayed(
+ mHandler.obtainMessage(
+ MessageHandler.MSG_VOLUME_INITIAL_DOWN,
+ mCurrentFullUserRecord.mFullUserId, 0),
+ mLongPressTimeout);
+ }
+ if (keyEvent.getRepeatCount() > 0 || keyEvent.isLongPress()) {
+ mHandler.removeMessages(MessageHandler.MSG_VOLUME_INITIAL_DOWN);
+ if (mCurrentFullUserRecord.mInitialDownVolumeKeyEvent != null) {
+ dispatchVolumeKeyLongPressLocked(
+ mCurrentFullUserRecord.mInitialDownVolumeKeyEvent);
+ // Mark that the key is already handled.
+ mCurrentFullUserRecord.mInitialDownVolumeKeyEvent = null;
+ }
+ dispatchVolumeKeyLongPressLocked(keyEvent);
+ }
+ } else { // if up
+ mHandler.removeMessages(MessageHandler.MSG_VOLUME_INITIAL_DOWN);
+ if (mCurrentFullUserRecord.mInitialDownVolumeKeyEvent != null
+ && mCurrentFullUserRecord.mInitialDownVolumeKeyEvent
+ .getDownTime() == keyEvent.getDownTime()) {
+ // Short-press. Should change volume.
+ dispatchVolumeKeyEventLocked(packageName, opPackageName, pid, uid,
+ asSystemService,
+ mCurrentFullUserRecord.mInitialDownVolumeKeyEvent,
+ mCurrentFullUserRecord.mInitialDownVolumeStream,
+ mCurrentFullUserRecord.mInitialDownMusicOnly);
+ dispatchVolumeKeyEventLocked(packageName, opPackageName, pid, uid,
+ asSystemService, keyEvent, stream, musicOnly);
+ } else {
+ dispatchVolumeKeyLongPressLocked(keyEvent);
+ }
+ }
+ }
+ }
+ } finally {
+ Binder.restoreCallingIdentity(token);
+ }
+ }
+
+ private void dispatchVolumeKeyEventLocked(String packageName, String opPackageName, int pid,
+ int uid, boolean asSystemService, KeyEvent keyEvent, int stream,
+ boolean musicOnly) {
+ boolean down = keyEvent.getAction() == KeyEvent.ACTION_DOWN;
+ boolean up = keyEvent.getAction() == KeyEvent.ACTION_UP;
+ int direction = 0;
+ boolean isMute = false;
+ switch (keyEvent.getKeyCode()) {
+ case KeyEvent.KEYCODE_VOLUME_UP:
+ direction = AudioManager.ADJUST_RAISE;
+ break;
+ case KeyEvent.KEYCODE_VOLUME_DOWN:
+ direction = AudioManager.ADJUST_LOWER;
+ break;
+ case KeyEvent.KEYCODE_VOLUME_MUTE:
+ isMute = true;
+ break;
+ }
+ if (down || up) {
+ int flags = AudioManager.FLAG_FROM_KEY;
+ if (musicOnly) {
+ // This flag is used when the screen is off to only affect active media.
+ flags |= AudioManager.FLAG_ACTIVE_MEDIA_ONLY;
+ } else {
+ // These flags are consistent with the home screen
+ if (up) {
+ flags |= AudioManager.FLAG_PLAY_SOUND | AudioManager.FLAG_VIBRATE;
+ } else {
+ flags |= AudioManager.FLAG_SHOW_UI | AudioManager.FLAG_VIBRATE;
+ }
+ }
+ if (direction != 0) {
+ // If this is action up we want to send a beep for non-music events
+ if (up) {
+ direction = 0;
+ }
+ dispatchAdjustVolumeLocked(packageName, opPackageName, pid, uid,
+ asSystemService, stream, direction, flags);
+ } else if (isMute) {
+ if (down && keyEvent.getRepeatCount() == 0) {
+ dispatchAdjustVolumeLocked(packageName, opPackageName, pid, uid,
+ asSystemService, stream, AudioManager.ADJUST_TOGGLE_MUTE, flags);
+ }
+ }
+ }
+ }
+
+ @Override
+ public void dispatchVolumeKeyEventToSessionAsSystemService(String packageName,
+ String opPackageName, MediaSession.Token sessionToken, KeyEvent keyEvent) {
+ int pid = Binder.getCallingPid();
+ int uid = Binder.getCallingUid();
+ final long token = Binder.clearCallingIdentity();
+ try {
+ synchronized (mLock) {
+ MediaSessionRecord record = getMediaSessionRecordLocked(sessionToken);
+ if (record == null) {
+ if (DEBUG) {
+ Log.d(TAG, "Failed to find session to dispatch key event.");
+ }
+ return;
+ }
+ if (DEBUG) {
+ Log.d(TAG, "dispatchVolumeKeyEventToSessionAsSystemService, pkg="
+ + packageName + ", opPkg=" + opPackageName + ", pid=" + pid
+ + ", uid=" + uid + ", sessionToken=" + sessionToken + ", event="
+ + keyEvent + ", session=" + record);
+ }
+ switch (keyEvent.getAction()) {
+ case KeyEvent.ACTION_DOWN: {
+ int direction = 0;
+ switch (keyEvent.getKeyCode()) {
+ case KeyEvent.KEYCODE_VOLUME_UP:
+ direction = AudioManager.ADJUST_RAISE;
+ break;
+ case KeyEvent.KEYCODE_VOLUME_DOWN:
+ direction = AudioManager.ADJUST_LOWER;
+ break;
+ case KeyEvent.KEYCODE_VOLUME_MUTE:
+ direction = AudioManager.ADJUST_TOGGLE_MUTE;
+ break;
+ }
+ record.adjustVolume(packageName, opPackageName, pid, uid,
+ null /* caller */, true /* asSystemService */, direction,
+ AudioManager.FLAG_SHOW_UI, false /* useSuggested */);
+ break;
+ }
+
+ case KeyEvent.ACTION_UP: {
+ final int flags =
+ AudioManager.FLAG_PLAY_SOUND | AudioManager.FLAG_VIBRATE
+ | AudioManager.FLAG_FROM_KEY;
+ record.adjustVolume(packageName, opPackageName, pid, uid,
+ null /* caller */, true /* asSystemService */, 0,
+ flags, false /* useSuggested */);
+ }
+ }
+ }
+ } finally {
+ Binder.restoreCallingIdentity(token);
+ }
+ }
+
+ @Override
+ public void dispatchAdjustVolume(String packageName, String opPackageName,
+ int suggestedStream, int delta, int flags) {
+ final int pid = Binder.getCallingPid();
+ final int uid = Binder.getCallingUid();
+ final long token = Binder.clearCallingIdentity();
+ try {
+ synchronized (mLock) {
+ dispatchAdjustVolumeLocked(packageName, opPackageName, pid, uid, false,
+ suggestedStream, delta, flags);
+ }
+ } finally {
+ Binder.restoreCallingIdentity(token);
+ }
+ }
+
+ @Override
+ public void registerRemoteVolumeController(IRemoteVolumeController rvc) {
+ final int pid = Binder.getCallingPid();
+ final int uid = Binder.getCallingUid();
+ final long token = Binder.clearCallingIdentity();
+ synchronized (mLock) {
+ try {
+ enforceStatusBarServicePermission("listen for volume changes", pid, uid);
+ mRemoteVolumeControllers.register(rvc);
+ } finally {
+ Binder.restoreCallingIdentity(token);
+ }
+ }
+ }
+
+ @Override
+ public void unregisterRemoteVolumeController(IRemoteVolumeController rvc) {
+ final int pid = Binder.getCallingPid();
+ final int uid = Binder.getCallingUid();
+ final long token = Binder.clearCallingIdentity();
+ synchronized (mLock) {
+ try {
+ enforceStatusBarServicePermission("listen for volume changes", pid, uid);
+ mRemoteVolumeControllers.unregister(rvc);
+ } finally {
+ Binder.restoreCallingIdentity(token);
+ }
+ }
+ }
+
+ @Override
+ public boolean isGlobalPriorityActive() {
+ synchronized (mLock) {
+ return isGlobalPriorityActiveLocked();
+ }
+ }
+
+ @Override
+ public void dump(FileDescriptor fd, final PrintWriter pw, String[] args) {
+ if (!DumpUtils.checkDumpPermission(mContext, TAG, pw)) return;
+
+ pw.println("MEDIA SESSION SERVICE (dumpsys media_session)");
+ pw.println();
+
+ synchronized (mLock) {
+ pw.println(mSessionsListeners.size() + " sessions listeners.");
+ pw.println("Global priority session is " + mGlobalPrioritySession);
+ if (mGlobalPrioritySession != null) {
+ mGlobalPrioritySession.dump(pw, " ");
+ }
+ pw.println("User Records:");
+ int count = mUserRecords.size();
+ for (int i = 0; i < count; i++) {
+ mUserRecords.valueAt(i).dumpLocked(pw, "");
+ }
+ mAudioPlayerStateMonitor.dump(mContext, pw, "");
+ }
+ }
+
+ /**
+ * Returns if the controller's package is trusted (i.e. has either MEDIA_CONTENT_CONTROL
+ * permission or an enabled notification listener)
+ *
+ * @param controllerPackageName package name of the controller app
+ * @param controllerPid pid of the controller app
+ * @param controllerUid uid of the controller app
+ */
+ @Override
+ public boolean isTrusted(String controllerPackageName, int controllerPid, int controllerUid)
+ throws RemoteException {
+ final int uid = Binder.getCallingUid();
+ final long token = Binder.clearCallingIdentity();
+ try {
+ // Don't perform sanity check between controllerPackageName and controllerUid.
+ // When an (activity|service) runs on the another apps process by specifying
+ // android:process in the AndroidManifest.xml, then PID and UID would have the
+ // running process' information instead of the (activity|service) that has created
+ // MediaController.
+ // Note that we can use Context#getOpPackageName() instead of
+ // Context#getPackageName() for getting package name that matches with the PID/UID,
+ // but it doesn't tell which package has created the MediaController, so useless.
+ return hasMediaControlPermission(UserHandle.getUserId(uid), controllerPackageName,
+ controllerPid, controllerUid);
+ } finally {
+ Binder.restoreCallingIdentity(token);
+ }
+ }
+
+ // For MediaSession
+ private int verifySessionsRequest(ComponentName componentName, int userId, final int pid,
+ final int uid) {
+ String packageName = null;
+ if (componentName != null) {
+ // If they gave us a component name verify they own the
+ // package
+ packageName = componentName.getPackageName();
+ enforcePackageName(packageName, uid);
+ }
+ // Check that they can make calls on behalf of the user and
+ // get the final user id
+ int resolvedUserId = ActivityManager.handleIncomingUser(pid, uid, userId,
+ true /* allowAll */, true /* requireFull */, "getSessions", packageName);
+ // Check if they have the permissions or their component is
+ // enabled for the user they're calling from.
+ enforceMediaPermissions(componentName, pid, uid, resolvedUserId);
+ return resolvedUserId;
+ }
+
+ private boolean hasMediaControlPermission(int resolvedUserId, String packageName,
+ int pid, int uid) throws RemoteException {
+ // Allow API calls from the System UI and Settings
+ if (hasStatusBarServicePermission(pid, uid)) {
+ return true;
+ }
+
+ // Check if it's system server or has MEDIA_CONTENT_CONTROL.
+ // Note that system server doesn't have MEDIA_CONTENT_CONTROL, so we need extra
+ // check here.
+ if (uid == Process.SYSTEM_UID || mContext.checkPermission(
+ android.Manifest.permission.MEDIA_CONTENT_CONTROL, pid, uid)
+ == PackageManager.PERMISSION_GRANTED) {
+ return true;
+ } else if (DEBUG) {
+ Log.d(TAG, packageName + " (uid=" + uid + ") hasn't granted MEDIA_CONTENT_CONTROL");
+ }
+
+ // You may not access another user's content as an enabled listener.
+ final int userId = UserHandle.getUserId(uid);
+ if (resolvedUserId != userId) {
+ return false;
+ }
+
+ // TODO(jaewan): (Post-P) Propose NotificationManager#hasEnabledNotificationListener(
+ // String pkgName) to notification team for optimization
+ final List<ComponentName> enabledNotificationListeners =
+ mNotificationManager.getEnabledNotificationListeners(userId);
+ if (enabledNotificationListeners != null) {
+ for (int i = 0; i < enabledNotificationListeners.size(); i++) {
+ if (TextUtils.equals(packageName,
+ enabledNotificationListeners.get(i).getPackageName())) {
+ return true;
+ }
+ }
+ }
+ if (DEBUG) {
+ Log.d(TAG, packageName + " (uid=" + uid + ") doesn't have an enabled "
+ + "notification listener");
+ }
+ return false;
+ }
+
+ private void dispatchAdjustVolumeLocked(String packageName, String opPackageName, int pid,
+ int uid, boolean asSystemService, int suggestedStream, int direction, int flags) {
+ MediaSessionRecord session = isGlobalPriorityActiveLocked() ? mGlobalPrioritySession
+ : mCurrentFullUserRecord.mPriorityStack.getDefaultVolumeSession();
+
+ boolean preferSuggestedStream = false;
+ if (isValidLocalStreamType(suggestedStream)
+ && AudioSystem.isStreamActive(suggestedStream, 0)) {
+ preferSuggestedStream = true;
+ }
+ if (DEBUG_KEY_EVENT) {
+ Log.d(TAG, "Adjusting " + session + " by " + direction + ". flags="
+ + flags + ", suggestedStream=" + suggestedStream
+ + ", preferSuggestedStream=" + preferSuggestedStream);
+ }
+ if (session == null || preferSuggestedStream) {
+ if ((flags & AudioManager.FLAG_ACTIVE_MEDIA_ONLY) != 0
+ && !AudioSystem.isStreamActive(AudioManager.STREAM_MUSIC, 0)) {
+ if (DEBUG) {
+ Log.d(TAG, "No active session to adjust, skipping media only volume event");
+ }
+ return;
+ }
+
+ // Execute mAudioService.adjustSuggestedStreamVolume() on
+ // handler thread of MediaSessionService.
+ // This will release the MediaSessionService.mLock sooner and avoid
+ // a potential deadlock between MediaSessionService.mLock and
+ // ActivityManagerService lock.
+ mHandler.post(new Runnable() {
+ @Override
+ public void run() {
+ final String callingOpPackageName;
+ final int callingUid;
+ if (asSystemService) {
+ callingOpPackageName = mContext.getOpPackageName();
+ callingUid = Process.myUid();
+ } else {
+ callingOpPackageName = opPackageName;
+ callingUid = uid;
+ }
+ try {
+ mAudioManagerInternal.adjustSuggestedStreamVolumeForUid(suggestedStream,
+ direction, flags, callingOpPackageName, callingUid);
+ } catch (SecurityException | IllegalArgumentException e) {
+ Log.e(TAG, "Cannot adjust volume: direction=" + direction
+ + ", suggestedStream=" + suggestedStream + ", flags=" + flags
+ + ", packageName=" + packageName + ", uid=" + uid
+ + ", asSystemService=" + asSystemService, e);
+ }
+ }
+ });
+ } else {
+ session.adjustVolume(packageName, opPackageName, pid, uid, null, asSystemService,
+ direction, flags, true);
+ }
+ }
+
+ private void handleVoiceKeyEventLocked(String packageName, int pid, int uid,
+ boolean asSystemService, KeyEvent keyEvent, boolean needWakeLock) {
+ int action = keyEvent.getAction();
+ boolean isLongPress = (keyEvent.getFlags() & KeyEvent.FLAG_LONG_PRESS) != 0;
+ if (action == KeyEvent.ACTION_DOWN) {
+ if (keyEvent.getRepeatCount() == 0) {
+ mVoiceButtonDown = true;
+ mVoiceButtonHandled = false;
+ } else if (mVoiceButtonDown && !mVoiceButtonHandled && isLongPress) {
+ mVoiceButtonHandled = true;
+ startVoiceInput(needWakeLock);
+ }
+ } else if (action == KeyEvent.ACTION_UP) {
+ if (mVoiceButtonDown) {
+ mVoiceButtonDown = false;
+ if (!mVoiceButtonHandled && !keyEvent.isCanceled()) {
+ // Resend the down then send this event through
+ KeyEvent downEvent = KeyEvent.changeAction(keyEvent, KeyEvent.ACTION_DOWN);
+ dispatchMediaKeyEventLocked(packageName, pid, uid, asSystemService,
+ downEvent, needWakeLock);
+ dispatchMediaKeyEventLocked(packageName, pid, uid, asSystemService,
+ keyEvent, needWakeLock);
+ }
+ }
+ }
+ }
+
+ private void dispatchMediaKeyEventLocked(String packageName, int pid, int uid,
+ boolean asSystemService, KeyEvent keyEvent, boolean needWakeLock) {
+ MediaSessionRecord session = mCurrentFullUserRecord.getMediaButtonSessionLocked();
+ if (session != null) {
+ if (DEBUG_KEY_EVENT) {
+ Log.d(TAG, "Sending " + keyEvent + " to " + session);
+ }
+ if (needWakeLock) {
+ mKeyEventReceiver.aquireWakeLockLocked();
+ }
+ // If we don't need a wakelock use -1 as the id so we won't release it later.
+ session.sendMediaButton(packageName, pid, uid, asSystemService, keyEvent,
+ needWakeLock ? mKeyEventReceiver.mLastTimeoutId : -1,
+ mKeyEventReceiver);
+ if (mCurrentFullUserRecord.mCallback != null) {
+ try {
+ mCurrentFullUserRecord.mCallback.onMediaKeyEventDispatchedToMediaSession(
+ keyEvent, session.getSessionToken());
+ } catch (RemoteException e) {
+ Log.w(TAG, "Failed to send callback", e);
+ }
+ }
+ } else if (mCurrentFullUserRecord.mLastMediaButtonReceiver != null
+ || mCurrentFullUserRecord.mRestoredMediaButtonReceiver != null) {
+ if (needWakeLock) {
+ mKeyEventReceiver.aquireWakeLockLocked();
+ }
+ Intent mediaButtonIntent = new Intent(Intent.ACTION_MEDIA_BUTTON);
+ mediaButtonIntent.addFlags(Intent.FLAG_RECEIVER_FOREGROUND);
+ mediaButtonIntent.putExtra(Intent.EXTRA_KEY_EVENT, keyEvent);
+ // TODO: Find a way to also send PID/UID in secure way.
+ String callerPackageName =
+ (asSystemService) ? mContext.getPackageName() : packageName;
+ mediaButtonIntent.putExtra(Intent.EXTRA_PACKAGE_NAME, callerPackageName);
+ try {
+ if (mCurrentFullUserRecord.mLastMediaButtonReceiver != null) {
+ PendingIntent receiver = mCurrentFullUserRecord.mLastMediaButtonReceiver;
+ if (DEBUG_KEY_EVENT) {
+ Log.d(TAG, "Sending " + keyEvent
+ + " to the last known PendingIntent " + receiver);
+ }
+ receiver.send(mContext,
+ needWakeLock ? mKeyEventReceiver.mLastTimeoutId : -1,
+ mediaButtonIntent, mKeyEventReceiver, mHandler);
+ if (mCurrentFullUserRecord.mCallback != null) {
+ ComponentName componentName = mCurrentFullUserRecord
+ .mLastMediaButtonReceiver.getIntent().getComponent();
+ if (componentName != null) {
+ mCurrentFullUserRecord.mCallback
+ .onMediaKeyEventDispatchedToMediaButtonReceiver(
+ keyEvent, componentName);
+ }
+ }
+ } else {
+ ComponentName receiver =
+ mCurrentFullUserRecord.mRestoredMediaButtonReceiver;
+ int componentType = mCurrentFullUserRecord
+ .mRestoredMediaButtonReceiverComponentType;
+ UserHandle userHandle = UserHandle.of(mCurrentFullUserRecord
+ .mRestoredMediaButtonReceiverUserId);
+ if (DEBUG_KEY_EVENT) {
+ Log.d(TAG, "Sending " + keyEvent + " to the restored intent "
+ + receiver + ", type=" + componentType);
+ }
+ mediaButtonIntent.setComponent(receiver);
+ try {
+ switch (componentType) {
+ case FullUserRecord.COMPONENT_TYPE_ACTIVITY:
+ mContext.startActivityAsUser(mediaButtonIntent, userHandle);
+ break;
+ case FullUserRecord.COMPONENT_TYPE_SERVICE:
+ mContext.startForegroundServiceAsUser(mediaButtonIntent,
+ userHandle);
+ break;
+ default:
+ // Legacy behavior for other cases.
+ mContext.sendBroadcastAsUser(mediaButtonIntent, userHandle);
+ }
+ } catch (Exception e) {
+ Log.w(TAG, "Error sending media button to the restored intent "
+ + receiver + ", type=" + componentType, e);
+ }
+ if (mCurrentFullUserRecord.mCallback != null) {
+ mCurrentFullUserRecord.mCallback
+ .onMediaKeyEventDispatchedToMediaButtonReceiver(
+ keyEvent, receiver);
+ }
+ }
+ } catch (CanceledException e) {
+ Log.i(TAG, "Error sending key event to media button receiver "
+ + mCurrentFullUserRecord.mLastMediaButtonReceiver, e);
+ } catch (RemoteException e) {
+ Log.w(TAG, "Failed to send callback", e);
+ }
+ }
+ }
+
+ private void startVoiceInput(boolean needWakeLock) {
+ Intent voiceIntent = null;
+ // select which type of search to launch:
+ // - screen on and device unlocked: action is ACTION_WEB_SEARCH
+ // - device locked or screen off: action is
+ // ACTION_VOICE_SEARCH_HANDS_FREE
+ // with EXTRA_SECURE set to true if the device is securely locked
+ PowerManager pm = (PowerManager) mContext.getSystemService(Context.POWER_SERVICE);
+ boolean isLocked = mKeyguardManager != null && mKeyguardManager.isKeyguardLocked();
+ if (!isLocked && pm.isScreenOn()) {
+ voiceIntent = new Intent(android.speech.RecognizerIntent.ACTION_WEB_SEARCH);
+ Log.i(TAG, "voice-based interactions: about to use ACTION_WEB_SEARCH");
+ } else {
+ voiceIntent = new Intent(RecognizerIntent.ACTION_VOICE_SEARCH_HANDS_FREE);
+ voiceIntent.putExtra(RecognizerIntent.EXTRA_SECURE,
+ isLocked && mKeyguardManager.isKeyguardSecure());
+ Log.i(TAG, "voice-based interactions: about to use ACTION_VOICE_SEARCH_HANDS_FREE");
+ }
+ // start the search activity
+ if (needWakeLock) {
+ mMediaEventWakeLock.acquire();
+ }
+ try {
+ if (voiceIntent != null) {
+ voiceIntent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK
+ | Intent.FLAG_ACTIVITY_EXCLUDE_FROM_RECENTS);
+ if (DEBUG) Log.d(TAG, "voiceIntent: " + voiceIntent);
+ mContext.startActivityAsUser(voiceIntent, UserHandle.CURRENT);
+ }
+ } catch (ActivityNotFoundException e) {
+ Log.w(TAG, "No activity for search: " + e);
+ } finally {
+ if (needWakeLock) {
+ mMediaEventWakeLock.release();
+ }
+ }
+ }
+
+ private boolean isVoiceKey(int keyCode) {
+ return keyCode == KeyEvent.KEYCODE_HEADSETHOOK
+ || (!mHasFeatureLeanback && keyCode == KeyEvent.KEYCODE_MEDIA_PLAY_PAUSE);
+ }
+
+ private boolean isUserSetupComplete() {
+ return Settings.Secure.getIntForUser(mContext.getContentResolver(),
+ Settings.Secure.USER_SETUP_COMPLETE, 0, UserHandle.USER_CURRENT) != 0;
+ }
+
+ // we only handle public stream types, which are 0-5
+ private boolean isValidLocalStreamType(int streamType) {
+ return streamType >= AudioManager.STREAM_VOICE_CALL
+ && streamType <= AudioManager.STREAM_NOTIFICATION;
+ }
+
+ private class MediaKeyListenerResultReceiver extends ResultReceiver implements Runnable {
+ private final String mPackageName;
+ private final int mPid;
+ private final int mUid;
+ private final boolean mAsSystemService;
+ private final KeyEvent mKeyEvent;
+ private final boolean mNeedWakeLock;
+ private boolean mHandled;
+
+ private MediaKeyListenerResultReceiver(String packageName, int pid, int uid,
+ boolean asSystemService, KeyEvent keyEvent, boolean needWakeLock) {
+ super(mHandler);
+ mHandler.postDelayed(this, MEDIA_KEY_LISTENER_TIMEOUT);
+ mPackageName = packageName;
+ mPid = pid;
+ mUid = uid;
+ mAsSystemService = asSystemService;
+ mKeyEvent = keyEvent;
+ mNeedWakeLock = needWakeLock;
+ }
+
+ @Override
+ public void run() {
+ Log.d(TAG, "The media key listener is timed-out for " + mKeyEvent);
+ dispatchMediaKeyEvent();
+ }
+
+ @Override
+ protected void onReceiveResult(int resultCode, Bundle resultData) {
+ if (resultCode == MediaSessionManager.RESULT_MEDIA_KEY_HANDLED) {
+ mHandled = true;
+ mHandler.removeCallbacks(this);
+ return;
+ }
+ dispatchMediaKeyEvent();
+ }
+
+ private void dispatchMediaKeyEvent() {
+ if (mHandled) {
+ return;
+ }
+ mHandled = true;
+ mHandler.removeCallbacks(this);
+ synchronized (mLock) {
+ if (!isGlobalPriorityActiveLocked()
+ && isVoiceKey(mKeyEvent.getKeyCode())) {
+ handleVoiceKeyEventLocked(mPackageName, mPid, mUid, mAsSystemService,
+ mKeyEvent, mNeedWakeLock);
+ } else {
+ dispatchMediaKeyEventLocked(mPackageName, mPid, mUid, mAsSystemService,
+ mKeyEvent, mNeedWakeLock);
+ }
+ }
+ }
+ }
+
+ private KeyEventWakeLockReceiver mKeyEventReceiver = new KeyEventWakeLockReceiver(mHandler);
+
+ class KeyEventWakeLockReceiver extends ResultReceiver implements Runnable,
+ PendingIntent.OnFinished {
+ private final Handler mHandler;
+ private int mRefCount = 0;
+ private int mLastTimeoutId = 0;
+
+ KeyEventWakeLockReceiver(Handler handler) {
+ super(handler);
+ mHandler = handler;
+ }
+
+ public void onTimeout() {
+ synchronized (mLock) {
+ if (mRefCount == 0) {
+ // We've already released it, so just return
+ return;
+ }
+ mLastTimeoutId++;
+ mRefCount = 0;
+ releaseWakeLockLocked();
+ }
+ }
+
+ public void aquireWakeLockLocked() {
+ if (mRefCount == 0) {
+ mMediaEventWakeLock.acquire();
+ }
+ mRefCount++;
+ mHandler.removeCallbacks(this);
+ mHandler.postDelayed(this, WAKELOCK_TIMEOUT);
+
+ }
+
+ @Override
+ public void run() {
+ onTimeout();
+ }
+
+ @Override
+ protected void onReceiveResult(int resultCode, Bundle resultData) {
+ if (resultCode < mLastTimeoutId) {
+ // Ignore results from calls that were before the last
+ // timeout, just in case.
+ return;
+ } else {
+ synchronized (mLock) {
+ if (mRefCount > 0) {
+ mRefCount--;
+ if (mRefCount == 0) {
+ releaseWakeLockLocked();
+ }
+ }
+ }
+ }
+ }
+
+ private void releaseWakeLockLocked() {
+ mMediaEventWakeLock.release();
+ mHandler.removeCallbacks(this);
+ }
+
+ @Override
+ public void onSendFinished(PendingIntent pendingIntent, Intent intent, int resultCode,
+ String resultData, Bundle resultExtras) {
+ onReceiveResult(resultCode, null);
+ }
+ };
+
+ BroadcastReceiver mKeyEventDone = new BroadcastReceiver() {
+ @Override
+ public void onReceive(Context context, Intent intent) {
+ if (intent == null) {
+ return;
+ }
+ Bundle extras = intent.getExtras();
+ if (extras == null) {
+ return;
+ }
+ synchronized (mLock) {
+ if (extras.containsKey(EXTRA_WAKELOCK_ACQUIRED)
+ && mMediaEventWakeLock.isHeld()) {
+ mMediaEventWakeLock.release();
+ }
+ }
+ }
+ };
+ }
+
+ final class MessageHandler extends Handler {
+ private static final int MSG_SESSIONS_CHANGED = 1;
+ private static final int MSG_VOLUME_INITIAL_DOWN = 2;
+ private final SparseArray<Integer> mIntegerCache = new SparseArray<>();
+
+ @Override
+ public void handleMessage(Message msg) {
+ switch (msg.what) {
+ case MSG_SESSIONS_CHANGED:
+ pushSessionsChanged((int) msg.obj);
+ break;
+ case MSG_VOLUME_INITIAL_DOWN:
+ synchronized (mLock) {
+ FullUserRecord user = mUserRecords.get((int) msg.arg1);
+ if (user != null && user.mInitialDownVolumeKeyEvent != null) {
+ dispatchVolumeKeyLongPressLocked(user.mInitialDownVolumeKeyEvent);
+ // Mark that the key is already handled.
+ user.mInitialDownVolumeKeyEvent = null;
+ }
+ }
+ break;
+ }
+ }
+
+ public void postSessionsChanged(int userId) {
+ // Use object instead of the arguments when posting message to remove pending requests.
+ Integer userIdInteger = mIntegerCache.get(userId);
+ if (userIdInteger == null) {
+ userIdInteger = Integer.valueOf(userId);
+ mIntegerCache.put(userId, userIdInteger);
+ }
+ removeMessages(MSG_SESSIONS_CHANGED, userIdInteger);
+ obtainMessage(MSG_SESSIONS_CHANGED, userIdInteger).sendToTarget();
+ }
+ }
+
+ private class Controller2Callback extends MediaController2.ControllerCallback {
+ private final Session2Token mToken;
+
+ Controller2Callback(Session2Token token) {
+ mToken = token;
+ }
+
+ @Override
+ public void onConnected(MediaController2 controller, Session2CommandGroup allowedCommands) {
+ synchronized (mLock) {
+ int userId = UserHandle.getUserId(mToken.getUid());
+ mSession2TokensPerUser.get(userId).add(mToken);
+ pushSession2TokensChangedLocked(userId);
+ }
+ }
+
+ @Override
+ public void onDisconnected(MediaController2 controller) {
+ synchronized (mLock) {
+ int userId = UserHandle.getUserId(mToken.getUid());
+ mSession2TokensPerUser.get(userId).remove(mToken);
+ pushSession2TokensChangedLocked(userId);
+ }
+ }
}
}
diff --git a/services/core/java/com/android/server/media/MediaSessionServiceImpl.java b/services/core/java/com/android/server/media/MediaSessionServiceImpl.java
deleted file mode 100644
index aa886c27d7d8..000000000000
--- a/services/core/java/com/android/server/media/MediaSessionServiceImpl.java
+++ /dev/null
@@ -1,2274 +0,0 @@
-/*
- * Copyright 2019 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-package com.android.server.media;
-
-import static android.os.UserHandle.USER_ALL;
-
-import android.annotation.Nullable;
-import android.app.ActivityManager;
-import android.app.INotificationManager;
-import android.app.KeyguardManager;
-import android.app.PendingIntent;
-import android.app.PendingIntent.CanceledException;
-import android.content.ActivityNotFoundException;
-import android.content.BroadcastReceiver;
-import android.content.ComponentName;
-import android.content.ContentResolver;
-import android.content.Context;
-import android.content.Intent;
-import android.content.pm.ActivityInfo;
-import android.content.pm.PackageManager;
-import android.content.pm.PackageManager.NameNotFoundException;
-import android.content.pm.ParceledListSlice;
-import android.content.pm.ServiceInfo;
-import android.content.pm.UserInfo;
-import android.database.ContentObserver;
-import android.media.AudioManager;
-import android.media.AudioManagerInternal;
-import android.media.AudioPlaybackConfiguration;
-import android.media.AudioSystem;
-import android.media.IAudioService;
-import android.media.IRemoteVolumeController;
-import android.media.MediaController2;
-import android.media.Session2CommandGroup;
-import android.media.Session2Token;
-import android.media.session.IActiveSessionsListener;
-import android.media.session.ICallback;
-import android.media.session.IOnMediaKeyListener;
-import android.media.session.IOnVolumeKeyLongPressListener;
-import android.media.session.ISession;
-import android.media.session.ISession2TokensListener;
-import android.media.session.ISessionCallback;
-import android.media.session.ISessionManager;
-import android.media.session.MediaSession;
-import android.media.session.MediaSessionManager;
-import android.net.Uri;
-import android.os.Binder;
-import android.os.Bundle;
-import android.os.Handler;
-import android.os.HandlerExecutor;
-import android.os.IBinder;
-import android.os.Message;
-import android.os.PowerManager;
-import android.os.Process;
-import android.os.RemoteCallbackList;
-import android.os.RemoteException;
-import android.os.ResultReceiver;
-import android.os.ServiceManager;
-import android.os.UserHandle;
-import android.os.UserManager;
-import android.provider.Settings;
-import android.speech.RecognizerIntent;
-import android.text.TextUtils;
-import android.util.Log;
-import android.util.Slog;
-import android.util.SparseArray;
-import android.util.SparseIntArray;
-import android.view.KeyEvent;
-import android.view.ViewConfiguration;
-
-import com.android.internal.annotations.GuardedBy;
-import com.android.internal.util.DumpUtils;
-import com.android.server.LocalServices;
-
-import java.io.FileDescriptor;
-import java.io.PrintWriter;
-import java.util.ArrayList;
-import java.util.List;
-
-/**
- * System implementation of MediaSessionManager
- */
-public class MediaSessionServiceImpl extends MediaSessionService.ServiceImpl {
- private static final String TAG = "MediaSessionService";
- static final boolean DEBUG = Log.isLoggable(TAG, Log.DEBUG);
- // Leave log for key event always.
- private static final boolean DEBUG_KEY_EVENT = true;
-
- private static final int WAKELOCK_TIMEOUT = 5000;
- private static final int MEDIA_KEY_LISTENER_TIMEOUT = 1000;
-
- private final Context mContext;
- private final SessionManagerImpl mSessionManagerImpl;
- private final MessageHandler mHandler = new MessageHandler();
- private final PowerManager.WakeLock mMediaEventWakeLock;
- private final int mLongPressTimeout;
- private final INotificationManager mNotificationManager;
- private final Object mLock = new Object();
- // Keeps the full user id for each user.
- @GuardedBy("mLock")
- private final SparseIntArray mFullUserIds = new SparseIntArray();
- @GuardedBy("mLock")
- private final SparseArray<FullUserRecord> mUserRecords = new SparseArray<FullUserRecord>();
- @GuardedBy("mLock")
- private final ArrayList<SessionsListenerRecord> mSessionsListeners =
- new ArrayList<SessionsListenerRecord>();
- // Map user id as index to list of Session2Tokens
- // TODO: Keep session2 info in MediaSessionStack for prioritizing both session1 and session2 in
- // one place.
- @GuardedBy("mLock")
- private final SparseArray<List<Session2Token>> mSession2TokensPerUser = new SparseArray<>();
- @GuardedBy("mLock")
- private final List<Session2TokensListenerRecord> mSession2TokensListenerRecords =
- new ArrayList<>();
-
- private KeyguardManager mKeyguardManager;
- private IAudioService mAudioService;
- private AudioManagerInternal mAudioManagerInternal;
- private ActivityManager mActivityManager;
- private ContentResolver mContentResolver;
- private SettingsObserver mSettingsObserver;
- private boolean mHasFeatureLeanback;
-
- // The FullUserRecord of the current users. (i.e. The foreground user that isn't a profile)
- // It's always not null after the MediaSessionService is started.
- private FullUserRecord mCurrentFullUserRecord;
- private MediaSessionRecord mGlobalPrioritySession;
- private AudioPlayerStateMonitor mAudioPlayerStateMonitor;
-
- // Used to notify System UI and Settings when remote volume was changed.
- @GuardedBy("mLock")
- final RemoteCallbackList<IRemoteVolumeController> mRemoteVolumeControllers =
- new RemoteCallbackList<>();
-
- public MediaSessionServiceImpl(Context context) {
- mContext = context;
- mSessionManagerImpl = new SessionManagerImpl();
- PowerManager pm = (PowerManager) context.getSystemService(Context.POWER_SERVICE);
- mMediaEventWakeLock = pm.newWakeLock(PowerManager.PARTIAL_WAKE_LOCK, "handleMediaEvent");
- mLongPressTimeout = ViewConfiguration.getLongPressTimeout();
- mNotificationManager = INotificationManager.Stub.asInterface(
- ServiceManager.getService(Context.NOTIFICATION_SERVICE));
- }
-
- Context getContext() {
- return mContext;
- }
-
- IBinder getServiceBinder() {
- return mSessionManagerImpl;
- }
-
- @Override
- public void onStart() {
- mKeyguardManager = (KeyguardManager) mContext.getSystemService(Context.KEYGUARD_SERVICE);
- mAudioService = getAudioService();
- mAudioManagerInternal = LocalServices.getService(AudioManagerInternal.class);
- mActivityManager =
- (ActivityManager) mContext.getSystemService(Context.ACTIVITY_SERVICE);
- mAudioPlayerStateMonitor = AudioPlayerStateMonitor.getInstance(mContext);
- mAudioPlayerStateMonitor.registerListener(
- (config, isRemoved) -> {
- if (config.getPlayerType()
- == AudioPlaybackConfiguration.PLAYER_TYPE_JAM_SOUNDPOOL) {
- return;
- }
- synchronized (mLock) {
- FullUserRecord user = getFullUserRecordLocked(
- UserHandle.getUserId(config.getClientUid()));
- if (user != null) {
- user.mPriorityStack.updateMediaButtonSessionIfNeeded();
- }
- }
- }, null /* handler */);
- mContentResolver = mContext.getContentResolver();
- mSettingsObserver = new SettingsObserver();
- mSettingsObserver.observe();
- mHasFeatureLeanback = mContext.getPackageManager().hasSystemFeature(
- PackageManager.FEATURE_LEANBACK);
-
- updateUser();
- }
-
- private IAudioService getAudioService() {
- IBinder b = ServiceManager.getService(Context.AUDIO_SERVICE);
- return IAudioService.Stub.asInterface(b);
- }
-
- private boolean isGlobalPriorityActiveLocked() {
- return mGlobalPrioritySession != null && mGlobalPrioritySession.isActive();
- }
-
- @Override
- public void updateSession(MediaSessionRecord record) {
- synchronized (mLock) {
- FullUserRecord user = getFullUserRecordLocked(record.getUserId());
- if (user == null) {
- Log.w(TAG, "Unknown session updated. Ignoring.");
- return;
- }
- if ((record.getFlags() & MediaSession.FLAG_EXCLUSIVE_GLOBAL_PRIORITY) != 0) {
- if (DEBUG_KEY_EVENT) {
- Log.d(TAG, "Global priority session is updated, active=" + record.isActive());
- }
- user.pushAddressedPlayerChangedLocked();
- } else {
- if (!user.mPriorityStack.contains(record)) {
- Log.w(TAG, "Unknown session updated. Ignoring.");
- return;
- }
- user.mPriorityStack.onSessionStateChange(record);
- }
- mHandler.postSessionsChanged(record.getUserId());
- }
- }
-
- @Override
- public void setGlobalPrioritySession(MediaSessionRecord record) {
- synchronized (mLock) {
- FullUserRecord user = getFullUserRecordLocked(record.getUserId());
- if (mGlobalPrioritySession != record) {
- Log.d(TAG, "Global priority session is changed from " + mGlobalPrioritySession
- + " to " + record);
- mGlobalPrioritySession = record;
- if (user != null && user.mPriorityStack.contains(record)) {
- // Handle the global priority session separately.
- // Otherwise, it can be the media button session regardless of the active state
- // because it or other system components might have been the lastly played media
- // app.
- user.mPriorityStack.removeSession(record);
- }
- }
- }
- }
-
- private List<MediaSessionRecord> getActiveSessionsLocked(int userId) {
- List<MediaSessionRecord> records = new ArrayList<>();
- if (userId == USER_ALL) {
- int size = mUserRecords.size();
- for (int i = 0; i < size; i++) {
- records.addAll(mUserRecords.valueAt(i).mPriorityStack.getActiveSessions(userId));
- }
- } else {
- FullUserRecord user = getFullUserRecordLocked(userId);
- if (user == null) {
- Log.w(TAG, "getSessions failed. Unknown user " + userId);
- return records;
- }
- records.addAll(user.mPriorityStack.getActiveSessions(userId));
- }
-
- // Return global priority session at the first whenever it's asked.
- if (isGlobalPriorityActiveLocked()
- && (userId == USER_ALL || userId == mGlobalPrioritySession.getUserId())) {
- records.add(0, mGlobalPrioritySession);
- }
- return records;
- }
-
- List<Session2Token> getSession2TokensLocked(int userId) {
- List<Session2Token> list = new ArrayList<>();
- if (userId == USER_ALL) {
- for (int i = 0; i < mSession2TokensPerUser.size(); i++) {
- list.addAll(mSession2TokensPerUser.valueAt(i));
- }
- } else {
- list.addAll(mSession2TokensPerUser.get(userId));
- }
- return list;
- }
-
- /**
- * Tells the System UI and Settings app that volume has changed on an active remote session.
- */
- public void notifyRemoteVolumeChanged(int flags, MediaSessionRecord session) {
- if (!session.isActive()) {
- return;
- }
- synchronized (mLock) {
- int size = mRemoteVolumeControllers.beginBroadcast();
- MediaSession.Token token = session.getSessionToken();
- for (int i = size - 1; i >= 0; i--) {
- try {
- IRemoteVolumeController cb = mRemoteVolumeControllers.getBroadcastItem(i);
- cb.remoteVolumeChanged(token, flags);
- } catch (Exception e) {
- Log.w(TAG, "Error sending volume change.", e);
- }
- }
- mRemoteVolumeControllers.finishBroadcast();
- }
- }
-
- @Override
- public void onSessionPlaystateChanged(MediaSessionRecord record, int oldState, int newState) {
- synchronized (mLock) {
- FullUserRecord user = getFullUserRecordLocked(record.getUserId());
- if (user == null || !user.mPriorityStack.contains(record)) {
- Log.d(TAG, "Unknown session changed playback state. Ignoring.");
- return;
- }
- user.mPriorityStack.onPlaystateChanged(record, oldState, newState);
- }
- }
-
- @Override
- public void onSessionPlaybackTypeChanged(MediaSessionRecord record) {
- synchronized (mLock) {
- FullUserRecord user = getFullUserRecordLocked(record.getUserId());
- if (user == null || !user.mPriorityStack.contains(record)) {
- Log.d(TAG, "Unknown session changed playback type. Ignoring.");
- return;
- }
- pushRemoteVolumeUpdateLocked(record.getUserId());
- }
- }
-
- @Override
- public void onStartUser(int userId) {
- if (DEBUG) Log.d(TAG, "onStartUser: " + userId);
- updateUser();
- }
-
- @Override
- public void onSwitchUser(int userId) {
- if (DEBUG) Log.d(TAG, "onSwitchUser: " + userId);
- updateUser();
- }
-
- // Called when the user with the userId is removed.
- @Override
- public void onStopUser(int userId) {
- if (DEBUG) Log.d(TAG, "onStopUser: " + userId);
- synchronized (mLock) {
- // TODO: Also handle removing user in updateUser() because adding/switching user is
- // handled in updateUser().
- FullUserRecord user = getFullUserRecordLocked(userId);
- if (user != null) {
- if (user.mFullUserId == userId) {
- user.destroySessionsForUserLocked(USER_ALL);
- mUserRecords.remove(userId);
- } else {
- user.destroySessionsForUserLocked(userId);
- }
- }
- mSession2TokensPerUser.remove(userId);
- updateUser();
- }
- }
-
- @Override
- public void monitor() {
- synchronized (mLock) {
- // Check for deadlock
- }
- }
-
- protected void enforcePhoneStatePermission(int pid, int uid) {
- if (mContext.checkPermission(android.Manifest.permission.MODIFY_PHONE_STATE, pid, uid)
- != PackageManager.PERMISSION_GRANTED) {
- throw new SecurityException("Must hold the MODIFY_PHONE_STATE permission.");
- }
- }
-
- void sessionDied(MediaSessionRecord session) {
- synchronized (mLock) {
- destroySessionLocked(session);
- }
- }
-
- void destroySession(MediaSessionRecord session) {
- synchronized (mLock) {
- destroySessionLocked(session);
- }
- }
-
- private void updateUser() {
- synchronized (mLock) {
- UserManager manager = (UserManager) mContext.getSystemService(Context.USER_SERVICE);
- mFullUserIds.clear();
- List<UserInfo> allUsers = manager.getUsers();
- if (allUsers != null) {
- for (UserInfo userInfo : allUsers) {
- if (userInfo.isManagedProfile()) {
- mFullUserIds.put(userInfo.id, userInfo.profileGroupId);
- } else {
- mFullUserIds.put(userInfo.id, userInfo.id);
- if (mUserRecords.get(userInfo.id) == null) {
- mUserRecords.put(userInfo.id, new FullUserRecord(userInfo.id));
- }
- }
- if (mSession2TokensPerUser.get(userInfo.id) == null) {
- mSession2TokensPerUser.put(userInfo.id, new ArrayList<>());
- }
- }
- }
- // Ensure that the current full user exists.
- int currentFullUserId = ActivityManager.getCurrentUser();
- mCurrentFullUserRecord = mUserRecords.get(currentFullUserId);
- if (mCurrentFullUserRecord == null) {
- Log.w(TAG, "Cannot find FullUserInfo for the current user " + currentFullUserId);
- mCurrentFullUserRecord = new FullUserRecord(currentFullUserId);
- mUserRecords.put(currentFullUserId, mCurrentFullUserRecord);
- if (mSession2TokensPerUser.get(currentFullUserId) == null) {
- mSession2TokensPerUser.put(currentFullUserId, new ArrayList<>());
- }
- }
- mFullUserIds.put(currentFullUserId, currentFullUserId);
- }
- }
-
- private void updateActiveSessionListeners() {
- synchronized (mLock) {
- for (int i = mSessionsListeners.size() - 1; i >= 0; i--) {
- SessionsListenerRecord listener = mSessionsListeners.get(i);
- try {
- enforceMediaPermissions(listener.componentName, listener.pid, listener.uid,
- listener.userId);
- } catch (SecurityException e) {
- Log.i(TAG, "ActiveSessionsListener " + listener.componentName
- + " is no longer authorized. Disconnecting.");
- mSessionsListeners.remove(i);
- try {
- listener.listener
- .onActiveSessionsChanged(new ArrayList<MediaSession.Token>());
- } catch (Exception e1) {
- // ignore
- }
- }
- }
- }
- }
-
- /*
- * When a session is removed several things need to happen.
- * 1. We need to remove it from the relevant user.
- * 2. We need to remove it from the priority stack.
- * 3. We need to remove it from all sessions.
- * 4. If this is the system priority session we need to clear it.
- * 5. We need to unlink to death from the cb binder
- * 6. We need to tell the session to do any final cleanup (onDestroy)
- */
- private void destroySessionLocked(MediaSessionRecord session) {
- if (DEBUG) {
- Log.d(TAG, "Destroying " + session);
- }
- FullUserRecord user = getFullUserRecordLocked(session.getUserId());
- if (mGlobalPrioritySession == session) {
- mGlobalPrioritySession = null;
- if (session.isActive() && user != null) {
- user.pushAddressedPlayerChangedLocked();
- }
- } else {
- if (user != null) {
- user.mPriorityStack.removeSession(session);
- }
- }
-
- try {
- session.getCallback().asBinder().unlinkToDeath(session, 0);
- } catch (Exception e) {
- // ignore exceptions while destroying a session.
- }
- session.onDestroy();
- mHandler.postSessionsChanged(session.getUserId());
- }
-
- private void enforcePackageName(String packageName, int uid) {
- if (TextUtils.isEmpty(packageName)) {
- throw new IllegalArgumentException("packageName may not be empty");
- }
- String[] packages = mContext.getPackageManager().getPackagesForUid(uid);
- final int packageCount = packages.length;
- for (int i = 0; i < packageCount; i++) {
- if (packageName.equals(packages[i])) {
- return;
- }
- }
- throw new IllegalArgumentException("packageName is not owned by the calling process");
- }
-
- /**
- * Checks a caller's authorization to register an IRemoteControlDisplay.
- * Authorization is granted if one of the following is true:
- * <ul>
- * <li>the caller has android.Manifest.permission.MEDIA_CONTENT_CONTROL
- * permission</li>
- * <li>the caller's listener is one of the enabled notification listeners
- * for the caller's user</li>
- * </ul>
- */
- private void enforceMediaPermissions(ComponentName compName, int pid, int uid,
- int resolvedUserId) {
- if (hasStatusBarServicePermission(pid, uid)) return;
- if (mContext
- .checkPermission(android.Manifest.permission.MEDIA_CONTENT_CONTROL, pid, uid)
- != PackageManager.PERMISSION_GRANTED
- && !isEnabledNotificationListener(compName, UserHandle.getUserId(uid),
- resolvedUserId)) {
- throw new SecurityException("Missing permission to control media.");
- }
- }
-
- private boolean hasStatusBarServicePermission(int pid, int uid) {
- return mContext.checkPermission(android.Manifest.permission.STATUS_BAR_SERVICE,
- pid, uid) == PackageManager.PERMISSION_GRANTED;
- }
-
- private void enforceStatusBarServicePermission(String action, int pid, int uid) {
- if (!hasStatusBarServicePermission(pid, uid)) {
- throw new SecurityException("Only System UI and Settings may " + action);
- }
- }
-
- /**
- * This checks if the component is an enabled notification listener for the
- * specified user. Enabled components may only operate on behalf of the user
- * they're running as.
- *
- * @param compName The component that is enabled.
- * @param userId The user id of the caller.
- * @param forUserId The user id they're making the request on behalf of.
- * @return True if the component is enabled, false otherwise
- */
- private boolean isEnabledNotificationListener(ComponentName compName, int userId,
- int forUserId) {
- if (userId != forUserId) {
- // You may not access another user's content as an enabled listener.
- return false;
- }
- if (DEBUG) {
- Log.d(TAG, "Checking if enabled notification listener " + compName);
- }
- if (compName != null) {
- try {
- return mNotificationManager.isNotificationListenerAccessGrantedForUser(
- compName, userId);
- } catch (RemoteException e) {
- Log.w(TAG, "Dead NotificationManager in isEnabledNotificationListener", e);
- }
- }
- return false;
- }
-
- private MediaSessionRecord createSessionInternal(int callerPid, int callerUid, int userId,
- String callerPackageName, ISessionCallback cb, String tag, Bundle sessionInfo)
- throws RemoteException {
- synchronized (mLock) {
- return createSessionLocked(callerPid, callerUid, userId, callerPackageName, cb,
- tag, sessionInfo);
- }
- }
-
- /*
- * When a session is created the following things need to happen.
- * 1. Its callback binder needs a link to death
- * 2. It needs to be added to all sessions.
- * 3. It needs to be added to the priority stack.
- * 4. It needs to be added to the relevant user record.
- */
- private MediaSessionRecord createSessionLocked(int callerPid, int callerUid, int userId,
- String callerPackageName, ISessionCallback cb, String tag, Bundle sessionInfo) {
- FullUserRecord user = getFullUserRecordLocked(userId);
- if (user == null) {
- Log.w(TAG, "Request from invalid user: " + userId + ", pkg=" + callerPackageName);
- throw new RuntimeException("Session request from invalid user.");
- }
-
- final MediaSessionRecord session = new MediaSessionRecord(callerPid, callerUid, userId,
- callerPackageName, cb, tag, sessionInfo, this, mHandler.getLooper());
- try {
- cb.asBinder().linkToDeath(session, 0);
- } catch (RemoteException e) {
- throw new RuntimeException("Media Session owner died prematurely.", e);
- }
-
- user.mPriorityStack.addSession(session);
- mHandler.postSessionsChanged(userId);
-
- if (DEBUG) {
- Log.d(TAG, "Created session for " + callerPackageName + " with tag " + tag);
- }
- return session;
- }
-
- private int findIndexOfSessionsListenerLocked(IActiveSessionsListener listener) {
- for (int i = mSessionsListeners.size() - 1; i >= 0; i--) {
- if (mSessionsListeners.get(i).listener.asBinder() == listener.asBinder()) {
- return i;
- }
- }
- return -1;
- }
-
- private int findIndexOfSession2TokensListenerLocked(ISession2TokensListener listener) {
- for (int i = mSession2TokensListenerRecords.size() - 1; i >= 0; i--) {
- if (mSession2TokensListenerRecords.get(i).listener.asBinder() == listener.asBinder()) {
- return i;
- }
- }
- return -1;
- }
-
-
- private void pushSessionsChanged(int userId) {
- synchronized (mLock) {
- FullUserRecord user = getFullUserRecordLocked(userId);
- if (user == null) {
- Log.w(TAG, "pushSessionsChanged failed. No user with id=" + userId);
- return;
- }
- List<MediaSessionRecord> records = getActiveSessionsLocked(userId);
- int size = records.size();
- ArrayList<MediaSession.Token> tokens = new ArrayList<MediaSession.Token>();
- for (int i = 0; i < size; i++) {
- tokens.add(records.get(i).getSessionToken());
- }
- pushRemoteVolumeUpdateLocked(userId);
- for (int i = mSessionsListeners.size() - 1; i >= 0; i--) {
- SessionsListenerRecord record = mSessionsListeners.get(i);
- if (record.userId == USER_ALL || record.userId == userId) {
- try {
- record.listener.onActiveSessionsChanged(tokens);
- } catch (RemoteException e) {
- Log.w(TAG, "Dead ActiveSessionsListener in pushSessionsChanged, removing",
- e);
- mSessionsListeners.remove(i);
- }
- }
- }
- }
- }
-
- private void pushRemoteVolumeUpdateLocked(int userId) {
- FullUserRecord user = getFullUserRecordLocked(userId);
- if (user == null) {
- Log.w(TAG, "pushRemoteVolumeUpdateLocked failed. No user with id=" + userId);
- return;
- }
-
- synchronized (mLock) {
- int size = mRemoteVolumeControllers.beginBroadcast();
- MediaSessionRecord record = user.mPriorityStack.getDefaultRemoteSession(userId);
- MediaSession.Token token = record == null ? null : record.getSessionToken();
-
- for (int i = size - 1; i >= 0; i--) {
- try {
- IRemoteVolumeController cb = mRemoteVolumeControllers.getBroadcastItem(i);
- cb.updateRemoteController(token);
- } catch (Exception e) {
- Log.w(TAG, "Error sending default remote volume.", e);
- }
- }
- mRemoteVolumeControllers.finishBroadcast();
- }
- }
-
- void pushSession2TokensChangedLocked(int userId) {
- List<Session2Token> allSession2Tokens = getSession2TokensLocked(USER_ALL);
- List<Session2Token> session2Tokens = getSession2TokensLocked(userId);
-
- for (int i = mSession2TokensListenerRecords.size() - 1; i >= 0; i--) {
- Session2TokensListenerRecord listenerRecord = mSession2TokensListenerRecords.get(i);
- try {
- if (listenerRecord.userId == USER_ALL) {
- listenerRecord.listener.onSession2TokensChanged(allSession2Tokens);
- } else if (listenerRecord.userId == userId) {
- listenerRecord.listener.onSession2TokensChanged(session2Tokens);
- }
- } catch (RemoteException e) {
- Log.w(TAG, "Failed to notify Session2Token change. Removing listener.", e);
- mSession2TokensListenerRecords.remove(i);
- }
- }
- }
-
- /**
- * Called when the media button receiver for the {@code record} is changed.
- *
- * @param record the media session whose media button receiver is updated.
- */
- public void onMediaButtonReceiverChanged(MediaSessionRecord record) {
- synchronized (mLock) {
- FullUserRecord user = getFullUserRecordLocked(record.getUserId());
- MediaSessionRecord mediaButtonSession =
- user.mPriorityStack.getMediaButtonSession();
- if (record == mediaButtonSession) {
- user.rememberMediaButtonReceiverLocked(mediaButtonSession);
- }
- }
- }
-
- private String getCallingPackageName(int uid) {
- String[] packages = mContext.getPackageManager().getPackagesForUid(uid);
- if (packages != null && packages.length > 0) {
- return packages[0];
- }
- return "";
- }
-
- private void dispatchVolumeKeyLongPressLocked(KeyEvent keyEvent) {
- if (mCurrentFullUserRecord.mOnVolumeKeyLongPressListener == null) {
- return;
- }
- try {
- mCurrentFullUserRecord.mOnVolumeKeyLongPressListener.onVolumeKeyLongPress(keyEvent);
- } catch (RemoteException e) {
- Log.w(TAG, "Failed to send " + keyEvent + " to volume key long-press listener");
- }
- }
-
- private FullUserRecord getFullUserRecordLocked(int userId) {
- int fullUserId = mFullUserIds.get(userId, -1);
- if (fullUserId < 0) {
- return null;
- }
- return mUserRecords.get(fullUserId);
- }
-
- private MediaSessionRecord getMediaSessionRecordLocked(MediaSession.Token sessionToken) {
- FullUserRecord user = getFullUserRecordLocked(UserHandle.getUserId(sessionToken.getUid()));
- if (user != null) {
- return user.mPriorityStack.getMediaSessionRecord(sessionToken);
- }
- return null;
- }
-
- /**
- * Information about a full user and its corresponding managed profiles.
- *
- * <p>Since the full user runs together with its managed profiles, a user wouldn't differentiate
- * them when he/she presses a media/volume button. So keeping media sessions for them in one
- * place makes more sense and increases the readability.</p>
- * <p>The contents of this object is guarded by {@link #mLock}.
- */
- final class FullUserRecord implements MediaSessionStack.OnMediaButtonSessionChangedListener {
- public static final int COMPONENT_TYPE_INVALID = 0;
- public static final int COMPONENT_TYPE_BROADCAST = 1;
- public static final int COMPONENT_TYPE_ACTIVITY = 2;
- public static final int COMPONENT_TYPE_SERVICE = 3;
- private static final String COMPONENT_NAME_USER_ID_DELIM = ",";
-
- private final int mFullUserId;
- private final MediaSessionStack mPriorityStack;
- private PendingIntent mLastMediaButtonReceiver;
- private ComponentName mRestoredMediaButtonReceiver;
- private int mRestoredMediaButtonReceiverComponentType;
- private int mRestoredMediaButtonReceiverUserId;
-
- private IOnVolumeKeyLongPressListener mOnVolumeKeyLongPressListener;
- private int mOnVolumeKeyLongPressListenerUid;
- private KeyEvent mInitialDownVolumeKeyEvent;
- private int mInitialDownVolumeStream;
- private boolean mInitialDownMusicOnly;
-
- private IOnMediaKeyListener mOnMediaKeyListener;
- private int mOnMediaKeyListenerUid;
- private ICallback mCallback;
-
- FullUserRecord(int fullUserId) {
- mFullUserId = fullUserId;
- mPriorityStack = new MediaSessionStack(mAudioPlayerStateMonitor, this);
- // Restore the remembered media button receiver before the boot.
- String mediaButtonReceiverInfo = Settings.Secure.getStringForUser(mContentResolver,
- Settings.System.MEDIA_BUTTON_RECEIVER, mFullUserId);
- if (mediaButtonReceiverInfo == null) {
- return;
- }
- String[] tokens = mediaButtonReceiverInfo.split(COMPONENT_NAME_USER_ID_DELIM);
- if (tokens == null || (tokens.length != 2 && tokens.length != 3)) {
- return;
- }
- mRestoredMediaButtonReceiver = ComponentName.unflattenFromString(tokens[0]);
- mRestoredMediaButtonReceiverUserId = Integer.parseInt(tokens[1]);
- if (tokens.length == 3) {
- mRestoredMediaButtonReceiverComponentType = Integer.parseInt(tokens[2]);
- } else {
- mRestoredMediaButtonReceiverComponentType =
- getComponentType(mRestoredMediaButtonReceiver);
- }
- }
-
- public void destroySessionsForUserLocked(int userId) {
- List<MediaSessionRecord> sessions = mPriorityStack.getPriorityList(false, userId);
- for (MediaSessionRecord session : sessions) {
- MediaSessionServiceImpl.this.destroySessionLocked(session);
- }
- }
-
- public void dumpLocked(PrintWriter pw, String prefix) {
- pw.print(prefix + "Record for full_user=" + mFullUserId);
- // Dump managed profile user ids associated with this user.
- int size = mFullUserIds.size();
- for (int i = 0; i < size; i++) {
- if (mFullUserIds.keyAt(i) != mFullUserIds.valueAt(i)
- && mFullUserIds.valueAt(i) == mFullUserId) {
- pw.print(", profile_user=" + mFullUserIds.keyAt(i));
- }
- }
- pw.println();
- String indent = prefix + " ";
- pw.println(indent + "Volume key long-press listener: " + mOnVolumeKeyLongPressListener);
- pw.println(indent + "Volume key long-press listener package: "
- + getCallingPackageName(mOnVolumeKeyLongPressListenerUid));
- pw.println(indent + "Media key listener: " + mOnMediaKeyListener);
- pw.println(indent + "Media key listener package: "
- + getCallingPackageName(mOnMediaKeyListenerUid));
- pw.println(indent + "Callback: " + mCallback);
- pw.println(indent + "Last MediaButtonReceiver: " + mLastMediaButtonReceiver);
- pw.println(indent + "Restored MediaButtonReceiver: " + mRestoredMediaButtonReceiver);
- pw.println(indent + "Restored MediaButtonReceiverComponentType: "
- + mRestoredMediaButtonReceiverComponentType);
- mPriorityStack.dump(pw, indent);
- pw.println(indent + "Session2Tokens:");
- for (int i = 0; i < mSession2TokensPerUser.size(); i++) {
- List<Session2Token> list = mSession2TokensPerUser.valueAt(i);
- if (list == null || list.size() == 0) {
- continue;
- }
- for (Session2Token token : list) {
- pw.println(indent + " " + token);
- }
- }
- }
-
- @Override
- public void onMediaButtonSessionChanged(MediaSessionRecord oldMediaButtonSession,
- MediaSessionRecord newMediaButtonSession) {
- if (DEBUG_KEY_EVENT) {
- Log.d(TAG, "Media button session is changed to " + newMediaButtonSession);
- }
- synchronized (mLock) {
- if (oldMediaButtonSession != null) {
- mHandler.postSessionsChanged(oldMediaButtonSession.getUserId());
- }
- if (newMediaButtonSession != null) {
- rememberMediaButtonReceiverLocked(newMediaButtonSession);
- mHandler.postSessionsChanged(newMediaButtonSession.getUserId());
- }
- pushAddressedPlayerChangedLocked();
- }
- }
-
- // Remember media button receiver and keep it in the persistent storage.
- public void rememberMediaButtonReceiverLocked(MediaSessionRecord record) {
- PendingIntent receiver = record.getMediaButtonReceiver();
- mLastMediaButtonReceiver = receiver;
- mRestoredMediaButtonReceiver = null;
- mRestoredMediaButtonReceiverComponentType = COMPONENT_TYPE_INVALID;
-
- String mediaButtonReceiverInfo = "";
- if (receiver != null) {
- ComponentName component = receiver.getIntent().getComponent();
- if (component != null
- && record.getPackageName().equals(component.getPackageName())) {
- String componentName = component.flattenToString();
- int componentType = getComponentType(component);
- mediaButtonReceiverInfo = String.join(COMPONENT_NAME_USER_ID_DELIM,
- componentName, String.valueOf(record.getUserId()),
- String.valueOf(componentType));
- }
- }
- Settings.Secure.putStringForUser(mContentResolver,
- Settings.System.MEDIA_BUTTON_RECEIVER, mediaButtonReceiverInfo,
- mFullUserId);
- }
-
- private void pushAddressedPlayerChangedLocked() {
- if (mCallback == null) {
- return;
- }
- try {
- MediaSessionRecord mediaButtonSession = getMediaButtonSessionLocked();
- if (mediaButtonSession != null) {
- mCallback.onAddressedPlayerChangedToMediaSession(
- mediaButtonSession.getSessionToken());
- } else if (mCurrentFullUserRecord.mLastMediaButtonReceiver != null) {
- mCallback.onAddressedPlayerChangedToMediaButtonReceiver(
- mCurrentFullUserRecord.mLastMediaButtonReceiver
- .getIntent().getComponent());
- } else if (mCurrentFullUserRecord.mRestoredMediaButtonReceiver != null) {
- mCallback.onAddressedPlayerChangedToMediaButtonReceiver(
- mCurrentFullUserRecord.mRestoredMediaButtonReceiver);
- }
- } catch (RemoteException e) {
- Log.w(TAG, "Failed to pushAddressedPlayerChangedLocked", e);
- }
- }
-
- private MediaSessionRecord getMediaButtonSessionLocked() {
- return isGlobalPriorityActiveLocked()
- ? mGlobalPrioritySession : mPriorityStack.getMediaButtonSession();
- }
-
- private int getComponentType(@Nullable ComponentName componentName) {
- if (componentName == null) {
- return COMPONENT_TYPE_INVALID;
- }
- PackageManager pm = mContext.getPackageManager();
- try {
- ActivityInfo activityInfo = pm.getActivityInfo(componentName,
- PackageManager.MATCH_DIRECT_BOOT_AWARE
- | PackageManager.MATCH_DIRECT_BOOT_UNAWARE
- | PackageManager.GET_ACTIVITIES);
- if (activityInfo != null) {
- return COMPONENT_TYPE_ACTIVITY;
- }
- } catch (NameNotFoundException e) {
- }
- try {
- ServiceInfo serviceInfo = pm.getServiceInfo(componentName,
- PackageManager.MATCH_DIRECT_BOOT_AWARE
- | PackageManager.MATCH_DIRECT_BOOT_UNAWARE
- | PackageManager.GET_SERVICES);
- if (serviceInfo != null) {
- return COMPONENT_TYPE_SERVICE;
- }
- } catch (NameNotFoundException e) {
- }
- // Pick legacy behavior for BroadcastReceiver or unknown.
- return COMPONENT_TYPE_BROADCAST;
- }
- }
-
- final class SessionsListenerRecord implements IBinder.DeathRecipient {
- public final IActiveSessionsListener listener;
- public final ComponentName componentName;
- public final int userId;
- public final int pid;
- public final int uid;
-
- SessionsListenerRecord(IActiveSessionsListener listener,
- ComponentName componentName,
- int userId, int pid, int uid) {
- this.listener = listener;
- this.componentName = componentName;
- this.userId = userId;
- this.pid = pid;
- this.uid = uid;
- }
-
- @Override
- public void binderDied() {
- synchronized (mLock) {
- mSessionsListeners.remove(this);
- }
- }
- }
-
- final class Session2TokensListenerRecord implements IBinder.DeathRecipient {
- public final ISession2TokensListener listener;
- public final int userId;
-
- Session2TokensListenerRecord(ISession2TokensListener listener,
- int userId) {
- this.listener = listener;
- this.userId = userId;
- }
-
- @Override
- public void binderDied() {
- synchronized (mLock) {
- mSession2TokensListenerRecords.remove(this);
- }
- }
- }
-
- final class SettingsObserver extends ContentObserver {
- private final Uri mSecureSettingsUri = Settings.Secure.getUriFor(
- Settings.Secure.ENABLED_NOTIFICATION_LISTENERS);
-
- private SettingsObserver() {
- super(null);
- }
-
- private void observe() {
- mContentResolver.registerContentObserver(mSecureSettingsUri,
- false, this, USER_ALL);
- }
-
- @Override
- public void onChange(boolean selfChange, Uri uri) {
- updateActiveSessionListeners();
- }
- }
-
- class SessionManagerImpl extends ISessionManager.Stub {
- private static final String EXTRA_WAKELOCK_ACQUIRED =
- "android.media.AudioService.WAKELOCK_ACQUIRED";
- private static final int WAKELOCK_RELEASE_ON_FINISHED = 1980; // magic number
-
- private boolean mVoiceButtonDown = false;
- private boolean mVoiceButtonHandled = false;
-
- @Override
- public ISession createSession(String packageName, ISessionCallback cb, String tag,
- Bundle sessionInfo, int userId) throws RemoteException {
- final int pid = Binder.getCallingPid();
- final int uid = Binder.getCallingUid();
- final long token = Binder.clearCallingIdentity();
- try {
- enforcePackageName(packageName, uid);
- int resolvedUserId = ActivityManager.handleIncomingUser(pid, uid, userId,
- false /* allowAll */, true /* requireFull */, "createSession", packageName);
- if (cb == null) {
- throw new IllegalArgumentException("Controller callback cannot be null");
- }
- return createSessionInternal(pid, uid, resolvedUserId, packageName, cb, tag,
- sessionInfo).getSessionBinder();
- } finally {
- Binder.restoreCallingIdentity(token);
- }
- }
-
- @Override
- public void notifySession2Created(Session2Token sessionToken) throws RemoteException {
- final int pid = Binder.getCallingPid();
- final int uid = Binder.getCallingUid();
- final long token = Binder.clearCallingIdentity();
- try {
- if (DEBUG) {
- Log.d(TAG, "Session2 is created " + sessionToken);
- }
- if (uid != sessionToken.getUid()) {
- throw new SecurityException("Unexpected Session2Token's UID, expected=" + uid
- + " but actually=" + sessionToken.getUid());
- }
- Controller2Callback callback = new Controller2Callback(sessionToken);
- // Note: It's safe not to keep controller here because it wouldn't be GC'ed until
- // it's closed.
- // TODO: Keep controller as well for better readability
- // because the GC behavior isn't straightforward.
- MediaController2 controller = new MediaController2.Builder(mContext, sessionToken)
- .setControllerCallback(new HandlerExecutor(mHandler), callback)
- .build();
- } finally {
- Binder.restoreCallingIdentity(token);
- }
- }
-
- @Override
- public List<MediaSession.Token> getSessions(ComponentName componentName, int userId) {
- final int pid = Binder.getCallingPid();
- final int uid = Binder.getCallingUid();
- final long token = Binder.clearCallingIdentity();
-
- try {
- int resolvedUserId = verifySessionsRequest(componentName, userId, pid, uid);
- ArrayList<MediaSession.Token> tokens = new ArrayList<>();
- synchronized (mLock) {
- List<MediaSessionRecord> records = getActiveSessionsLocked(resolvedUserId);
- for (MediaSessionRecord record : records) {
- tokens.add(record.getSessionToken());
- }
- }
- return tokens;
- } finally {
- Binder.restoreCallingIdentity(token);
- }
- }
-
- @Override
- public ParceledListSlice getSession2Tokens(int userId) {
- final int pid = Binder.getCallingPid();
- final int uid = Binder.getCallingUid();
- final long token = Binder.clearCallingIdentity();
-
- try {
- // Check that they can make calls on behalf of the user and
- // get the final user id
- int resolvedUserId = ActivityManager.handleIncomingUser(pid, uid, userId,
- true /* allowAll */, true /* requireFull */, "getSession2Tokens",
- null /* optional packageName */);
- List<Session2Token> result;
- synchronized (mLock) {
- result = getSession2TokensLocked(resolvedUserId);
- }
- return new ParceledListSlice(result);
- } finally {
- Binder.restoreCallingIdentity(token);
- }
- }
-
- @Override
- public void addSessionsListener(IActiveSessionsListener listener,
- ComponentName componentName, int userId) throws RemoteException {
- final int pid = Binder.getCallingPid();
- final int uid = Binder.getCallingUid();
- final long token = Binder.clearCallingIdentity();
-
- try {
- int resolvedUserId = verifySessionsRequest(componentName, userId, pid, uid);
- synchronized (mLock) {
- int index = findIndexOfSessionsListenerLocked(listener);
- if (index != -1) {
- Log.w(TAG, "ActiveSessionsListener is already added, ignoring");
- return;
- }
- SessionsListenerRecord record = new SessionsListenerRecord(listener,
- componentName, resolvedUserId, pid, uid);
- try {
- listener.asBinder().linkToDeath(record, 0);
- } catch (RemoteException e) {
- Log.e(TAG, "ActiveSessionsListener is dead, ignoring it", e);
- return;
- }
- mSessionsListeners.add(record);
- }
- } finally {
- Binder.restoreCallingIdentity(token);
- }
- }
-
- @Override
- public void removeSessionsListener(IActiveSessionsListener listener)
- throws RemoteException {
- synchronized (mLock) {
- int index = findIndexOfSessionsListenerLocked(listener);
- if (index != -1) {
- SessionsListenerRecord record = mSessionsListeners.remove(index);
- try {
- record.listener.asBinder().unlinkToDeath(record, 0);
- } catch (Exception e) {
- // ignore exceptions, the record is being removed
- }
- }
- }
- }
-
- @Override
- public void addSession2TokensListener(ISession2TokensListener listener,
- int userId) {
- final int pid = Binder.getCallingPid();
- final int uid = Binder.getCallingUid();
- final long token = Binder.clearCallingIdentity();
-
- try {
- // Check that they can make calls on behalf of the user and get the final user id.
- int resolvedUserId = ActivityManager.handleIncomingUser(pid, uid, userId,
- true /* allowAll */, true /* requireFull */, "addSession2TokensListener",
- null /* optional packageName */);
- synchronized (mLock) {
- int index = findIndexOfSession2TokensListenerLocked(listener);
- if (index >= 0) {
- Log.w(TAG, "addSession2TokensListener is already added, ignoring");
- return;
- }
- mSession2TokensListenerRecords.add(
- new Session2TokensListenerRecord(listener, resolvedUserId));
- }
- } finally {
- Binder.restoreCallingIdentity(token);
- }
- }
-
- @Override
- public void removeSession2TokensListener(ISession2TokensListener listener) {
- final int pid = Binder.getCallingPid();
- final int uid = Binder.getCallingUid();
- final long token = Binder.clearCallingIdentity();
-
- try {
- synchronized (mLock) {
- int index = findIndexOfSession2TokensListenerLocked(listener);
- if (index >= 0) {
- Session2TokensListenerRecord listenerRecord =
- mSession2TokensListenerRecords.remove(index);
- try {
- listenerRecord.listener.asBinder().unlinkToDeath(listenerRecord, 0);
- } catch (Exception e) {
- // Ignore exception.
- }
- }
- }
- } finally {
- Binder.restoreCallingIdentity(token);
- }
- }
-
- /**
- * Handles the dispatching of the media button events to one of the
- * registered listeners, or if there was none, broadcast an
- * ACTION_MEDIA_BUTTON intent to the rest of the system.
- *
- * @param packageName The caller package
- * @param asSystemService {@code true} if the event sent to the session as if it was come
- * from the system service instead of the app process. This helps sessions to
- * distinguish between the key injection by the app and key events from the
- * hardware devices. Should be used only when the volume key events aren't handled
- * by foreground activity. {@code false} otherwise to tell session about the real
- * caller.
- * @param keyEvent a non-null KeyEvent whose key code is one of the
- * supported media buttons
- * @param needWakeLock true if a PARTIAL_WAKE_LOCK needs to be held
- * while this key event is dispatched.
- */
- @Override
- public void dispatchMediaKeyEvent(String packageName, boolean asSystemService,
- KeyEvent keyEvent, boolean needWakeLock) {
- if (keyEvent == null || !KeyEvent.isMediaSessionKey(keyEvent.getKeyCode())) {
- Log.w(TAG, "Attempted to dispatch null or non-media key event.");
- return;
- }
-
- final int pid = Binder.getCallingPid();
- final int uid = Binder.getCallingUid();
- final long token = Binder.clearCallingIdentity();
- try {
- if (DEBUG) {
- Log.d(TAG, "dispatchMediaKeyEvent, pkg=" + packageName + " pid=" + pid
- + ", uid=" + uid + ", asSystem=" + asSystemService + ", event="
- + keyEvent);
- }
- if (!isUserSetupComplete()) {
- // Global media key handling can have the side-effect of starting new
- // activities which is undesirable while setup is in progress.
- Slog.i(TAG, "Not dispatching media key event because user "
- + "setup is in progress.");
- return;
- }
-
- synchronized (mLock) {
- boolean isGlobalPriorityActive = isGlobalPriorityActiveLocked();
- if (isGlobalPriorityActive && uid != Process.SYSTEM_UID) {
- // Prevent dispatching key event through reflection while the global
- // priority session is active.
- Slog.i(TAG, "Only the system can dispatch media key event "
- + "to the global priority session.");
- return;
- }
- if (!isGlobalPriorityActive) {
- if (mCurrentFullUserRecord.mOnMediaKeyListener != null) {
- if (DEBUG_KEY_EVENT) {
- Log.d(TAG, "Send " + keyEvent + " to the media key listener");
- }
- try {
- mCurrentFullUserRecord.mOnMediaKeyListener.onMediaKey(keyEvent,
- new MediaKeyListenerResultReceiver(packageName, pid, uid,
- asSystemService, keyEvent, needWakeLock));
- return;
- } catch (RemoteException e) {
- Log.w(TAG, "Failed to send " + keyEvent
- + " to the media key listener");
- }
- }
- }
- if (!isGlobalPriorityActive && isVoiceKey(keyEvent.getKeyCode())) {
- handleVoiceKeyEventLocked(packageName, pid, uid, asSystemService, keyEvent,
- needWakeLock);
- } else {
- dispatchMediaKeyEventLocked(packageName, pid, uid, asSystemService,
- keyEvent, needWakeLock);
- }
- }
- } finally {
- Binder.restoreCallingIdentity(token);
- }
- }
-
- @Override
- public boolean dispatchMediaKeyEventToSessionAsSystemService(String packageName,
- MediaSession.Token sessionToken, KeyEvent keyEvent) {
- final int pid = Binder.getCallingPid();
- final int uid = Binder.getCallingUid();
- final long token = Binder.clearCallingIdentity();
- try {
- synchronized (mLock) {
- MediaSessionRecord record = getMediaSessionRecordLocked(sessionToken);
- if (record == null) {
- if (DEBUG) {
- Log.d(TAG, "Failed to find session to dispatch key event.");
- }
- return false;
- }
- if (DEBUG) {
- Log.d(TAG, "dispatchMediaKeyEventToSessionAsSystemService, pkg="
- + packageName + ", pid=" + pid + ", uid=" + uid + ", sessionToken="
- + sessionToken + ", event=" + keyEvent + ", session=" + record);
- }
- return record.sendMediaButton(packageName, pid, uid, true /* asSystemService */,
- keyEvent, 0, null);
- }
- } finally {
- Binder.restoreCallingIdentity(token);
- }
- }
-
- @Override
- public void setCallback(ICallback callback) {
- final int pid = Binder.getCallingPid();
- final int uid = Binder.getCallingUid();
- final long token = Binder.clearCallingIdentity();
- try {
- if (!UserHandle.isSameApp(uid, Process.BLUETOOTH_UID)) {
- throw new SecurityException("Only Bluetooth service processes can set"
- + " Callback");
- }
- synchronized (mLock) {
- int userId = UserHandle.getUserId(uid);
- FullUserRecord user = getFullUserRecordLocked(userId);
- if (user == null || user.mFullUserId != userId) {
- Log.w(TAG, "Only the full user can set the callback"
- + ", userId=" + userId);
- return;
- }
- user.mCallback = callback;
- Log.d(TAG, "The callback " + user.mCallback
- + " is set by " + getCallingPackageName(uid));
- if (user.mCallback == null) {
- return;
- }
- try {
- user.mCallback.asBinder().linkToDeath(
- new IBinder.DeathRecipient() {
- @Override
- public void binderDied() {
- synchronized (mLock) {
- user.mCallback = null;
- }
- }
- }, 0);
- user.pushAddressedPlayerChangedLocked();
- } catch (RemoteException e) {
- Log.w(TAG, "Failed to set callback", e);
- user.mCallback = null;
- }
- }
- } finally {
- Binder.restoreCallingIdentity(token);
- }
- }
-
- @Override
- public void setOnVolumeKeyLongPressListener(IOnVolumeKeyLongPressListener listener) {
- final int pid = Binder.getCallingPid();
- final int uid = Binder.getCallingUid();
- final long token = Binder.clearCallingIdentity();
- try {
- // Enforce SET_VOLUME_KEY_LONG_PRESS_LISTENER permission.
- if (mContext.checkPermission(
- android.Manifest.permission.SET_VOLUME_KEY_LONG_PRESS_LISTENER, pid, uid)
- != PackageManager.PERMISSION_GRANTED) {
- throw new SecurityException("Must hold the SET_VOLUME_KEY_LONG_PRESS_LISTENER"
- + " permission.");
- }
-
- synchronized (mLock) {
- int userId = UserHandle.getUserId(uid);
- FullUserRecord user = getFullUserRecordLocked(userId);
- if (user == null || user.mFullUserId != userId) {
- Log.w(TAG, "Only the full user can set the volume key long-press listener"
- + ", userId=" + userId);
- return;
- }
- if (user.mOnVolumeKeyLongPressListener != null
- && user.mOnVolumeKeyLongPressListenerUid != uid) {
- Log.w(TAG, "The volume key long-press listener cannot be reset"
- + " by another app , mOnVolumeKeyLongPressListener="
- + user.mOnVolumeKeyLongPressListenerUid
- + ", uid=" + uid);
- return;
- }
-
- user.mOnVolumeKeyLongPressListener = listener;
- user.mOnVolumeKeyLongPressListenerUid = uid;
-
- Log.d(TAG, "The volume key long-press listener "
- + listener + " is set by " + getCallingPackageName(uid));
-
- if (user.mOnVolumeKeyLongPressListener != null) {
- try {
- user.mOnVolumeKeyLongPressListener.asBinder().linkToDeath(
- new IBinder.DeathRecipient() {
- @Override
- public void binderDied() {
- synchronized (mLock) {
- user.mOnVolumeKeyLongPressListener = null;
- }
- }
- }, 0);
- } catch (RemoteException e) {
- Log.w(TAG, "Failed to set death recipient "
- + user.mOnVolumeKeyLongPressListener);
- user.mOnVolumeKeyLongPressListener = null;
- }
- }
- }
- } finally {
- Binder.restoreCallingIdentity(token);
- }
- }
-
- @Override
- public void setOnMediaKeyListener(IOnMediaKeyListener listener) {
- final int pid = Binder.getCallingPid();
- final int uid = Binder.getCallingUid();
- final long token = Binder.clearCallingIdentity();
- try {
- // Enforce SET_MEDIA_KEY_LISTENER permission.
- if (mContext.checkPermission(
- android.Manifest.permission.SET_MEDIA_KEY_LISTENER, pid, uid)
- != PackageManager.PERMISSION_GRANTED) {
- throw new SecurityException("Must hold the SET_MEDIA_KEY_LISTENER permission.");
- }
-
- synchronized (mLock) {
- int userId = UserHandle.getUserId(uid);
- FullUserRecord user = getFullUserRecordLocked(userId);
- if (user == null || user.mFullUserId != userId) {
- Log.w(TAG, "Only the full user can set the media key listener"
- + ", userId=" + userId);
- return;
- }
- if (user.mOnMediaKeyListener != null && user.mOnMediaKeyListenerUid != uid) {
- Log.w(TAG, "The media key listener cannot be reset by another app. "
- + ", mOnMediaKeyListenerUid=" + user.mOnMediaKeyListenerUid
- + ", uid=" + uid);
- return;
- }
-
- user.mOnMediaKeyListener = listener;
- user.mOnMediaKeyListenerUid = uid;
-
- Log.d(TAG, "The media key listener " + user.mOnMediaKeyListener
- + " is set by " + getCallingPackageName(uid));
-
- if (user.mOnMediaKeyListener != null) {
- try {
- user.mOnMediaKeyListener.asBinder().linkToDeath(
- new IBinder.DeathRecipient() {
- @Override
- public void binderDied() {
- synchronized (mLock) {
- user.mOnMediaKeyListener = null;
- }
- }
- }, 0);
- } catch (RemoteException e) {
- Log.w(TAG, "Failed to set death recipient " + user.mOnMediaKeyListener);
- user.mOnMediaKeyListener = null;
- }
- }
- }
- } finally {
- Binder.restoreCallingIdentity(token);
- }
- }
-
- /**
- * Handles the dispatching of the volume button events to one of the
- * registered listeners. If there's a volume key long-press listener and
- * there's no active global priority session, long-pressess will be sent to the
- * long-press listener instead of adjusting volume.
- *
- * @param packageName The caller's package name, obtained by Context#getPackageName()
- * @param opPackageName The caller's op package name, obtained by Context#getOpPackageName()
- * @param asSystemService {@code true} if the event sent to the session as if it was come
- * from the system service instead of the app process. This helps sessions to
- * distinguish between the key injection by the app and key events from the
- * hardware devices. Should be used only when the volume key events aren't handled
- * by foreground activity. {@code false} otherwise to tell session about the real
- * caller.
- * @param keyEvent a non-null KeyEvent whose key code is one of the
- * {@link KeyEvent#KEYCODE_VOLUME_UP},
- * {@link KeyEvent#KEYCODE_VOLUME_DOWN},
- * or {@link KeyEvent#KEYCODE_VOLUME_MUTE}.
- * @param stream stream type to adjust volume.
- * @param musicOnly true if both UI nor haptic feedback aren't needed when adjust volume.
- */
- @Override
- public void dispatchVolumeKeyEvent(String packageName, String opPackageName,
- boolean asSystemService, KeyEvent keyEvent, int stream, boolean musicOnly) {
- if (keyEvent == null
- || (keyEvent.getKeyCode() != KeyEvent.KEYCODE_VOLUME_UP
- && keyEvent.getKeyCode() != KeyEvent.KEYCODE_VOLUME_DOWN
- && keyEvent.getKeyCode() != KeyEvent.KEYCODE_VOLUME_MUTE)) {
- Log.w(TAG, "Attempted to dispatch null or non-volume key event.");
- return;
- }
-
- final int pid = Binder.getCallingPid();
- final int uid = Binder.getCallingUid();
- final long token = Binder.clearCallingIdentity();
-
- if (DEBUG_KEY_EVENT) {
- Log.d(TAG, "dispatchVolumeKeyEvent, pkg=" + packageName
- + ", opPkg=" + opPackageName + ", pid=" + pid + ", uid=" + uid
- + ", asSystem=" + asSystemService + ", event=" + keyEvent
- + ", stream=" + stream + ", musicOnly=" + musicOnly);
- }
-
- try {
- synchronized (mLock) {
- if (isGlobalPriorityActiveLocked()
- || mCurrentFullUserRecord.mOnVolumeKeyLongPressListener == null) {
- dispatchVolumeKeyEventLocked(packageName, opPackageName, pid, uid,
- asSystemService, keyEvent, stream, musicOnly);
- } else {
- // TODO: Consider the case when both volume up and down keys are pressed
- // at the same time.
- if (keyEvent.getAction() == KeyEvent.ACTION_DOWN) {
- if (keyEvent.getRepeatCount() == 0) {
- // Keeps the copy of the KeyEvent because it can be reused.
- mCurrentFullUserRecord.mInitialDownVolumeKeyEvent =
- KeyEvent.obtain(keyEvent);
- mCurrentFullUserRecord.mInitialDownVolumeStream = stream;
- mCurrentFullUserRecord.mInitialDownMusicOnly = musicOnly;
- mHandler.sendMessageDelayed(
- mHandler.obtainMessage(
- MessageHandler.MSG_VOLUME_INITIAL_DOWN,
- mCurrentFullUserRecord.mFullUserId, 0),
- mLongPressTimeout);
- }
- if (keyEvent.getRepeatCount() > 0 || keyEvent.isLongPress()) {
- mHandler.removeMessages(MessageHandler.MSG_VOLUME_INITIAL_DOWN);
- if (mCurrentFullUserRecord.mInitialDownVolumeKeyEvent != null) {
- dispatchVolumeKeyLongPressLocked(
- mCurrentFullUserRecord.mInitialDownVolumeKeyEvent);
- // Mark that the key is already handled.
- mCurrentFullUserRecord.mInitialDownVolumeKeyEvent = null;
- }
- dispatchVolumeKeyLongPressLocked(keyEvent);
- }
- } else { // if up
- mHandler.removeMessages(MessageHandler.MSG_VOLUME_INITIAL_DOWN);
- if (mCurrentFullUserRecord.mInitialDownVolumeKeyEvent != null
- && mCurrentFullUserRecord.mInitialDownVolumeKeyEvent
- .getDownTime() == keyEvent.getDownTime()) {
- // Short-press. Should change volume.
- dispatchVolumeKeyEventLocked(packageName, opPackageName, pid, uid,
- asSystemService,
- mCurrentFullUserRecord.mInitialDownVolumeKeyEvent,
- mCurrentFullUserRecord.mInitialDownVolumeStream,
- mCurrentFullUserRecord.mInitialDownMusicOnly);
- dispatchVolumeKeyEventLocked(packageName, opPackageName, pid, uid,
- asSystemService, keyEvent, stream, musicOnly);
- } else {
- dispatchVolumeKeyLongPressLocked(keyEvent);
- }
- }
- }
- }
- } finally {
- Binder.restoreCallingIdentity(token);
- }
- }
-
- private void dispatchVolumeKeyEventLocked(String packageName, String opPackageName, int pid,
- int uid, boolean asSystemService, KeyEvent keyEvent, int stream,
- boolean musicOnly) {
- boolean down = keyEvent.getAction() == KeyEvent.ACTION_DOWN;
- boolean up = keyEvent.getAction() == KeyEvent.ACTION_UP;
- int direction = 0;
- boolean isMute = false;
- switch (keyEvent.getKeyCode()) {
- case KeyEvent.KEYCODE_VOLUME_UP:
- direction = AudioManager.ADJUST_RAISE;
- break;
- case KeyEvent.KEYCODE_VOLUME_DOWN:
- direction = AudioManager.ADJUST_LOWER;
- break;
- case KeyEvent.KEYCODE_VOLUME_MUTE:
- isMute = true;
- break;
- }
- if (down || up) {
- int flags = AudioManager.FLAG_FROM_KEY;
- if (musicOnly) {
- // This flag is used when the screen is off to only affect active media.
- flags |= AudioManager.FLAG_ACTIVE_MEDIA_ONLY;
- } else {
- // These flags are consistent with the home screen
- if (up) {
- flags |= AudioManager.FLAG_PLAY_SOUND | AudioManager.FLAG_VIBRATE;
- } else {
- flags |= AudioManager.FLAG_SHOW_UI | AudioManager.FLAG_VIBRATE;
- }
- }
- if (direction != 0) {
- // If this is action up we want to send a beep for non-music events
- if (up) {
- direction = 0;
- }
- dispatchAdjustVolumeLocked(packageName, opPackageName, pid, uid,
- asSystemService, stream, direction, flags);
- } else if (isMute) {
- if (down && keyEvent.getRepeatCount() == 0) {
- dispatchAdjustVolumeLocked(packageName, opPackageName, pid, uid,
- asSystemService, stream, AudioManager.ADJUST_TOGGLE_MUTE, flags);
- }
- }
- }
- }
-
- @Override
- public void dispatchVolumeKeyEventToSessionAsSystemService(String packageName,
- String opPackageName, MediaSession.Token sessionToken, KeyEvent keyEvent) {
- int pid = Binder.getCallingPid();
- int uid = Binder.getCallingUid();
- final long token = Binder.clearCallingIdentity();
- try {
- synchronized (mLock) {
- MediaSessionRecord record = getMediaSessionRecordLocked(sessionToken);
- if (record == null) {
- if (DEBUG) {
- Log.d(TAG, "Failed to find session to dispatch key event.");
- }
- return;
- }
- if (DEBUG) {
- Log.d(TAG, "dispatchVolumeKeyEventToSessionAsSystemService, pkg="
- + packageName + ", opPkg=" + opPackageName + ", pid=" + pid
- + ", uid=" + uid + ", sessionToken=" + sessionToken + ", event="
- + keyEvent + ", session=" + record);
- }
- switch (keyEvent.getAction()) {
- case KeyEvent.ACTION_DOWN: {
- int direction = 0;
- switch (keyEvent.getKeyCode()) {
- case KeyEvent.KEYCODE_VOLUME_UP:
- direction = AudioManager.ADJUST_RAISE;
- break;
- case KeyEvent.KEYCODE_VOLUME_DOWN:
- direction = AudioManager.ADJUST_LOWER;
- break;
- case KeyEvent.KEYCODE_VOLUME_MUTE:
- direction = AudioManager.ADJUST_TOGGLE_MUTE;
- break;
- }
- record.adjustVolume(packageName, opPackageName, pid, uid,
- null /* caller */, true /* asSystemService */, direction,
- AudioManager.FLAG_SHOW_UI, false /* useSuggested */);
- break;
- }
-
- case KeyEvent.ACTION_UP: {
- final int flags =
- AudioManager.FLAG_PLAY_SOUND | AudioManager.FLAG_VIBRATE
- | AudioManager.FLAG_FROM_KEY;
- record.adjustVolume(packageName, opPackageName, pid, uid,
- null /* caller */, true /* asSystemService */, 0,
- flags, false /* useSuggested */);
- }
- }
- }
- } finally {
- Binder.restoreCallingIdentity(token);
- }
- }
-
- @Override
- public void dispatchAdjustVolume(String packageName, String opPackageName,
- int suggestedStream, int delta, int flags) {
- final int pid = Binder.getCallingPid();
- final int uid = Binder.getCallingUid();
- final long token = Binder.clearCallingIdentity();
- try {
- synchronized (mLock) {
- dispatchAdjustVolumeLocked(packageName, opPackageName, pid, uid, false,
- suggestedStream, delta, flags);
- }
- } finally {
- Binder.restoreCallingIdentity(token);
- }
- }
-
- @Override
- public void registerRemoteVolumeController(IRemoteVolumeController rvc) {
- final int pid = Binder.getCallingPid();
- final int uid = Binder.getCallingUid();
- final long token = Binder.clearCallingIdentity();
- synchronized (mLock) {
- try {
- enforceStatusBarServicePermission("listen for volume changes", pid, uid);
- mRemoteVolumeControllers.register(rvc);
- } finally {
- Binder.restoreCallingIdentity(token);
- }
- }
- }
-
- @Override
- public void unregisterRemoteVolumeController(IRemoteVolumeController rvc) {
- final int pid = Binder.getCallingPid();
- final int uid = Binder.getCallingUid();
- final long token = Binder.clearCallingIdentity();
- synchronized (mLock) {
- try {
- enforceStatusBarServicePermission("listen for volume changes", pid, uid);
- mRemoteVolumeControllers.unregister(rvc);
- } finally {
- Binder.restoreCallingIdentity(token);
- }
- }
- }
-
- @Override
- public boolean isGlobalPriorityActive() {
- synchronized (mLock) {
- return isGlobalPriorityActiveLocked();
- }
- }
-
- @Override
- public void dump(FileDescriptor fd, final PrintWriter pw, String[] args) {
- if (!DumpUtils.checkDumpPermission(mContext, TAG, pw)) return;
-
- pw.println("MEDIA SESSION SERVICE (dumpsys media_session)");
- pw.println();
-
- synchronized (mLock) {
- pw.println(mSessionsListeners.size() + " sessions listeners.");
- pw.println("Global priority session is " + mGlobalPrioritySession);
- if (mGlobalPrioritySession != null) {
- mGlobalPrioritySession.dump(pw, " ");
- }
- pw.println("User Records:");
- int count = mUserRecords.size();
- for (int i = 0; i < count; i++) {
- mUserRecords.valueAt(i).dumpLocked(pw, "");
- }
- mAudioPlayerStateMonitor.dump(mContext, pw, "");
- }
- }
-
- /**
- * Returns if the controller's package is trusted (i.e. has either MEDIA_CONTENT_CONTROL
- * permission or an enabled notification listener)
- *
- * @param controllerPackageName package name of the controller app
- * @param controllerPid pid of the controller app
- * @param controllerUid uid of the controller app
- */
- @Override
- public boolean isTrusted(String controllerPackageName, int controllerPid, int controllerUid)
- throws RemoteException {
- final int uid = Binder.getCallingUid();
- final long token = Binder.clearCallingIdentity();
- try {
- // Don't perform sanity check between controllerPackageName and controllerUid.
- // When an (activity|service) runs on the another apps process by specifying
- // android:process in the AndroidManifest.xml, then PID and UID would have the
- // running process' information instead of the (activity|service) that has created
- // MediaController.
- // Note that we can use Context#getOpPackageName() instead of
- // Context#getPackageName() for getting package name that matches with the PID/UID,
- // but it doesn't tell which package has created the MediaController, so useless.
- return hasMediaControlPermission(UserHandle.getUserId(uid), controllerPackageName,
- controllerPid, controllerUid);
- } finally {
- Binder.restoreCallingIdentity(token);
- }
- }
-
- // For MediaSession
- private int verifySessionsRequest(ComponentName componentName, int userId, final int pid,
- final int uid) {
- String packageName = null;
- if (componentName != null) {
- // If they gave us a component name verify they own the
- // package
- packageName = componentName.getPackageName();
- enforcePackageName(packageName, uid);
- }
- // Check that they can make calls on behalf of the user and
- // get the final user id
- int resolvedUserId = ActivityManager.handleIncomingUser(pid, uid, userId,
- true /* allowAll */, true /* requireFull */, "getSessions", packageName);
- // Check if they have the permissions or their component is
- // enabled for the user they're calling from.
- enforceMediaPermissions(componentName, pid, uid, resolvedUserId);
- return resolvedUserId;
- }
-
- private boolean hasMediaControlPermission(int resolvedUserId, String packageName,
- int pid, int uid) throws RemoteException {
- // Allow API calls from the System UI and Settings
- if (hasStatusBarServicePermission(pid, uid)) {
- return true;
- }
-
- // Check if it's system server or has MEDIA_CONTENT_CONTROL.
- // Note that system server doesn't have MEDIA_CONTENT_CONTROL, so we need extra
- // check here.
- if (uid == Process.SYSTEM_UID || mContext.checkPermission(
- android.Manifest.permission.MEDIA_CONTENT_CONTROL, pid, uid)
- == PackageManager.PERMISSION_GRANTED) {
- return true;
- } else if (DEBUG) {
- Log.d(TAG, packageName + " (uid=" + uid + ") hasn't granted MEDIA_CONTENT_CONTROL");
- }
-
- // You may not access another user's content as an enabled listener.
- final int userId = UserHandle.getUserId(uid);
- if (resolvedUserId != userId) {
- return false;
- }
-
- // TODO(jaewan): (Post-P) Propose NotificationManager#hasEnabledNotificationListener(
- // String pkgName) to notification team for optimization
- final List<ComponentName> enabledNotificationListeners =
- mNotificationManager.getEnabledNotificationListeners(userId);
- if (enabledNotificationListeners != null) {
- for (int i = 0; i < enabledNotificationListeners.size(); i++) {
- if (TextUtils.equals(packageName,
- enabledNotificationListeners.get(i).getPackageName())) {
- return true;
- }
- }
- }
- if (DEBUG) {
- Log.d(TAG, packageName + " (uid=" + uid + ") doesn't have an enabled "
- + "notification listener");
- }
- return false;
- }
-
- private void dispatchAdjustVolumeLocked(String packageName, String opPackageName, int pid,
- int uid, boolean asSystemService, int suggestedStream, int direction, int flags) {
- MediaSessionRecord session = isGlobalPriorityActiveLocked() ? mGlobalPrioritySession
- : mCurrentFullUserRecord.mPriorityStack.getDefaultVolumeSession();
-
- boolean preferSuggestedStream = false;
- if (isValidLocalStreamType(suggestedStream)
- && AudioSystem.isStreamActive(suggestedStream, 0)) {
- preferSuggestedStream = true;
- }
- if (DEBUG_KEY_EVENT) {
- Log.d(TAG, "Adjusting " + session + " by " + direction + ". flags="
- + flags + ", suggestedStream=" + suggestedStream
- + ", preferSuggestedStream=" + preferSuggestedStream);
- }
- if (session == null || preferSuggestedStream) {
- if ((flags & AudioManager.FLAG_ACTIVE_MEDIA_ONLY) != 0
- && !AudioSystem.isStreamActive(AudioManager.STREAM_MUSIC, 0)) {
- if (DEBUG) {
- Log.d(TAG, "No active session to adjust, skipping media only volume event");
- }
- return;
- }
-
- // Execute mAudioService.adjustSuggestedStreamVolume() on
- // handler thread of MediaSessionService.
- // This will release the MediaSessionService.mLock sooner and avoid
- // a potential deadlock between MediaSessionService.mLock and
- // ActivityManagerService lock.
- mHandler.post(new Runnable() {
- @Override
- public void run() {
- final String callingOpPackageName;
- final int callingUid;
- if (asSystemService) {
- callingOpPackageName = mContext.getOpPackageName();
- callingUid = Process.myUid();
- } else {
- callingOpPackageName = opPackageName;
- callingUid = uid;
- }
- try {
- mAudioManagerInternal.adjustSuggestedStreamVolumeForUid(suggestedStream,
- direction, flags, callingOpPackageName, callingUid);
- } catch (SecurityException | IllegalArgumentException e) {
- Log.e(TAG, "Cannot adjust volume: direction=" + direction
- + ", suggestedStream=" + suggestedStream + ", flags=" + flags
- + ", packageName=" + packageName + ", uid=" + uid
- + ", asSystemService=" + asSystemService, e);
- }
- }
- });
- } else {
- session.adjustVolume(packageName, opPackageName, pid, uid, null, asSystemService,
- direction, flags, true);
- }
- }
-
- private void handleVoiceKeyEventLocked(String packageName, int pid, int uid,
- boolean asSystemService, KeyEvent keyEvent, boolean needWakeLock) {
- int action = keyEvent.getAction();
- boolean isLongPress = (keyEvent.getFlags() & KeyEvent.FLAG_LONG_PRESS) != 0;
- if (action == KeyEvent.ACTION_DOWN) {
- if (keyEvent.getRepeatCount() == 0) {
- mVoiceButtonDown = true;
- mVoiceButtonHandled = false;
- } else if (mVoiceButtonDown && !mVoiceButtonHandled && isLongPress) {
- mVoiceButtonHandled = true;
- startVoiceInput(needWakeLock);
- }
- } else if (action == KeyEvent.ACTION_UP) {
- if (mVoiceButtonDown) {
- mVoiceButtonDown = false;
- if (!mVoiceButtonHandled && !keyEvent.isCanceled()) {
- // Resend the down then send this event through
- KeyEvent downEvent = KeyEvent.changeAction(keyEvent, KeyEvent.ACTION_DOWN);
- dispatchMediaKeyEventLocked(packageName, pid, uid, asSystemService,
- downEvent, needWakeLock);
- dispatchMediaKeyEventLocked(packageName, pid, uid, asSystemService,
- keyEvent, needWakeLock);
- }
- }
- }
- }
-
- private void dispatchMediaKeyEventLocked(String packageName, int pid, int uid,
- boolean asSystemService, KeyEvent keyEvent, boolean needWakeLock) {
- MediaSessionRecord session = mCurrentFullUserRecord.getMediaButtonSessionLocked();
- if (session != null) {
- if (DEBUG_KEY_EVENT) {
- Log.d(TAG, "Sending " + keyEvent + " to " + session);
- }
- if (needWakeLock) {
- mKeyEventReceiver.aquireWakeLockLocked();
- }
- // If we don't need a wakelock use -1 as the id so we won't release it later.
- session.sendMediaButton(packageName, pid, uid, asSystemService, keyEvent,
- needWakeLock ? mKeyEventReceiver.mLastTimeoutId : -1,
- mKeyEventReceiver);
- if (mCurrentFullUserRecord.mCallback != null) {
- try {
- mCurrentFullUserRecord.mCallback.onMediaKeyEventDispatchedToMediaSession(
- keyEvent, session.getSessionToken());
- } catch (RemoteException e) {
- Log.w(TAG, "Failed to send callback", e);
- }
- }
- } else if (mCurrentFullUserRecord.mLastMediaButtonReceiver != null
- || mCurrentFullUserRecord.mRestoredMediaButtonReceiver != null) {
- if (needWakeLock) {
- mKeyEventReceiver.aquireWakeLockLocked();
- }
- Intent mediaButtonIntent = new Intent(Intent.ACTION_MEDIA_BUTTON);
- mediaButtonIntent.addFlags(Intent.FLAG_RECEIVER_FOREGROUND);
- mediaButtonIntent.putExtra(Intent.EXTRA_KEY_EVENT, keyEvent);
- // TODO: Find a way to also send PID/UID in secure way.
- String callerPackageName =
- (asSystemService) ? mContext.getPackageName() : packageName;
- mediaButtonIntent.putExtra(Intent.EXTRA_PACKAGE_NAME, callerPackageName);
- try {
- if (mCurrentFullUserRecord.mLastMediaButtonReceiver != null) {
- PendingIntent receiver = mCurrentFullUserRecord.mLastMediaButtonReceiver;
- if (DEBUG_KEY_EVENT) {
- Log.d(TAG, "Sending " + keyEvent
- + " to the last known PendingIntent " + receiver);
- }
- receiver.send(mContext,
- needWakeLock ? mKeyEventReceiver.mLastTimeoutId : -1,
- mediaButtonIntent, mKeyEventReceiver, mHandler);
- if (mCurrentFullUserRecord.mCallback != null) {
- ComponentName componentName = mCurrentFullUserRecord
- .mLastMediaButtonReceiver.getIntent().getComponent();
- if (componentName != null) {
- mCurrentFullUserRecord.mCallback
- .onMediaKeyEventDispatchedToMediaButtonReceiver(
- keyEvent, componentName);
- }
- }
- } else {
- ComponentName receiver =
- mCurrentFullUserRecord.mRestoredMediaButtonReceiver;
- int componentType = mCurrentFullUserRecord
- .mRestoredMediaButtonReceiverComponentType;
- UserHandle userHandle = UserHandle.of(mCurrentFullUserRecord
- .mRestoredMediaButtonReceiverUserId);
- if (DEBUG_KEY_EVENT) {
- Log.d(TAG, "Sending " + keyEvent + " to the restored intent "
- + receiver + ", type=" + componentType);
- }
- mediaButtonIntent.setComponent(receiver);
- try {
- switch (componentType) {
- case FullUserRecord.COMPONENT_TYPE_ACTIVITY:
- mContext.startActivityAsUser(mediaButtonIntent, userHandle);
- break;
- case FullUserRecord.COMPONENT_TYPE_SERVICE:
- mContext.startForegroundServiceAsUser(mediaButtonIntent,
- userHandle);
- break;
- default:
- // Legacy behavior for other cases.
- mContext.sendBroadcastAsUser(mediaButtonIntent, userHandle);
- }
- } catch (Exception e) {
- Log.w(TAG, "Error sending media button to the restored intent "
- + receiver + ", type=" + componentType, e);
- }
- if (mCurrentFullUserRecord.mCallback != null) {
- mCurrentFullUserRecord.mCallback
- .onMediaKeyEventDispatchedToMediaButtonReceiver(
- keyEvent, receiver);
- }
- }
- } catch (CanceledException e) {
- Log.i(TAG, "Error sending key event to media button receiver "
- + mCurrentFullUserRecord.mLastMediaButtonReceiver, e);
- } catch (RemoteException e) {
- Log.w(TAG, "Failed to send callback", e);
- }
- }
- }
-
- private void startVoiceInput(boolean needWakeLock) {
- Intent voiceIntent = null;
- // select which type of search to launch:
- // - screen on and device unlocked: action is ACTION_WEB_SEARCH
- // - device locked or screen off: action is
- // ACTION_VOICE_SEARCH_HANDS_FREE
- // with EXTRA_SECURE set to true if the device is securely locked
- PowerManager pm = (PowerManager) mContext.getSystemService(Context.POWER_SERVICE);
- boolean isLocked = mKeyguardManager != null && mKeyguardManager.isKeyguardLocked();
- if (!isLocked && pm.isScreenOn()) {
- voiceIntent = new Intent(android.speech.RecognizerIntent.ACTION_WEB_SEARCH);
- Log.i(TAG, "voice-based interactions: about to use ACTION_WEB_SEARCH");
- } else {
- voiceIntent = new Intent(RecognizerIntent.ACTION_VOICE_SEARCH_HANDS_FREE);
- voiceIntent.putExtra(RecognizerIntent.EXTRA_SECURE,
- isLocked && mKeyguardManager.isKeyguardSecure());
- Log.i(TAG, "voice-based interactions: about to use ACTION_VOICE_SEARCH_HANDS_FREE");
- }
- // start the search activity
- if (needWakeLock) {
- mMediaEventWakeLock.acquire();
- }
- try {
- if (voiceIntent != null) {
- voiceIntent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK
- | Intent.FLAG_ACTIVITY_EXCLUDE_FROM_RECENTS);
- if (DEBUG) Log.d(TAG, "voiceIntent: " + voiceIntent);
- mContext.startActivityAsUser(voiceIntent, UserHandle.CURRENT);
- }
- } catch (ActivityNotFoundException e) {
- Log.w(TAG, "No activity for search: " + e);
- } finally {
- if (needWakeLock) {
- mMediaEventWakeLock.release();
- }
- }
- }
-
- private boolean isVoiceKey(int keyCode) {
- return keyCode == KeyEvent.KEYCODE_HEADSETHOOK
- || (!mHasFeatureLeanback && keyCode == KeyEvent.KEYCODE_MEDIA_PLAY_PAUSE);
- }
-
- private boolean isUserSetupComplete() {
- return Settings.Secure.getIntForUser(mContext.getContentResolver(),
- Settings.Secure.USER_SETUP_COMPLETE, 0, UserHandle.USER_CURRENT) != 0;
- }
-
- // we only handle public stream types, which are 0-5
- private boolean isValidLocalStreamType(int streamType) {
- return streamType >= AudioManager.STREAM_VOICE_CALL
- && streamType <= AudioManager.STREAM_NOTIFICATION;
- }
-
- private class MediaKeyListenerResultReceiver extends ResultReceiver implements Runnable {
- private final String mPackageName;
- private final int mPid;
- private final int mUid;
- private final boolean mAsSystemService;
- private final KeyEvent mKeyEvent;
- private final boolean mNeedWakeLock;
- private boolean mHandled;
-
- private MediaKeyListenerResultReceiver(String packageName, int pid, int uid,
- boolean asSystemService, KeyEvent keyEvent, boolean needWakeLock) {
- super(mHandler);
- mHandler.postDelayed(this, MEDIA_KEY_LISTENER_TIMEOUT);
- mPackageName = packageName;
- mPid = pid;
- mUid = uid;
- mAsSystemService = asSystemService;
- mKeyEvent = keyEvent;
- mNeedWakeLock = needWakeLock;
- }
-
- @Override
- public void run() {
- Log.d(TAG, "The media key listener is timed-out for " + mKeyEvent);
- dispatchMediaKeyEvent();
- }
-
- @Override
- protected void onReceiveResult(int resultCode, Bundle resultData) {
- if (resultCode == MediaSessionManager.RESULT_MEDIA_KEY_HANDLED) {
- mHandled = true;
- mHandler.removeCallbacks(this);
- return;
- }
- dispatchMediaKeyEvent();
- }
-
- private void dispatchMediaKeyEvent() {
- if (mHandled) {
- return;
- }
- mHandled = true;
- mHandler.removeCallbacks(this);
- synchronized (mLock) {
- if (!isGlobalPriorityActiveLocked()
- && isVoiceKey(mKeyEvent.getKeyCode())) {
- handleVoiceKeyEventLocked(mPackageName, mPid, mUid, mAsSystemService,
- mKeyEvent, mNeedWakeLock);
- } else {
- dispatchMediaKeyEventLocked(mPackageName, mPid, mUid, mAsSystemService,
- mKeyEvent, mNeedWakeLock);
- }
- }
- }
- }
-
- private KeyEventWakeLockReceiver mKeyEventReceiver = new KeyEventWakeLockReceiver(mHandler);
-
- class KeyEventWakeLockReceiver extends ResultReceiver implements Runnable,
- PendingIntent.OnFinished {
- private final Handler mHandler;
- private int mRefCount = 0;
- private int mLastTimeoutId = 0;
-
- KeyEventWakeLockReceiver(Handler handler) {
- super(handler);
- mHandler = handler;
- }
-
- public void onTimeout() {
- synchronized (mLock) {
- if (mRefCount == 0) {
- // We've already released it, so just return
- return;
- }
- mLastTimeoutId++;
- mRefCount = 0;
- releaseWakeLockLocked();
- }
- }
-
- public void aquireWakeLockLocked() {
- if (mRefCount == 0) {
- mMediaEventWakeLock.acquire();
- }
- mRefCount++;
- mHandler.removeCallbacks(this);
- mHandler.postDelayed(this, WAKELOCK_TIMEOUT);
-
- }
-
- @Override
- public void run() {
- onTimeout();
- }
-
- @Override
- protected void onReceiveResult(int resultCode, Bundle resultData) {
- if (resultCode < mLastTimeoutId) {
- // Ignore results from calls that were before the last
- // timeout, just in case.
- return;
- } else {
- synchronized (mLock) {
- if (mRefCount > 0) {
- mRefCount--;
- if (mRefCount == 0) {
- releaseWakeLockLocked();
- }
- }
- }
- }
- }
-
- private void releaseWakeLockLocked() {
- mMediaEventWakeLock.release();
- mHandler.removeCallbacks(this);
- }
-
- @Override
- public void onSendFinished(PendingIntent pendingIntent, Intent intent, int resultCode,
- String resultData, Bundle resultExtras) {
- onReceiveResult(resultCode, null);
- }
- };
-
- BroadcastReceiver mKeyEventDone = new BroadcastReceiver() {
- @Override
- public void onReceive(Context context, Intent intent) {
- if (intent == null) {
- return;
- }
- Bundle extras = intent.getExtras();
- if (extras == null) {
- return;
- }
- synchronized (mLock) {
- if (extras.containsKey(EXTRA_WAKELOCK_ACQUIRED)
- && mMediaEventWakeLock.isHeld()) {
- mMediaEventWakeLock.release();
- }
- }
- }
- };
- }
-
- final class MessageHandler extends Handler {
- private static final int MSG_SESSIONS_CHANGED = 1;
- private static final int MSG_VOLUME_INITIAL_DOWN = 2;
- private final SparseArray<Integer> mIntegerCache = new SparseArray<>();
-
- @Override
- public void handleMessage(Message msg) {
- switch (msg.what) {
- case MSG_SESSIONS_CHANGED:
- pushSessionsChanged((int) msg.obj);
- break;
- case MSG_VOLUME_INITIAL_DOWN:
- synchronized (mLock) {
- FullUserRecord user = mUserRecords.get((int) msg.arg1);
- if (user != null && user.mInitialDownVolumeKeyEvent != null) {
- dispatchVolumeKeyLongPressLocked(user.mInitialDownVolumeKeyEvent);
- // Mark that the key is already handled.
- user.mInitialDownVolumeKeyEvent = null;
- }
- }
- break;
- }
- }
-
- public void postSessionsChanged(int userId) {
- // Use object instead of the arguments when posting message to remove pending requests.
- Integer userIdInteger = mIntegerCache.get(userId);
- if (userIdInteger == null) {
- userIdInteger = Integer.valueOf(userId);
- mIntegerCache.put(userId, userIdInteger);
- }
- removeMessages(MSG_SESSIONS_CHANGED, userIdInteger);
- obtainMessage(MSG_SESSIONS_CHANGED, userIdInteger).sendToTarget();
- }
- }
-
- private class Controller2Callback extends MediaController2.ControllerCallback {
- private final Session2Token mToken;
-
- Controller2Callback(Session2Token token) {
- mToken = token;
- }
-
- @Override
- public void onConnected(MediaController2 controller, Session2CommandGroup allowedCommands) {
- synchronized (mLock) {
- int userId = UserHandle.getUserId(mToken.getUid());
- mSession2TokensPerUser.get(userId).add(mToken);
- pushSession2TokensChangedLocked(userId);
- }
- }
-
- @Override
- public void onDisconnected(MediaController2 controller) {
- synchronized (mLock) {
- int userId = UserHandle.getUserId(mToken.getUid());
- mSession2TokensPerUser.get(userId).remove(mToken);
- pushSession2TokensChangedLocked(userId);
- }
- }
- }
-}
diff --git a/services/core/java/com/android/server/notification/NotificationManagerService.java b/services/core/java/com/android/server/notification/NotificationManagerService.java
index 3e26e013a0a5..4f859412f5f4 100644
--- a/services/core/java/com/android/server/notification/NotificationManagerService.java
+++ b/services/core/java/com/android/server/notification/NotificationManagerService.java
@@ -121,8 +121,6 @@ import android.app.backup.BackupManager;
import android.app.role.OnRoleHoldersChangedListener;
import android.app.role.RoleManager;
import android.app.usage.UsageEvents;
-import android.app.usage.UsageStats;
-import android.app.usage.UsageStatsManager;
import android.app.usage.UsageStatsManagerInternal;
import android.companion.ICompanionDeviceManager;
import android.content.BroadcastReceiver;
@@ -183,7 +181,6 @@ import android.service.notification.NotificationRankingUpdate;
import android.service.notification.NotificationRecordProto;
import android.service.notification.NotificationServiceDumpProto;
import android.service.notification.NotificationStats;
-import android.service.notification.NotifyingApp;
import android.service.notification.SnoozeCriterion;
import android.service.notification.StatusBarNotification;
import android.service.notification.ZenModeConfig;
@@ -260,8 +257,6 @@ import java.nio.charset.StandardCharsets;
import java.util.ArrayDeque;
import java.util.ArrayList;
import java.util.Arrays;
-import java.util.Calendar;
-import java.util.GregorianCalendar;
import java.util.Iterator;
import java.util.List;
import java.util.Map.Entry;
@@ -2467,7 +2462,8 @@ public class NotificationManagerService extends SystemService {
*/
@Override
public boolean areNotificationsEnabledForPackage(String pkg, int uid) {
- checkCallerIsSystemOrSameApp(pkg);
+ enforceSystemOrSystemUIOrSamePackage(pkg,
+ "Caller not system or systemui or same package");
if (UserHandle.getCallingUserId() != UserHandle.getUserId(uid)) {
getContext().enforceCallingPermission(
android.Manifest.permission.INTERACT_ACROSS_USERS,
@@ -2793,7 +2789,7 @@ public class NotificationManagerService extends SystemService {
@Override
public ParceledListSlice<NotificationChannelGroup> getNotificationChannelGroupsForPackage(
String pkg, int uid, boolean includeDeleted) {
- checkCallerIsSystem();
+ enforceSystemOrSystemUI("getNotificationChannelGroupsForPackage");
return mPreferencesHelper.getNotificationChannelGroups(
pkg, uid, includeDeleted, true, false);
}
diff --git a/services/core/java/com/android/server/pm/ApexManager.java b/services/core/java/com/android/server/pm/ApexManager.java
index 497385fef39c..dd2d300f35d8 100644
--- a/services/core/java/com/android/server/pm/ApexManager.java
+++ b/services/core/java/com/android/server/pm/ApexManager.java
@@ -22,131 +22,114 @@ import android.apex.ApexInfo;
import android.apex.ApexInfoList;
import android.apex.ApexSessionInfo;
import android.apex.IApexService;
+import android.content.BroadcastReceiver;
import android.content.Context;
+import android.content.Intent;
+import android.content.IntentFilter;
import android.content.pm.PackageInfo;
import android.content.pm.PackageManager;
import android.content.pm.PackageParser;
import android.content.pm.PackageParser.PackageParserException;
-import android.os.HandlerThread;
import android.os.RemoteException;
import android.os.ServiceManager;
import android.os.ServiceManager.ServiceNotFoundException;
-import android.os.SystemClock;
import android.sysprop.ApexProperties;
+import android.util.ArrayMap;
import android.util.Slog;
+import com.android.internal.annotations.GuardedBy;
import com.android.internal.util.IndentingPrintWriter;
-import com.android.server.SystemService;
import java.io.File;
import java.io.PrintWriter;
-import java.util.ArrayList;
import java.util.Collection;
import java.util.Collections;
-import java.util.List;
-import java.util.Map;
-import java.util.concurrent.CountDownLatch;
-import java.util.function.Function;
-import java.util.stream.Collectors;
/**
* ApexManager class handles communications with the apex service to perform operation and queries,
* as well as providing caching to avoid unnecessary calls to the service.
- *
- * @hide
*/
-public final class ApexManager extends SystemService {
- private static final String TAG = "ApexManager";
- private IApexService mApexService;
-
- private final CountDownLatch mActivePackagesCacheLatch = new CountDownLatch(1);
- private Map<String, PackageInfo> mActivePackagesCache;
-
- private final CountDownLatch mApexFilesCacheLatch = new CountDownLatch(1);
- private ApexInfo[] mApexFiles;
-
- public ApexManager(Context context) {
- super(context);
- }
+class ApexManager {
+ static final String TAG = "ApexManager";
+ private final IApexService mApexService;
+ private final Context mContext;
+ private final Object mLock = new Object();
+ /**
+ * A map from {@code APEX packageName} to the {@Link PackageInfo} generated from the {@code
+ * AndroidManifest.xml}
+ *
+ * <p>Note that key of this map is {@code packageName} field of the corresponding {@code
+ * AndroidManfiset.xml}.
+ */
+ @GuardedBy("mLock")
+ private ArrayMap<String, PackageInfo> mActivePackagesCache;
+ /**
+ * A map from {@code apexName} to the {@Link PackageInfo} generated from the {@code
+ * AndroidManifest.xml}.
+ *
+ * <p>Note that key of this map is {@code apexName} field which corresponds to the {@code name}
+ * field of {@code apex_manifest.json}.
+ */
+ // TODO(b/132324953): remove.
+ @GuardedBy("mLock")
+ private ArrayMap<String, PackageInfo> mApexNameToPackageInfoCache;
- @Override
- public void onStart() {
+ ApexManager(Context context) {
try {
mApexService = IApexService.Stub.asInterface(
- ServiceManager.getServiceOrThrow("apexservice"));
+ ServiceManager.getServiceOrThrow("apexservice"));
} catch (ServiceNotFoundException e) {
throw new IllegalStateException("Required service apexservice not available");
}
- publishLocalService(ApexManager.class, this);
- HandlerThread oneShotThread = new HandlerThread("ApexManagerOneShotHandler");
- oneShotThread.start();
- oneShotThread.getThreadHandler().post(this::initSequence);
- oneShotThread.quitSafely();
+ mContext = context;
}
- private void initSequence() {
- populateApexFilesCache();
- parseApexFiles();
- }
-
- private void populateApexFilesCache() {
- if (mApexFiles != null) {
- return;
- }
- long startTimeMicros = SystemClock.currentTimeMicro();
- Slog.i(TAG, "Starting to populate apex files cache");
- try {
- mApexFiles = mApexService.getActivePackages();
- Slog.i(TAG, "IPC to apexd finished in " + (SystemClock.currentTimeMicro()
- - startTimeMicros) + " μs");
- } catch (RemoteException re) {
- // TODO: make sure this error is propagated to system server.
- Slog.e(TAG, "Unable to retrieve packages from apexservice: " + re.toString());
- re.rethrowAsRuntimeException();
- }
- mApexFilesCacheLatch.countDown();
- Slog.i(TAG, "Finished populating apex files cache in " + (SystemClock.currentTimeMicro()
- - startTimeMicros) + " μs");
+ void systemReady() {
+ mContext.registerReceiver(new BroadcastReceiver() {
+ @Override
+ public void onReceive(Context context, Intent intent) {
+ onBootCompleted();
+ mContext.unregisterReceiver(this);
+ }
+ }, new IntentFilter(Intent.ACTION_BOOT_COMPLETED));
}
- private void parseApexFiles() {
- waitForLatch(mApexFilesCacheLatch);
- if (mApexFiles == null) {
- throw new IllegalStateException("mApexFiles must be populated");
- }
- long startTimeMicros = SystemClock.currentTimeMicro();
- Slog.i(TAG, "Starting to parse apex files");
- List<PackageInfo> list = new ArrayList<>();
- // TODO: this can be parallelized.
- for (ApexInfo ai : mApexFiles) {
+ private void populateActivePackagesCacheIfNeeded() {
+ synchronized (mLock) {
+ if (mActivePackagesCache != null) {
+ return;
+ }
+ mActivePackagesCache = new ArrayMap<>();
+ mApexNameToPackageInfoCache = new ArrayMap<>();
try {
- // If the device is using flattened APEX, don't report any APEX
- // packages since they won't be managed or updated by PackageManager.
- if ((new File(ai.packagePath)).isDirectory()) {
- break;
+ final ApexInfo[] activePkgs = mApexService.getActivePackages();
+ for (ApexInfo ai : activePkgs) {
+ // If the device is using flattened APEX, don't report any APEX
+ // packages since they won't be managed or updated by PackageManager.
+ if ((new File(ai.packagePath)).isDirectory()) {
+ break;
+ }
+ try {
+ final PackageInfo pkg = PackageParser.generatePackageInfoFromApex(
+ new File(ai.packagePath), PackageManager.GET_META_DATA
+ | PackageManager.GET_SIGNING_CERTIFICATES);
+ mActivePackagesCache.put(pkg.packageName, pkg);
+ // TODO(b/132324953): remove.
+ mApexNameToPackageInfoCache.put(ai.packageName, pkg);
+ } catch (PackageParserException pe) {
+ throw new IllegalStateException("Unable to parse: " + ai, pe);
+ }
}
- list.add(PackageParser.generatePackageInfoFromApex(
- new File(ai.packagePath), PackageManager.GET_META_DATA
- | PackageManager.GET_SIGNING_CERTIFICATES));
- } catch (PackageParserException pe) {
- // TODO: make sure this error is propagated to system server.
- throw new IllegalStateException("Unable to parse: " + ai, pe);
+ } catch (RemoteException re) {
+ Slog.e(TAG, "Unable to retrieve packages from apexservice: " + re.toString());
+ throw new RuntimeException(re);
}
}
- mActivePackagesCache = list.stream().collect(
- Collectors.toMap(p -> p.packageName, Function.identity()));
- mActivePackagesCacheLatch.countDown();
- Slog.i(TAG, "Finished parsing apex files in " + (SystemClock.currentTimeMicro()
- - startTimeMicros) + " μs");
}
/**
* Retrieves information about an active APEX package.
*
- * <p>This method blocks caller thread until {@link #parseApexFiles()} succeeds. Note that in
- * case {@link #parseApexFiles()}} throws an exception this method will never finish
- * essentially putting device into a boot loop.
- *
* @param packageName the package name to look for. Note that this is the package name reported
* in the APK container manifest (i.e. AndroidManifest.xml), which might
* differ from the one reported in the APEX manifest (i.e.
@@ -155,43 +138,42 @@ public final class ApexManager extends SystemService {
* is not found.
*/
@Nullable PackageInfo getActivePackage(String packageName) {
- waitForLatch(mActivePackagesCacheLatch);
+ populateActivePackagesCacheIfNeeded();
return mActivePackagesCache.get(packageName);
}
/**
- * Retrieves information about all active APEX packages.
+ * Returns a {@link PackageInfo} for an APEX package keyed by it's {@code apexName}.
*
- * <p>This method blocks caller thread until {@link #parseApexFiles()} succeeds. Note that in
- * case {@link #parseApexFiles()}} throws an exception this method will never finish
- * essentially putting device into a boot loop.
+ * @deprecated this API will soon be deleted, please don't depend on it.
+ */
+ // TODO(b/132324953): delete.
+ @Deprecated
+ @Nullable PackageInfo getPackageInfoForApexName(String apexName) {
+ populateActivePackagesCacheIfNeeded();
+ return mApexNameToPackageInfoCache.get(apexName);
+ }
+
+ /**
+ * Retrieves information about all active APEX packages.
*
* @return a Collection of PackageInfo object, each one containing information about a different
* active package.
*/
Collection<PackageInfo> getActivePackages() {
- waitForLatch(mActivePackagesCacheLatch);
+ populateActivePackagesCacheIfNeeded();
return mActivePackagesCache.values();
}
/**
* Checks if {@code packageName} is an apex package.
*
- * <p>This method blocks caller thread until {@link #populateApexFilesCache()} succeeds. Note
- * that in case {@link #populateApexFilesCache()} throws an exception this method will never
- * finish essentially putting device into a boot loop.
- *
* @param packageName package to check.
* @return {@code true} if {@code packageName} is an apex package.
*/
boolean isApexPackage(String packageName) {
- waitForLatch(mApexFilesCacheLatch);
- for (ApexInfo ai : mApexFiles) {
- if (ai.packageName.equals(packageName)) {
- return true;
- }
- }
- return false;
+ populateActivePackagesCacheIfNeeded();
+ return mActivePackagesCache.containsKey(packageName);
}
/**
@@ -319,19 +301,6 @@ public final class ApexManager extends SystemService {
}
/**
- * Blocks current thread until {@code latch} has counted down to zero.
- *
- * @throws RuntimeException if thread was interrupted while waiting.
- */
- private void waitForLatch(CountDownLatch latch) {
- try {
- latch.await();
- } catch (InterruptedException e) {
- throw new RuntimeException("Interrupted waiting for cache to be populated", e);
- }
- }
-
- /**
* Dumps various state information to the provided {@link PrintWriter} object.
*
* @param pw the {@link PrintWriter} object to send information to.
@@ -344,7 +313,7 @@ public final class ApexManager extends SystemService {
ipw.println("Active APEX packages:");
ipw.increaseIndent();
try {
- waitForLatch(mActivePackagesCacheLatch);
+ populateActivePackagesCacheIfNeeded();
for (PackageInfo pi : mActivePackagesCache.values()) {
if (packageName != null && !packageName.equals(pi.packageName)) {
continue;
@@ -389,4 +358,8 @@ public final class ApexManager extends SystemService {
ipw.println("Couldn't communicate with apexd.");
}
}
+
+ public void onBootCompleted() {
+ populateActivePackagesCacheIfNeeded();
+ }
}
diff --git a/services/core/java/com/android/server/pm/PackageDexOptimizer.java b/services/core/java/com/android/server/pm/PackageDexOptimizer.java
index 7f346f5accda..65947511bc1d 100644
--- a/services/core/java/com/android/server/pm/PackageDexOptimizer.java
+++ b/services/core/java/com/android/server/pm/PackageDexOptimizer.java
@@ -506,15 +506,27 @@ public class PackageDexOptimizer {
*/
private String getRealCompilerFilter(ApplicationInfo info, String targetCompilerFilter,
boolean isUsedByOtherApps) {
- int flags = info.flags;
- boolean vmSafeMode = (flags & ApplicationInfo.FLAG_VM_SAFE_MODE) != 0;
// When an app or priv app is configured to run out of box, only verify it.
if (info.isEmbeddedDexUsed()
|| (info.isPrivilegedApp()
&& DexManager.isPackageSelectedToRunOob(info.packageName))) {
return "verify";
}
- if (vmSafeMode) {
+
+ // We force vmSafeMode on debuggable apps as well:
+ // - the runtime ignores their compiled code
+ // - they generally have lots of methods that could make the compiler used run
+ // out of memory (b/130828957)
+ // Note that forcing the compiler filter here applies to all compilations (even if they
+ // are done via adb shell commands). That's ok because right now the runtime will ignore
+ // the compiled code anyway. The alternative would have been to update either
+ // PackageDexOptimizer#canOptimizePackage or PackageManagerService#getOptimizablePackages
+ // but that would have the downside of possibly producing a big odex files which would
+ // be ignored anyway.
+ boolean vmSafeModeOrDebuggable = ((info.flags & ApplicationInfo.FLAG_VM_SAFE_MODE) != 0)
+ || ((info.flags & ApplicationInfo.FLAG_DEBUGGABLE) != 0);
+
+ if (vmSafeModeOrDebuggable) {
return getSafeModeCompilerFilter(targetCompilerFilter);
}
diff --git a/services/core/java/com/android/server/pm/PackageInstallerService.java b/services/core/java/com/android/server/pm/PackageInstallerService.java
index 35f21496f2cc..44f76774fc8a 100644
--- a/services/core/java/com/android/server/pm/PackageInstallerService.java
+++ b/services/core/java/com/android/server/pm/PackageInstallerService.java
@@ -363,8 +363,7 @@ public class PackageInstallerService extends IPackageInstaller.Stub implements
System.currentTimeMillis() - session.getUpdatedMillis();
final boolean valid;
if (session.isStaged()) {
- if (timeSinceUpdate >= MAX_TIME_SINCE_UPDATE_MILLIS
- && session.isStagedAndInTerminalState()) {
+ if (timeSinceUpdate >= MAX_TIME_SINCE_UPDATE_MILLIS) {
valid = false;
} else {
valid = true;
diff --git a/services/core/java/com/android/server/pm/PackageInstallerSession.java b/services/core/java/com/android/server/pm/PackageInstallerSession.java
index 5f6e7399f3a7..6f9a918d105c 100644
--- a/services/core/java/com/android/server/pm/PackageInstallerSession.java
+++ b/services/core/java/com/android/server/pm/PackageInstallerSession.java
@@ -1150,7 +1150,7 @@ public class PackageInstallerSession extends IPackageInstallerSession.Stub {
*/
void sealAndValidateIfNecessary() {
synchronized (mLock) {
- if (!mShouldBeSealed) {
+ if (!mShouldBeSealed || isStagedAndInTerminalState()) {
return;
}
}
diff --git a/services/core/java/com/android/server/pm/PackageManagerService.java b/services/core/java/com/android/server/pm/PackageManagerService.java
index ed83cbced49f..5eb9d500e584 100644
--- a/services/core/java/com/android/server/pm/PackageManagerService.java
+++ b/services/core/java/com/android/server/pm/PackageManagerService.java
@@ -939,7 +939,6 @@ public class PackageManagerService extends IPackageManager.Stub
ComponentName mCustomResolverComponentName;
boolean mResolverReplaced = false;
- boolean mOkToReplacePersistentPackages = false;
private final @Nullable ComponentName mIntentFilterVerifierComponent;
private final @Nullable IntentFilterVerifier<ActivityIntentInfo> mIntentFilterVerifier;
@@ -1009,6 +1008,9 @@ public class PackageManagerService extends IPackageManager.Stub
private PackageManagerInternal.DefaultBrowserProvider mDefaultBrowserProvider;
@GuardedBy("mPackages")
+ private PackageManagerInternal.DefaultDialerProvider mDefaultDialerProvider;
+
+ @GuardedBy("mPackages")
private PackageManagerInternal.DefaultHomeProvider mDefaultHomeProvider;
private class IntentVerifierProxy implements IntentFilterVerifier<ActivityIntentInfo> {
@@ -2375,8 +2377,6 @@ public class PackageManagerService extends IPackageManager.Stub
public PackageManagerService(Context context, Installer installer,
boolean factoryTest, boolean onlyCore) {
- mApexManager = LocalServices.getService(ApexManager.class);
-
LockGuard.installLock(mPackages, LockGuard.INDEX_PACKAGES);
Trace.traceBegin(TRACE_TAG_PACKAGE_MANAGER, "create package manager");
EventLog.writeEvent(EventLogTags.BOOT_PROGRESS_PMS_START,
@@ -2473,6 +2473,7 @@ public class PackageManagerService extends IPackageManager.Stub
mProtectedPackages = new ProtectedPackages(mContext);
+ mApexManager = new ApexManager(context);
synchronized (mInstallLock) {
// writer
synchronized (mPackages) {
@@ -10338,31 +10339,6 @@ public class PackageManagerService extends IPackageManager.Stub
} catch (InstallerException e) {
Slog.w(TAG, String.valueOf(e));
}
- // If this package doesn't have a sharedUserId or there are no other packages
- // present with same sharedUserId, then delete the sandbox data too.
- try {
- final SharedUserSetting sharedUserSetting = mSettings.getSharedUserLPw(
- pkg.mSharedUserId, 0 /* pkgFlags */,
- 0 /* pkgPrivateFlags */, false /* create */);
- boolean deleteSandboxData = true;
- if (sharedUserSetting != null && sharedUserSetting.packages != null) {
- for (int i = sharedUserSetting.packages.size() - 1; i >= 0; --i) {
- final PackageSetting packageSetting = sharedUserSetting.packages.valueAt(i);
- if (!packageSetting.name.equals(pkg.packageName)
- && packageSetting.readUserState(realUserId).isAvailable(
- MATCH_UNINSTALLED_PACKAGES)) {
- deleteSandboxData = false;
- break;
- }
- }
- }
- if (deleteSandboxData && getStorageManagerInternal() != null) {
- getStorageManagerInternal().destroySandboxForApp(pkg.packageName,
- pkg.mSharedUserId, realUserId);
- }
- } catch (PackageManagerException e) {
- // Should not happen
- }
mDexManager.notifyPackageDataDestroyed(pkg.packageName, userId);
}
}
@@ -14003,10 +13979,17 @@ public class PackageManagerService extends IPackageManager.Stub
return resolveInfo == null ? null : resolveInfo.activityInfo.packageName;
}
- private String getDefaultDialerPackageName(int userId) {
+ @Nullable
+ private String getDefaultDialerPackageName(@UserIdInt int userId) {
+ PackageManagerInternal.DefaultDialerProvider provider;
synchronized (mPackages) {
- return mSettings.getDefaultDialerPackageNameLPw(userId);
+ provider = mDefaultDialerProvider;
+ }
+ if (provider == null) {
+ Slog.e(TAG, "mDefaultDialerProvider is null");
+ return null;
}
+ return provider.getDefaultDialer(userId);
}
@Override
@@ -17392,7 +17375,7 @@ public class PackageManagerService extends IPackageManager.Stub
}
// Prevent persistent apps from being updated
if (((oldPackage.applicationInfo.flags & ApplicationInfo.FLAG_PERSISTENT) != 0)
- && !mOkToReplacePersistentPackages) {
+ && ((installFlags & PackageManager.INSTALL_STAGED) == 0)) {
throw new PrepareFailure(PackageManager.INSTALL_FAILED_INVALID_APK,
"Package " + oldPackage.packageName + " is a persistent app. "
+ "Persistent apps are not updateable.");
@@ -21531,6 +21514,7 @@ public class PackageManagerService extends IPackageManager.Stub
storage.registerListener(mStorageListener);
mInstallerService.systemReady();
+ mApexManager.systemReady();
mPackageDexOptimizer.systemReady();
getStorageManagerInternal().addExternalStoragePolicy(
@@ -21573,12 +21557,10 @@ public class PackageManagerService extends IPackageManager.Stub
mModuleInfoProvider.systemReady();
- mOkToReplacePersistentPackages = true;
// Installer service might attempt to install some packages that have been staged for
// installation on reboot. Make sure this is the last component to be call since the
// installation might require other components to be ready.
mInstallerService.restoreAndApplyStagedSessionIfNeeded();
- mOkToReplacePersistentPackages = false;
}
public void waitForAppDataPrepared() {
@@ -22933,10 +22915,6 @@ public class PackageManagerService extends IPackageManager.Stub
}
prepareAppDataContentsLeafLIF(pkg, userId, flags);
- if (getStorageManagerInternal() != null) {
- getStorageManagerInternal().prepareSandboxForApp(
- pkg.packageName, appId, pkg.mSharedUserId, userId);
- }
}
private void prepareAppDataContentsLIF(PackageParser.Package pkg, int userId, int flags) {
@@ -24240,13 +24218,6 @@ public class PackageManagerService extends IPackageManager.Stub
}
@Override
- public void onDefaultDialerAppChanged(String packageName, int userId) {
- synchronized (mPackages) {
- mSettings.setDefaultDialerPackageNameLPw(packageName, userId);
- }
- }
-
- @Override
public void grantDefaultPermissionsToDefaultUseOpenWifiApp(String packageName, int userId) {
mDefaultPermissionPolicy.grantDefaultPermissionsToDefaultUseOpenWifiApp(
packageName, userId);
@@ -24792,6 +24763,13 @@ public class PackageManagerService extends IPackageManager.Stub
}
@Override
+ public void setDefaultDialerProvider(@NonNull DefaultDialerProvider provider) {
+ synchronized (mPackages) {
+ mDefaultDialerProvider = provider;
+ }
+ }
+
+ @Override
public void setDefaultHomeProvider(@NonNull DefaultHomeProvider provider) {
synchronized (mPackages) {
mDefaultHomeProvider = provider;
diff --git a/services/core/java/com/android/server/pm/Settings.java b/services/core/java/com/android/server/pm/Settings.java
index 2a9cb8998cac..4e897d2a5b64 100644
--- a/services/core/java/com/android/server/pm/Settings.java
+++ b/services/core/java/com/android/server/pm/Settings.java
@@ -362,9 +362,6 @@ public final class Settings {
// For every user, it is used to find the package name of the default Browser App.
final SparseArray<String> mDefaultBrowserApp = new SparseArray<String>();
- // For every user, a record of the package name of the default Dialer App.
- final SparseArray<String> mDefaultDialerApp = new SparseArray<String>();
-
// App-link priority tracking, per-user
final SparseIntArray mNextAppLinkGeneration = new SparseIntArray();
@@ -1270,19 +1267,6 @@ public final class Settings {
return (userId == UserHandle.USER_ALL) ? null : mDefaultBrowserApp.removeReturnOld(userId);
}
- boolean setDefaultDialerPackageNameLPw(String packageName, int userId) {
- if (userId == UserHandle.USER_ALL) {
- return false;
- }
- mDefaultDialerApp.put(userId, packageName);
- writePackageRestrictionsLPr(userId);
- return true;
- }
-
- String getDefaultDialerPackageNameLPw(int userId) {
- return (userId == UserHandle.USER_ALL) ? null : mDefaultDialerApp.get(userId);
- }
-
private File getUserPackagesStateFile(int userId) {
// TODO: Implement a cleaner solution when adding tests.
// This instead of Environment.getUserSystemDirectory(userId) to support testing.
@@ -1482,8 +1466,7 @@ public final class Settings {
String packageName = parser.getAttributeValue(null, ATTR_PACKAGE_NAME);
mDefaultBrowserApp.put(userId, packageName);
} else if (tagName.equals(TAG_DEFAULT_DIALER)) {
- String packageName = parser.getAttributeValue(null, ATTR_PACKAGE_NAME);
- mDefaultDialerApp.put(userId, packageName);
+ // Ignored.
} else {
String msg = "Unknown element under " + TAG_DEFAULT_APPS + ": " +
parser.getName();
@@ -1938,12 +1921,6 @@ public final class Settings {
serializer.attribute(null, ATTR_PACKAGE_NAME, defaultBrowser);
serializer.endTag(null, TAG_DEFAULT_BROWSER);
}
- String defaultDialer = mDefaultDialerApp.get(userId);
- if (!TextUtils.isEmpty(defaultDialer)) {
- serializer.startTag(null, TAG_DEFAULT_DIALER);
- serializer.attribute(null, ATTR_PACKAGE_NAME, defaultDialer);
- serializer.endTag(null, TAG_DEFAULT_DIALER);
- }
serializer.endTag(null, TAG_DEFAULT_APPS);
}
@@ -2575,10 +2552,6 @@ public final class Settings {
writeKernelMappingLPr(ps);
}
- for (final SharedUserSetting sus : mSharedUsers.values()) {
- knownSet.remove(sus.getStorageSandboxName());
- }
-
// Remove any unclaimed mappings
for (int i = 0; i < knownSet.size(); i++) {
final String name = knownSet.valueAt(i);
@@ -2589,20 +2562,10 @@ public final class Settings {
}
}
- void writeKernelMappingLPr(SharedUserSetting sus) {
- if (mKernelMappingFilename == null || sus == null || sus.name == null) return;
-
- writeKernelMappingLPr(sus.getStorageSandboxName(),
- sus.userId, sus.getNotInstalledUserIds());
- }
-
void writeKernelMappingLPr(PackageSetting ps) {
if (mKernelMappingFilename == null || ps == null || ps.name == null) return;
writeKernelMappingLPr(ps.name, ps.appId, ps.getNotInstalledUserIds());
- if (ps.sharedUser != null) {
- writeKernelMappingLPr(ps.sharedUser);
- }
}
void writeKernelMappingLPr(String name, int appId, int[] excludedUserIds) {
diff --git a/services/core/java/com/android/server/pm/SharedUserSetting.java b/services/core/java/com/android/server/pm/SharedUserSetting.java
index d67144e8ce39..cbc9124b8476 100644
--- a/services/core/java/com/android/server/pm/SharedUserSetting.java
+++ b/services/core/java/com/android/server/pm/SharedUserSetting.java
@@ -19,7 +19,6 @@ package com.android.server.pm;
import android.annotation.Nullable;
import android.content.pm.ApplicationInfo;
import android.content.pm.PackageParser;
-import android.os.storage.StorageManager;
import android.service.pm.PackageServiceDumpProto;
import android.util.ArraySet;
import android.util.proto.ProtoOutputStream;
@@ -167,10 +166,6 @@ public final class SharedUserSetting extends SettingBase {
return excludedUserIds == null ? EmptyArray.INT : excludedUserIds;
}
- public String getStorageSandboxName() {
- return StorageManager.SHARED_SANDBOX_PREFIX + name;
- }
-
/** Updates all fields in this shared user setting from another. */
public SharedUserSetting updateFrom(SharedUserSetting sharedUser) {
copyFrom(sharedUser);
diff --git a/services/core/java/com/android/server/pm/StagingManager.java b/services/core/java/com/android/server/pm/StagingManager.java
index 170d0850bf0f..24bf18de13c8 100644
--- a/services/core/java/com/android/server/pm/StagingManager.java
+++ b/services/core/java/com/android/server/pm/StagingManager.java
@@ -113,7 +113,7 @@ public class StagingManager {
return false;
}
- final PackageInfo packageInfo = mApexManager.getActivePackage(packageName);
+ final PackageInfo packageInfo = mApexManager.getPackageInfoForApexName(packageName);
if (packageInfo == null) {
// Only allow installing new apexes if on a debuggable build.
@@ -158,7 +158,8 @@ public class StagingManager {
return false;
}
for (ApexInfo newPackage : apexInfoList.apexInfos) {
- PackageInfo activePackage = mApexManager.getActivePackage(newPackage.packageName);
+ PackageInfo activePackage = mApexManager.getPackageInfoForApexName(
+ newPackage.packageName);
if (activePackage == null) {
continue;
}
@@ -383,6 +384,7 @@ public class StagingManager {
PackageInstaller.SessionParams params = originalSession.params.copy();
params.isStaged = false;
params.installFlags |= PackageManager.INSTALL_DISABLE_VERIFICATION;
+ params.installFlags |= PackageManager.INSTALL_STAGED;
// TODO(b/129744602): use the userid from the original session.
int apkSessionId = mPi.createSession(
params, originalSession.getInstallerPackageName(),
diff --git a/services/core/java/com/android/server/pm/permission/DefaultPermissionGrantPolicy.java b/services/core/java/com/android/server/pm/permission/DefaultPermissionGrantPolicy.java
index 4fdf1bc58e05..82737521aa3a 100644
--- a/services/core/java/com/android/server/pm/permission/DefaultPermissionGrantPolicy.java
+++ b/services/core/java/com/android/server/pm/permission/DefaultPermissionGrantPolicy.java
@@ -849,21 +849,6 @@ public final class DefaultPermissionGrantPolicy {
grantPermissionsToSystemPackage(useOpenWifiPackage, userId, ALWAYS_LOCATION_PERMISSIONS);
}
- public void grantDefaultPermissionsToDefaultSmsApp(String packageName, int userId) {
- Log.i(TAG, "Granting permissions to default sms app for user:" + userId);
- grantIgnoringSystemPackage(packageName, userId,
- PHONE_PERMISSIONS, CONTACTS_PERMISSIONS, SMS_PERMISSIONS, STORAGE_PERMISSIONS,
- MICROPHONE_PERMISSIONS, CAMERA_PERMISSIONS);
- }
-
- public void grantDefaultPermissionsToDefaultDialerApp(String packageName, int userId) {
- mServiceInternal.onDefaultDialerAppChanged(packageName, userId);
- Log.i(TAG, "Granting permissions to default dialer app for user:" + userId);
- grantIgnoringSystemPackage(packageName, userId,
- PHONE_PERMISSIONS, CONTACTS_PERMISSIONS, SMS_PERMISSIONS,
- MICROPHONE_PERMISSIONS, CAMERA_PERMISSIONS);
- }
-
public void grantDefaultPermissionsToDefaultUseOpenWifiApp(String packageName, int userId) {
Log.i(TAG, "Granting permissions to default Use Open WiFi app for user:" + userId);
grantIgnoringSystemPackage(packageName, userId, ALWAYS_LOCATION_PERMISSIONS);
diff --git a/services/core/java/com/android/server/power/AttentionDetector.java b/services/core/java/com/android/server/power/AttentionDetector.java
index a65a81263780..3262eb67a052 100644
--- a/services/core/java/com/android/server/power/AttentionDetector.java
+++ b/services/core/java/com/android/server/power/AttentionDetector.java
@@ -196,7 +196,7 @@ public class AttentionDetector {
mRequested.set(false);
}
- Slog.v(TAG, "Checking user attention");
+ Slog.v(TAG, "Checking user attention, ID: " + mRequestId);
return whenToCheck;
}
@@ -277,12 +277,12 @@ public class AttentionDetector {
}
public void dump(PrintWriter pw) {
- pw.print("AttentionDetector:");
- pw.print(" mMaximumExtensionMillis=" + mMaximumExtensionMillis);
- pw.print(" mMaxAttentionApiTimeoutMillis=" + mMaxAttentionApiTimeoutMillis);
- pw.print(" mLastUserActivityTime(excludingAttention)=" + mLastUserActivityTime);
- pw.print(" mAttentionServiceSupported=" + isAttentionServiceSupported());
- pw.print(" mRequested=" + mRequested);
+ pw.println("AttentionDetector:");
+ pw.println(" mMaximumExtensionMillis=" + mMaximumExtensionMillis);
+ pw.println(" mMaxAttentionApiTimeoutMillis=" + mMaxAttentionApiTimeoutMillis);
+ pw.println(" mLastUserActivityTime(excludingAttention)=" + mLastUserActivityTime);
+ pw.println(" mAttentionServiceSupported=" + isAttentionServiceSupported());
+ pw.println(" mRequested=" + mRequested);
}
@VisibleForTesting
diff --git a/services/core/java/com/android/server/role/RoleManagerService.java b/services/core/java/com/android/server/role/RoleManagerService.java
index 0e20905db32a..33803b742042 100644
--- a/services/core/java/com/android/server/role/RoleManagerService.java
+++ b/services/core/java/com/android/server/role/RoleManagerService.java
@@ -156,6 +156,7 @@ public class RoleManagerService extends SystemService implements RoleUserState.C
PackageManagerInternal packageManagerInternal = LocalServices.getService(
PackageManagerInternal.class);
packageManagerInternal.setDefaultBrowserProvider(new DefaultBrowserProvider());
+ packageManagerInternal.setDefaultDialerProvider(new DefaultDialerProvider());
packageManagerInternal.setDefaultHomeProvider(new DefaultHomeProvider());
registerUserRemovedReceiver();
@@ -772,6 +773,16 @@ public class RoleManagerService extends SystemService implements RoleUserState.C
}
}
+ private class DefaultDialerProvider implements PackageManagerInternal.DefaultDialerProvider {
+
+ @Nullable
+ @Override
+ public String getDefaultDialer(@UserIdInt int userId) {
+ return CollectionUtils.firstOrNull(getOrCreateUserState(userId).getRoleHolders(
+ RoleManager.ROLE_DIALER));
+ }
+ }
+
private class DefaultHomeProvider implements PackageManagerInternal.DefaultHomeProvider {
@Nullable
diff --git a/services/core/java/com/android/server/telecom/TelecomLoaderService.java b/services/core/java/com/android/server/telecom/TelecomLoaderService.java
index f581bc0bca46..e65eae0ab156 100644
--- a/services/core/java/com/android/server/telecom/TelecomLoaderService.java
+++ b/services/core/java/com/android/server/telecom/TelecomLoaderService.java
@@ -70,38 +70,9 @@ public class TelecomLoaderService extends SystemService {
ServiceManager.addService(Context.TELECOM_SERVICE, service);
synchronized (mLock) {
- if (mDefaultSmsAppRequests != null || mDefaultDialerAppRequests != null
- || mDefaultSimCallManagerRequests != null) {
+ if (mDefaultSimCallManagerRequests != null) {
final DefaultPermissionGrantPolicy permissionPolicy =
getDefaultPermissionGrantPolicy();
-
- if (mDefaultSmsAppRequests != null) {
- ComponentName smsComponent = SmsApplication.getDefaultSmsApplication(
- mContext, true);
- if (smsComponent != null) {
- final int requestCount = mDefaultSmsAppRequests.size();
- for (int i = requestCount - 1; i >= 0; i--) {
- final int userid = mDefaultSmsAppRequests.get(i);
- mDefaultSmsAppRequests.remove(i);
- permissionPolicy.grantDefaultPermissionsToDefaultSmsApp(
- smsComponent.getPackageName(), userid);
- }
- }
- }
-
- if (mDefaultDialerAppRequests != null) {
- String packageName = DefaultDialerManager.getDefaultDialerApplication(
- mContext);
- if (packageName != null) {
- final int requestCount = mDefaultDialerAppRequests.size();
- for (int i = requestCount - 1; i >= 0; i--) {
- final int userId = mDefaultDialerAppRequests.get(i);
- mDefaultDialerAppRequests.remove(i);
- permissionPolicy.grantDefaultPermissionsToDefaultDialerApp(
- packageName, userId);
- }
- }
- }
if (mDefaultSimCallManagerRequests != null) {
TelecomManager telecomManager =
(TelecomManager) mContext.getSystemService(Context.TELECOM_SERVICE);
@@ -146,12 +117,6 @@ public class TelecomLoaderService extends SystemService {
private final Object mLock = new Object();
@GuardedBy("mLock")
- private IntArray mDefaultSmsAppRequests;
-
- @GuardedBy("mLock")
- private IntArray mDefaultDialerAppRequests;
-
- @GuardedBy("mLock")
private IntArray mDefaultSimCallManagerRequests;
private final Context mContext;
@@ -207,10 +172,6 @@ public class TelecomLoaderService extends SystemService {
permissionPolicy.setSmsAppPackagesProvider(userId -> {
synchronized (mLock) {
if (mServiceConnection == null) {
- if (mDefaultSmsAppRequests == null) {
- mDefaultSmsAppRequests = new IntArray();
- }
- mDefaultSmsAppRequests.add(userId);
return null;
}
}
@@ -226,10 +187,6 @@ public class TelecomLoaderService extends SystemService {
permissionPolicy.setDialerAppPackagesProvider(userId -> {
synchronized (mLock) {
if (mServiceConnection == null) {
- if (mDefaultDialerAppRequests == null) {
- mDefaultDialerAppRequests = new IntArray();
- }
- mDefaultDialerAppRequests.add(userId);
return null;
}
}
@@ -263,38 +220,18 @@ public class TelecomLoaderService extends SystemService {
private void registerDefaultAppNotifier() {
final DefaultPermissionGrantPolicy permissionPolicy = getDefaultPermissionGrantPolicy();
-
// Notify the package manager on default app changes
- final Uri defaultSmsAppUri = Settings.Secure.getUriFor(
- Settings.Secure.SMS_DEFAULT_APPLICATION);
final Uri defaultDialerAppUri = Settings.Secure.getUriFor(
Settings.Secure.DIALER_DEFAULT_APPLICATION);
-
ContentObserver contentObserver = new ContentObserver(
new Handler(Looper.getMainLooper())) {
@Override
public void onChange(boolean selfChange, Uri uri, int userId) {
- if (defaultSmsAppUri.equals(uri)) {
- ComponentName smsComponent = SmsApplication.getDefaultSmsApplication(
- mContext, true);
- if (smsComponent != null) {
- permissionPolicy.grantDefaultPermissionsToDefaultSmsApp(
- smsComponent.getPackageName(), userId);
- }
- } else if (defaultDialerAppUri.equals(uri)) {
- String packageName = DefaultDialerManager.getDefaultDialerApplication(
- mContext);
- if (packageName != null) {
- permissionPolicy.grantDefaultPermissionsToDefaultDialerApp(
- packageName, userId);
- }
+ if (defaultDialerAppUri.equals(uri)) {
updateSimCallManagerPermissions(permissionPolicy, userId);
}
}
};
-
- mContext.getContentResolver().registerContentObserver(defaultSmsAppUri,
- false, contentObserver, UserHandle.USER_ALL);
mContext.getContentResolver().registerContentObserver(defaultDialerAppUri,
false, contentObserver, UserHandle.USER_ALL);
}
diff --git a/services/core/java/com/android/server/wm/ActivityStarter.java b/services/core/java/com/android/server/wm/ActivityStarter.java
index e7e34bb881e4..2846b383507f 100644
--- a/services/core/java/com/android/server/wm/ActivityStarter.java
+++ b/services/core/java/com/android/server/wm/ActivityStarter.java
@@ -942,8 +942,9 @@ class ActivityStarter {
WindowProcessController callerApp, PendingIntentRecord originatingPendingIntent,
boolean allowBackgroundActivityStart, Intent intent) {
// don't abort for the most important UIDs
- if (callingUid == Process.ROOT_UID || callingUid == Process.SYSTEM_UID
- || callingUid == Process.NFC_UID) {
+ final int callingAppId = UserHandle.getAppId(callingUid);
+ if (callingUid == Process.ROOT_UID || callingAppId == Process.SYSTEM_UID
+ || callingAppId == Process.NFC_UID) {
return false;
}
// don't abort if the callingUid has a visible window or is a persistent system process
@@ -953,8 +954,8 @@ class ActivityStarter {
final boolean isCallingUidForeground = callingUidHasAnyVisibleWindow
|| callingUidProcState == ActivityManager.PROCESS_STATE_TOP
|| callingUidProcState == ActivityManager.PROCESS_STATE_BOUND_TOP;
- final boolean isCallingUidPersistentSystemProcess = (callingUid == Process.SYSTEM_UID)
- || callingUidProcState <= ActivityManager.PROCESS_STATE_PERSISTENT_UI;
+ final boolean isCallingUidPersistentSystemProcess =
+ callingUidProcState <= ActivityManager.PROCESS_STATE_PERSISTENT_UI;
if (callingUidHasAnyVisibleWindow || isCallingUidPersistentSystemProcess) {
return false;
}
@@ -969,14 +970,15 @@ class ActivityStarter {
? isCallingUidForeground
: realCallingUidHasAnyVisibleWindow
|| realCallingUidProcState == ActivityManager.PROCESS_STATE_TOP;
+ final int realCallingAppId = UserHandle.getAppId(realCallingUid);
final boolean isRealCallingUidPersistentSystemProcess = (callingUid == realCallingUid)
? isCallingUidPersistentSystemProcess
- : (realCallingUid == Process.SYSTEM_UID)
+ : (realCallingAppId == Process.SYSTEM_UID)
|| realCallingUidProcState <= ActivityManager.PROCESS_STATE_PERSISTENT_UI;
if (realCallingUid != callingUid) {
// don't abort if the realCallingUid has a visible window, unless realCallingUid is
// SYSTEM_UID, in which case it start needs to be explicitly whitelisted
- if (realCallingUidHasAnyVisibleWindow && realCallingUid != Process.SYSTEM_UID) {
+ if (realCallingUidHasAnyVisibleWindow && realCallingAppId != Process.SYSTEM_UID) {
return false;
}
// if the realCallingUid is a persistent system process, abort if the IntentSender
diff --git a/services/core/java/com/android/server/wm/ActivityTaskManagerService.java b/services/core/java/com/android/server/wm/ActivityTaskManagerService.java
index b234bc6f77c3..a8b56d3ccbed 100644
--- a/services/core/java/com/android/server/wm/ActivityTaskManagerService.java
+++ b/services/core/java/com/android/server/wm/ActivityTaskManagerService.java
@@ -1375,6 +1375,9 @@ public class ActivityTaskManagerService extends IActivityTaskManager.Stub {
.setMayWait(userId)
.setIgnoreTargetSecurity(ignoreTargetSecurity)
.setFilterCallingUid(isResolver ? 0 /* system */ : targetUid)
+ // The target may well be in the background, which would normally prevent it
+ // from starting an activity. Here we definitely want the start to succeed.
+ .setAllowBackgroundActivityStart(true)
.execute();
} catch (SecurityException e) {
// XXX need to figure out how to propagate to original app.
diff --git a/services/core/java/com/android/server/wm/DisplayContent.java b/services/core/java/com/android/server/wm/DisplayContent.java
index 7a26f7cbf640..58a03b26b959 100644
--- a/services/core/java/com/android/server/wm/DisplayContent.java
+++ b/services/core/java/com/android/server/wm/DisplayContent.java
@@ -26,6 +26,7 @@ import static android.app.WindowConfiguration.WINDOWING_MODE_SPLIT_SCREEN_PRIMAR
import static android.content.pm.ActivityInfo.SCREEN_ORIENTATION_BEHIND;
import static android.content.pm.ActivityInfo.SCREEN_ORIENTATION_UNSET;
import static android.content.pm.ActivityInfo.SCREEN_ORIENTATION_UNSPECIFIED;
+import static android.content.pm.ActivityInfo.SCREEN_ORIENTATION_USER;
import static android.content.res.Configuration.ORIENTATION_LANDSCAPE;
import static android.content.res.Configuration.ORIENTATION_PORTRAIT;
import static android.os.Trace.TRACE_TAG_WINDOW_MANAGER;
@@ -78,6 +79,8 @@ import static com.android.server.policy.WindowManagerPolicy.FINISH_LAYOUT_REDO_W
import static com.android.server.wm.DisplayContentProto.ABOVE_APP_WINDOWS;
import static com.android.server.wm.DisplayContentProto.APP_TRANSITION;
import static com.android.server.wm.DisplayContentProto.BELOW_APP_WINDOWS;
+import static com.android.server.wm.DisplayContentProto.CHANGING_APPS;
+import static com.android.server.wm.DisplayContentProto.CLOSING_APPS;
import static com.android.server.wm.DisplayContentProto.DISPLAY_FRAMES;
import static com.android.server.wm.DisplayContentProto.DISPLAY_INFO;
import static com.android.server.wm.DisplayContentProto.DOCKED_STACK_DIVIDER_CONTROLLER;
@@ -85,14 +88,12 @@ import static com.android.server.wm.DisplayContentProto.DPI;
import static com.android.server.wm.DisplayContentProto.FOCUSED_APP;
import static com.android.server.wm.DisplayContentProto.ID;
import static com.android.server.wm.DisplayContentProto.IME_WINDOWS;
+import static com.android.server.wm.DisplayContentProto.OPENING_APPS;
import static com.android.server.wm.DisplayContentProto.PINNED_STACK_CONTROLLER;
import static com.android.server.wm.DisplayContentProto.ROTATION;
import static com.android.server.wm.DisplayContentProto.SCREEN_ROTATION_ANIMATION;
import static com.android.server.wm.DisplayContentProto.STACKS;
import static com.android.server.wm.DisplayContentProto.WINDOW_CONTAINER;
-import static com.android.server.wm.DisplayContentProto.OPENING_APPS;
-import static com.android.server.wm.DisplayContentProto.CHANGING_APPS;
-import static com.android.server.wm.DisplayContentProto.CLOSING_APPS;
import static com.android.server.wm.WindowManagerDebugConfig.DEBUG_ADD_REMOVE;
import static com.android.server.wm.WindowManagerDebugConfig.DEBUG_APP_TRANSITIONS;
import static com.android.server.wm.WindowManagerDebugConfig.DEBUG_BOOT;
@@ -375,6 +376,20 @@ class DisplayContent extends WindowContainer<DisplayContent.DisplayChildWindowCo
private int mLastKeyguardForcedOrientation = SCREEN_ORIENTATION_UNSPECIFIED;
/**
+ * The maximum aspect ratio (longerSide/shorterSide) that is treated as close-to-square. The
+ * orientation requests from apps would be ignored if the display is close-to-square.
+ */
+ @VisibleForTesting
+ final float mCloseToSquareMaxAspectRatio;
+
+ /**
+ * If this is true, we would not rotate the display for apps. The rotation would be either the
+ * sensor rotation or the user rotation, controlled by
+ * {@link WindowManagerPolicy.UserRotationMode}.
+ */
+ private boolean mIgnoreRotationForApps;
+
+ /**
* Keep track of wallpaper visibility to notify changes.
*/
private boolean mLastWallpaperVisible = false;
@@ -909,6 +924,8 @@ class DisplayContent extends WindowContainer<DisplayContent.DisplayChildWindowCo
mDisplayPolicy = new DisplayPolicy(service, this);
mDisplayRotation = new DisplayRotation(service, this);
+ mCloseToSquareMaxAspectRatio = service.mContext.getResources().getFloat(
+ com.android.internal.R.dimen.config_closeToSquareDisplayMaxAspectRatio);
if (isDefaultDisplay) {
// The policy may be invoked right after here, so it requires the necessary default
// fields of this display content.
@@ -1539,6 +1556,21 @@ class DisplayContent extends WindowContainer<DisplayContent.DisplayChildWindowCo
mDisplayFrames.onDisplayInfoUpdated(mDisplayInfo,
calculateDisplayCutoutForRotation(mDisplayInfo.rotation));
+
+ // Not much of use to rotate the display for apps since it's close to square.
+ mIgnoreRotationForApps = isNonDecorDisplayCloseToSquare(Surface.ROTATION_0, width, height);
+ }
+
+ private boolean isNonDecorDisplayCloseToSquare(int rotation, int width, int height) {
+ final DisplayCutout displayCutout =
+ calculateDisplayCutoutForRotation(rotation).getDisplayCutout();
+ final int uiMode = mWmService.mPolicy.getUiMode();
+ final int w = mDisplayPolicy.getNonDecorDisplayWidth(
+ width, height, rotation, uiMode, displayCutout);
+ final int h = mDisplayPolicy.getNonDecorDisplayHeight(
+ width, height, rotation, uiMode, displayCutout);
+ final float aspectRatio = Math.max(w, h) / (float) Math.min(w, h);
+ return aspectRatio <= mCloseToSquareMaxAspectRatio;
}
/**
@@ -2119,6 +2151,10 @@ class DisplayContent extends WindowContainer<DisplayContent.DisplayChildWindowCo
int getOrientation() {
final WindowManagerPolicy policy = mWmService.mPolicy;
+ if (mIgnoreRotationForApps) {
+ return SCREEN_ORIENTATION_USER;
+ }
+
if (mWmService.mDisplayFrozen) {
if (mLastWindowForcedOrientation != SCREEN_ORIENTATION_UNSPECIFIED) {
if (DEBUG_ORIENTATION) Slog.v(TAG_WM, "Display id=" + mDisplayId
@@ -2945,9 +2981,16 @@ class DisplayContent extends WindowContainer<DisplayContent.DisplayChildWindowCo
forAllWindows(mScheduleToastTimeout, false /* traverseTopToBottom */);
}
- WindowState findFocusedWindowIfNeeded() {
- return (mWmService.mPerDisplayFocusEnabled
- || mWmService.mRoot.mTopFocusedAppByProcess.isEmpty()) ? findFocusedWindow() : null;
+ /**
+ * Looking for the focused window on this display if the top focused display hasn't been
+ * found yet (topFocusedDisplayId is INVALID_DISPLAY) or per-display focused was allowed.
+ *
+ * @param topFocusedDisplayId Id of the top focused display.
+ * @return The focused window or null if there isn't any or no need to seek.
+ */
+ WindowState findFocusedWindowIfNeeded(int topFocusedDisplayId) {
+ return (mWmService.mPerDisplayFocusEnabled || topFocusedDisplayId == INVALID_DISPLAY)
+ ? findFocusedWindow() : null;
}
WindowState findFocusedWindow() {
@@ -2971,10 +3014,12 @@ class DisplayContent extends WindowContainer<DisplayContent.DisplayChildWindowCo
* {@link WindowManagerService#UPDATE_FOCUS_WILL_PLACE_SURFACES},
* {@link WindowManagerService#UPDATE_FOCUS_REMOVING_FOCUS}
* @param updateInputWindows Whether to sync the window information to the input module.
+ * @param topFocusedDisplayId Display id of current top focused display.
* @return {@code true} if the focused window has changed.
*/
- boolean updateFocusedWindowLocked(int mode, boolean updateInputWindows) {
- WindowState newFocus = findFocusedWindowIfNeeded();
+ boolean updateFocusedWindowLocked(int mode, boolean updateInputWindows,
+ int topFocusedDisplayId) {
+ WindowState newFocus = findFocusedWindowIfNeeded(topFocusedDisplayId);
if (mCurrentFocus == newFocus) {
return false;
}
@@ -2994,7 +3039,7 @@ class DisplayContent extends WindowContainer<DisplayContent.DisplayChildWindowCo
if (imWindowChanged) {
mWmService.mWindowsChanged = true;
setLayoutNeeded();
- newFocus = findFocusedWindowIfNeeded();
+ newFocus = findFocusedWindowIfNeeded(topFocusedDisplayId);
}
if (mCurrentFocus != newFocus) {
mWmService.mH.obtainMessage(REPORT_FOCUS_CHANGE, this).sendToTarget();
diff --git a/services/core/java/com/android/server/wm/DisplayRotation.java b/services/core/java/com/android/server/wm/DisplayRotation.java
index 34a480291863..282ed42468dd 100644
--- a/services/core/java/com/android/server/wm/DisplayRotation.java
+++ b/services/core/java/com/android/server/wm/DisplayRotation.java
@@ -39,7 +39,6 @@ import android.os.UserHandle;
import android.provider.Settings;
import android.util.Slog;
import android.util.SparseArray;
-import android.view.DisplayCutout;
import android.view.Surface;
import com.android.internal.annotations.VisibleForTesting;
@@ -74,8 +73,6 @@ public class DisplayRotation {
private final int mDeskDockRotation;
private final int mUndockedHdmiRotation;
- private final float mCloseToSquareMaxAspectRatio;
-
private OrientationListener mOrientationListener;
private StatusBarManagerInternal mStatusBarManagerInternal;
private SettingsObserver mSettingsObserver;
@@ -163,9 +160,6 @@ public class DisplayRotation {
mUndockedHdmiRotation = readRotation(
com.android.internal.R.integer.config_undockedHdmiRotation);
- mCloseToSquareMaxAspectRatio = mContext.getResources().getFloat(
- com.android.internal.R.dimen.config_closeToSquareDisplayMaxAspectRatio);
-
if (isDefaultDisplay) {
final Handler uiHandler = UiThread.getHandler();
mOrientationListener = new OrientationListener(mContext, uiHandler);
@@ -242,31 +236,16 @@ public class DisplayRotation {
// It's also not likely to rotate a TV screen.
final boolean isTv = mContext.getPackageManager().hasSystemFeature(
PackageManager.FEATURE_LEANBACK);
- // Not much of use to rotate the display since it's close to square.
- final boolean isCloseToSquare =
- isNonDecorDisplayCloseToSquare(Surface.ROTATION_0, width, height);
final boolean forceDesktopMode =
mService.mForceDesktopModeOnExternalDisplays && !isDefaultDisplay;
mDefaultFixedToUserRotation =
- (isCar || isTv || mService.mIsPc || forceDesktopMode || isCloseToSquare)
+ (isCar || isTv || mService.mIsPc || forceDesktopMode)
// For debug purposes the next line turns this feature off with:
// $ adb shell setprop config.override_forced_orient true
// $ adb shell wm size reset
&& !"true".equals(SystemProperties.get("config.override_forced_orient"));
}
- private boolean isNonDecorDisplayCloseToSquare(int rotation, int width, int height) {
- final DisplayCutout displayCutout =
- mDisplayContent.calculateDisplayCutoutForRotation(rotation).getDisplayCutout();
- final int uiMode = mService.mPolicy.getUiMode();
- final int w = mDisplayPolicy.getNonDecorDisplayWidth(
- width, height, rotation, uiMode, displayCutout);
- final int h = mDisplayPolicy.getNonDecorDisplayHeight(
- width, height, rotation, uiMode, displayCutout);
- final float aspectRatio = Math.max(w, h) / (float) Math.min(w, h);
- return aspectRatio <= mCloseToSquareMaxAspectRatio;
- }
-
void setRotation(int rotation) {
if (mOrientationListener != null) {
mOrientationListener.setCurrentRotation(rotation);
diff --git a/services/core/java/com/android/server/wm/LockTaskController.java b/services/core/java/com/android/server/wm/LockTaskController.java
index 2411e006a562..ef2a21d919e1 100644
--- a/services/core/java/com/android/server/wm/LockTaskController.java
+++ b/services/core/java/com/android/server/wm/LockTaskController.java
@@ -802,18 +802,24 @@ public class LockTaskController {
* leaves the pinned mode.
*/
private void lockKeyguardIfNeeded() {
+ if (shouldLockKeyguard()) {
+ mWindowManager.lockNow(null);
+ mWindowManager.dismissKeyguard(null /* callback */, null /* message */);
+ getLockPatternUtils().requireCredentialEntry(USER_ALL);
+ }
+ }
+
+ private boolean shouldLockKeyguard() {
+ // This functionality should be kept consistent with
+ // com.android.settings.security.ScreenPinningSettings (see b/127605586)
try {
- boolean shouldLockKeyguard = Settings.Secure.getIntForUser(
+ return Settings.Secure.getIntForUser(
mContext.getContentResolver(),
- Settings.Secure.LOCK_TO_APP_EXIT_LOCKED,
- USER_CURRENT) != 0;
- if (shouldLockKeyguard) {
- mWindowManager.lockNow(null);
- mWindowManager.dismissKeyguard(null /* callback */, null /* message */);
- getLockPatternUtils().requireCredentialEntry(USER_ALL);
- }
+ Settings.Secure.LOCK_TO_APP_EXIT_LOCKED, USER_CURRENT) != 0;
} catch (Settings.SettingNotFoundException e) {
- // No setting, don't lock.
+ // Log to SafetyNet for b/127605586
+ android.util.EventLog.writeEvent(0x534e4554, "127605586", -1, "");
+ return mLockPatternUtils.isSecure(USER_CURRENT);
}
}
diff --git a/services/core/java/com/android/server/wm/RootWindowContainer.java b/services/core/java/com/android/server/wm/RootWindowContainer.java
index 9f4232400221..8a5f52f8c453 100644
--- a/services/core/java/com/android/server/wm/RootWindowContainer.java
+++ b/services/core/java/com/android/server/wm/RootWindowContainer.java
@@ -170,7 +170,7 @@ class RootWindowContainer extends WindowContainer<DisplayContent>
int topFocusedDisplayId = INVALID_DISPLAY;
for (int i = mChildren.size() - 1; i >= 0; --i) {
final DisplayContent dc = mChildren.get(i);
- changed |= dc.updateFocusedWindowLocked(mode, updateInputWindows);
+ changed |= dc.updateFocusedWindowLocked(mode, updateInputWindows, topFocusedDisplayId);
final WindowState newFocus = dc.mCurrentFocus;
if (newFocus != null) {
final int pidOfNewFocus = newFocus.mSession.mPid;
@@ -180,6 +180,11 @@ class RootWindowContainer extends WindowContainer<DisplayContent>
if (topFocusedDisplayId == INVALID_DISPLAY) {
topFocusedDisplayId = dc.getDisplayId();
}
+ } else if (topFocusedDisplayId == INVALID_DISPLAY && dc.mFocusedApp != null) {
+ // The top-most display that has a focused app should still be the top focused
+ // display even when the app window is not ready yet (process not attached or
+ // window not added yet).
+ topFocusedDisplayId = dc.getDisplayId();
}
}
if (topFocusedDisplayId == INVALID_DISPLAY) {
diff --git a/services/core/jni/com_android_server_input_InputManagerService.cpp b/services/core/jni/com_android_server_input_InputManagerService.cpp
index 204a1ea977e7..00671c1401dc 100644
--- a/services/core/jni/com_android_server_input_InputManagerService.cpp
+++ b/services/core/jni/com_android_server_input_InputManagerService.cpp
@@ -724,19 +724,18 @@ nsecs_t NativeInputManager::notifyANR(const sp<InputApplicationHandle>& inputApp
JNIEnv* env = jniEnv();
- jobject tokenObj = javaObjectForIBinder(env, token);
- jstring reasonObj = env->NewStringUTF(reason.c_str());
+ ScopedLocalRef<jobject> tokenObj(env, javaObjectForIBinder(env, token));
+ ScopedLocalRef<jstring> reasonObj(env, env->NewStringUTF(reason.c_str()));
jlong newTimeout = env->CallLongMethod(mServiceObj,
- gServiceClassInfo.notifyANR, tokenObj,
- reasonObj);
+ gServiceClassInfo.notifyANR, tokenObj.get(),
+ reasonObj.get());
if (checkAndClearExceptionFromCallback(env, "notifyANR")) {
newTimeout = 0; // abort dispatch
} else {
assert(newTimeout >= 0);
}
- env->DeleteLocalRef(reasonObj);
return newTimeout;
}
@@ -748,10 +747,10 @@ void NativeInputManager::notifyInputChannelBroken(const sp<IBinder>& token) {
JNIEnv* env = jniEnv();
- jobject tokenObj = javaObjectForIBinder(env, token);
- if (tokenObj) {
+ ScopedLocalRef<jobject> tokenObj(env, javaObjectForIBinder(env, token));
+ if (tokenObj.get()) {
env->CallVoidMethod(mServiceObj, gServiceClassInfo.notifyInputChannelBroken,
- tokenObj);
+ tokenObj.get());
checkAndClearExceptionFromCallback(env, "notifyInputChannelBroken");
}
}
@@ -765,10 +764,10 @@ void NativeInputManager::notifyFocusChanged(const sp<IBinder>& oldToken,
JNIEnv* env = jniEnv();
- jobject oldTokenObj = javaObjectForIBinder(env, oldToken);
- jobject newTokenObj = javaObjectForIBinder(env, newToken);
+ ScopedLocalRef<jobject> oldTokenObj(env, javaObjectForIBinder(env, oldToken));
+ ScopedLocalRef<jobject> newTokenObj(env, javaObjectForIBinder(env, newToken));
env->CallVoidMethod(mServiceObj, gServiceClassInfo.notifyFocusChanged,
- oldTokenObj, newTokenObj);
+ oldTokenObj.get(), newTokenObj.get());
checkAndClearExceptionFromCallback(env, "notifyFocusChanged");
}
@@ -1141,13 +1140,13 @@ nsecs_t NativeInputManager::interceptKeyBeforeDispatching(
JNIEnv* env = jniEnv();
// Token may be null
- jobject tokenObj = javaObjectForIBinder(env, token);
+ ScopedLocalRef<jobject> tokenObj(env, javaObjectForIBinder(env, token));
jobject keyEventObj = android_view_KeyEvent_fromNative(env, keyEvent);
if (keyEventObj) {
jlong delayMillis = env->CallLongMethod(mServiceObj,
gServiceClassInfo.interceptKeyBeforeDispatching,
- tokenObj, keyEventObj, policyFlags);
+ tokenObj.get(), keyEventObj, policyFlags);
bool error = checkAndClearExceptionFromCallback(env, "interceptKeyBeforeDispatching");
android_view_KeyEvent_recycle(env, keyEventObj);
env->DeleteLocalRef(keyEventObj);
@@ -1175,12 +1174,12 @@ bool NativeInputManager::dispatchUnhandledKey(const sp<IBinder>& token,
JNIEnv* env = jniEnv();
// Note: tokenObj may be null.
- jobject tokenObj = javaObjectForIBinder(env, token);
+ ScopedLocalRef<jobject> tokenObj(env, javaObjectForIBinder(env, token));
jobject keyEventObj = android_view_KeyEvent_fromNative(env, keyEvent);
if (keyEventObj) {
jobject fallbackKeyEventObj = env->CallObjectMethod(mServiceObj,
gServiceClassInfo.dispatchUnhandledKey,
- tokenObj, keyEventObj, policyFlags);
+ tokenObj.get(), keyEventObj, policyFlags);
if (checkAndClearExceptionFromCallback(env, "dispatchUnhandledKey")) {
fallbackKeyEventObj = nullptr;
}
@@ -1225,8 +1224,9 @@ void NativeInputManager::onPointerDownOutsideFocus(const sp<IBinder>& touchedTok
ATRACE_CALL();
JNIEnv* env = jniEnv();
- jobject touchedTokenObj = javaObjectForIBinder(env, touchedToken);
- env->CallVoidMethod(mServiceObj, gServiceClassInfo.onPointerDownOutsideFocus, touchedTokenObj);
+ ScopedLocalRef<jobject> touchedTokenObj(env, javaObjectForIBinder(env, touchedToken));
+ env->CallVoidMethod(mServiceObj, gServiceClassInfo.onPointerDownOutsideFocus,
+ touchedTokenObj.get());
checkAndClearExceptionFromCallback(env, "onPointerDownOutsideFocus");
}
diff --git a/services/core/xsd/vts/Android.bp b/services/core/xsd/vts/Android.bp
index 967750ddc5de..5545656a36de 100644
--- a/services/core/xsd/vts/Android.bp
+++ b/services/core/xsd/vts/Android.bp
@@ -25,6 +25,7 @@ cc_test {
],
shared_libs: [
"liblog",
+ "libbase",
],
cflags: [
"-Wall",
diff --git a/services/core/xsd/vts/ValidateDefaultPermissions.cpp b/services/core/xsd/vts/ValidateDefaultPermissions.cpp
index 54c115b14e37..518f7bbae09b 100644
--- a/services/core/xsd/vts/ValidateDefaultPermissions.cpp
+++ b/services/core/xsd/vts/ValidateDefaultPermissions.cpp
@@ -16,13 +16,48 @@
#include "utility/ValidateXml.h"
-TEST(CheckConfig, mediaDefaultPermissions) {
+#include <dirent.h>
+#include <stdlib.h>
+#include <sys/stat.h>
+#include <unistd.h>
+
+#include <string>
+
+#include <android-base/strings.h>
+
+static std::vector<std::string> get_files_in_dirs(const char* dir_path) {
+ std::vector<std::string> files;
+ std::unique_ptr<DIR, decltype(&closedir)> d(opendir(dir_path), closedir);
+
+ if (d == nullptr) {
+ return files;
+ }
+
+ struct dirent* de;
+ while ((de = readdir(d.get()))) {
+ if (de->d_type != DT_REG) {
+ continue;
+ }
+ if (android::base::EndsWith(de->d_name, ".xml")) {
+ files.push_back(de->d_name);
+ }
+ }
+ return files;
+}
+
+TEST(CheckConfig, defaultPermissions) {
RecordProperty("description",
"Verify that the default-permissions file "
"is valid according to the schema");
- const char* location = "/vendor/etc/default-permissions";
+ std::vector<const char*> locations = {"/vendor/etc/default-permissions",
+ "/odm/etc/default-permissions"};
- EXPECT_ONE_VALID_XML_MULTIPLE_LOCATIONS("default-permissions.xml", {location},
- "/data/local/tmp/default-permissions.xsd");
+ for (const char* dir_path : locations) {
+ std::vector<std::string> files = get_files_in_dirs(dir_path);
+ for (auto& file_name : files) {
+ EXPECT_ONE_VALID_XML_MULTIPLE_LOCATIONS(file_name.c_str(), {dir_path},
+ "/data/local/tmp/default-permissions.xsd");
+ }
+ }
}
diff --git a/services/java/com/android/server/SystemServer.java b/services/java/com/android/server/SystemServer.java
index 4ac8342e6e60..be7dd31380ba 100644
--- a/services/java/com/android/server/SystemServer.java
+++ b/services/java/com/android/server/SystemServer.java
@@ -115,7 +115,6 @@ import com.android.server.om.OverlayManagerService;
import com.android.server.os.BugreportManagerService;
import com.android.server.os.DeviceIdentifiersPolicyService;
import com.android.server.os.SchedulingPolicyService;
-import com.android.server.pm.ApexManager;
import com.android.server.pm.BackgroundDexOptService;
import com.android.server.pm.CrossProfileAppsService;
import com.android.server.pm.DynamicCodeLoggingService;
@@ -628,12 +627,6 @@ public final class SystemServer {
watchdog.start();
traceEnd();
- // Start ApexManager as early as we can to give it enough time to call apexd and populate
- // cache of known apex packages. Note that calling apexd will happen asynchronously.
- traceBeginAndSlog("StartApexManager");
- mSystemServiceManager.startService(ApexManager.class);
- traceEnd();
-
Slog.i(TAG, "Reading configuration...");
final String TAG_SYSTEM_CONFIG = "ReadingSystemConfig";
traceBeginAndSlog(TAG_SYSTEM_CONFIG);
diff --git a/services/net/java/android/net/IpMemoryStore.java b/services/net/java/android/net/IpMemoryStore.java
index 4a115e6ec55b..6f91e006c853 100644
--- a/services/net/java/android/net/IpMemoryStore.java
+++ b/services/net/java/android/net/IpMemoryStore.java
@@ -18,11 +18,14 @@ package android.net;
import android.annotation.NonNull;
import android.content.Context;
+import android.util.Log;
import com.android.internal.annotations.VisibleForTesting;
import java.util.concurrent.CompletableFuture;
import java.util.concurrent.ExecutionException;
+import java.util.concurrent.atomic.AtomicReference;
+import java.util.function.Consumer;
/**
* Manager class used to communicate with the ip memory store service in the network stack,
@@ -30,15 +33,18 @@ import java.util.concurrent.ExecutionException;
* @hide
*/
public class IpMemoryStore extends IpMemoryStoreClient {
- private final CompletableFuture<IIpMemoryStore> mService;
+ private static final String TAG = IpMemoryStore.class.getSimpleName();
+ @NonNull private final CompletableFuture<IIpMemoryStore> mService;
+ @NonNull private final AtomicReference<CompletableFuture<IIpMemoryStore>> mTailNode;
public IpMemoryStore(@NonNull final Context context) {
super(context);
mService = new CompletableFuture<>();
+ mTailNode = new AtomicReference<CompletableFuture<IIpMemoryStore>>(mService);
getNetworkStackClient().fetchIpMemoryStore(
new IIpMemoryStoreCallbacks.Stub() {
@Override
- public void onIpMemoryStoreFetched(final IIpMemoryStore memoryStore) {
+ public void onIpMemoryStoreFetched(@NonNull final IIpMemoryStore memoryStore) {
mService.complete(memoryStore);
}
@@ -49,9 +55,28 @@ public class IpMemoryStore extends IpMemoryStoreClient {
});
}
+ /*
+ * If the IpMemoryStore is ready, this function will run the request synchronously.
+ * Otherwise, it will enqueue the requests for execution immediately after the
+ * service becomes ready. The requests are guaranteed to be executed in the order
+ * they are sumbitted.
+ */
@Override
- protected IIpMemoryStore getService() throws InterruptedException, ExecutionException {
- return mService.get();
+ protected void runWhenServiceReady(Consumer<IIpMemoryStore> cb) throws ExecutionException {
+ mTailNode.getAndUpdate(future -> future.handle((store, exception) -> {
+ if (exception != null) {
+ // this should never happens since we also catch the exception below
+ Log.wtf(TAG, "Error fetching IpMemoryStore", exception);
+ return store;
+ }
+
+ try {
+ cb.accept(store);
+ } catch (Exception e) {
+ Log.wtf(TAG, "Exception occured: " + e.getMessage());
+ }
+ return store;
+ }));
}
@VisibleForTesting
diff --git a/services/net/java/android/net/IpMemoryStoreClient.java b/services/net/java/android/net/IpMemoryStoreClient.java
index 379c017b2990..3d562022a2e5 100644
--- a/services/net/java/android/net/IpMemoryStoreClient.java
+++ b/services/net/java/android/net/IpMemoryStoreClient.java
@@ -31,6 +31,7 @@ import android.os.RemoteException;
import android.util.Log;
import java.util.concurrent.ExecutionException;
+import java.util.function.Consumer;
/**
* service used to communicate with the ip memory store service in network stack,
@@ -46,8 +47,25 @@ public abstract class IpMemoryStoreClient {
mContext = context;
}
- @NonNull
- protected abstract IIpMemoryStore getService() throws InterruptedException, ExecutionException;
+ protected abstract void runWhenServiceReady(Consumer<IIpMemoryStore> cb)
+ throws ExecutionException;
+
+ @FunctionalInterface
+ private interface ThrowingRunnable {
+ void run() throws RemoteException;
+ }
+
+ private void ignoringRemoteException(ThrowingRunnable r) {
+ ignoringRemoteException("Failed to execute remote procedure call", r);
+ }
+
+ private void ignoringRemoteException(String message, ThrowingRunnable r) {
+ try {
+ r.run();
+ } catch (RemoteException e) {
+ Log.e(TAG, message, e);
+ }
+ }
/**
* Store network attributes for a given L2 key.
@@ -69,14 +87,12 @@ public abstract class IpMemoryStoreClient {
@NonNull final NetworkAttributes attributes,
@Nullable final OnStatusListener listener) {
try {
- try {
- getService().storeNetworkAttributes(l2Key, attributes.toParcelable(),
- OnStatusListener.toAIDL(listener));
- } catch (InterruptedException | ExecutionException m) {
- listener.onComplete(new Status(Status.ERROR_UNKNOWN));
- }
- } catch (RemoteException e) {
- Log.e(TAG, "Error storing network attributes", e);
+ runWhenServiceReady(service -> ignoringRemoteException(
+ () -> service.storeNetworkAttributes(l2Key, attributes.toParcelable(),
+ OnStatusListener.toAIDL(listener))));
+ } catch (ExecutionException m) {
+ ignoringRemoteException("Error storing network attributes",
+ () -> listener.onComplete(new Status(Status.ERROR_UNKNOWN)));
}
}
@@ -95,14 +111,12 @@ public abstract class IpMemoryStoreClient {
@NonNull final String name, @NonNull final Blob data,
@Nullable final OnStatusListener listener) {
try {
- try {
- getService().storeBlob(l2Key, clientId, name, data,
- OnStatusListener.toAIDL(listener));
- } catch (InterruptedException | ExecutionException m) {
- listener.onComplete(new Status(Status.ERROR_UNKNOWN));
- }
- } catch (RemoteException e) {
- Log.e(TAG, "Error storing blob", e);
+ runWhenServiceReady(service -> ignoringRemoteException(
+ () -> service.storeBlob(l2Key, clientId, name, data,
+ OnStatusListener.toAIDL(listener))));
+ } catch (ExecutionException m) {
+ ignoringRemoteException("Error storing blob",
+ () -> listener.onComplete(new Status(Status.ERROR_UNKNOWN)));
}
}
@@ -123,14 +137,12 @@ public abstract class IpMemoryStoreClient {
public void findL2Key(@NonNull final NetworkAttributes attributes,
@NonNull final OnL2KeyResponseListener listener) {
try {
- try {
- getService().findL2Key(attributes.toParcelable(),
- OnL2KeyResponseListener.toAIDL(listener));
- } catch (InterruptedException | ExecutionException m) {
- listener.onL2KeyResponse(new Status(Status.ERROR_UNKNOWN), null);
- }
- } catch (RemoteException e) {
- Log.e(TAG, "Error finding L2 Key", e);
+ runWhenServiceReady(service -> ignoringRemoteException(
+ () -> service.findL2Key(attributes.toParcelable(),
+ OnL2KeyResponseListener.toAIDL(listener))));
+ } catch (ExecutionException m) {
+ ignoringRemoteException("Error finding L2 Key",
+ () -> listener.onL2KeyResponse(new Status(Status.ERROR_UNKNOWN), null));
}
}
@@ -146,14 +158,12 @@ public abstract class IpMemoryStoreClient {
public void isSameNetwork(@NonNull final String l2Key1, @NonNull final String l2Key2,
@NonNull final OnSameL3NetworkResponseListener listener) {
try {
- try {
- getService().isSameNetwork(l2Key1, l2Key2,
- OnSameL3NetworkResponseListener.toAIDL(listener));
- } catch (InterruptedException | ExecutionException m) {
- listener.onSameL3NetworkResponse(new Status(Status.ERROR_UNKNOWN), null);
- }
- } catch (RemoteException e) {
- Log.e(TAG, "Error checking for network sameness", e);
+ runWhenServiceReady(service -> ignoringRemoteException(
+ () -> service.isSameNetwork(l2Key1, l2Key2,
+ OnSameL3NetworkResponseListener.toAIDL(listener))));
+ } catch (ExecutionException m) {
+ ignoringRemoteException("Error checking for network sameness",
+ () -> listener.onSameL3NetworkResponse(new Status(Status.ERROR_UNKNOWN), null));
}
}
@@ -169,14 +179,13 @@ public abstract class IpMemoryStoreClient {
public void retrieveNetworkAttributes(@NonNull final String l2Key,
@NonNull final OnNetworkAttributesRetrievedListener listener) {
try {
- try {
- getService().retrieveNetworkAttributes(l2Key,
- OnNetworkAttributesRetrievedListener.toAIDL(listener));
- } catch (InterruptedException | ExecutionException m) {
- listener.onNetworkAttributesRetrieved(new Status(Status.ERROR_UNKNOWN), null, null);
- }
- } catch (RemoteException e) {
- Log.e(TAG, "Error retrieving network attributes", e);
+ runWhenServiceReady(service -> ignoringRemoteException(
+ () -> service.retrieveNetworkAttributes(l2Key,
+ OnNetworkAttributesRetrievedListener.toAIDL(listener))));
+ } catch (ExecutionException m) {
+ ignoringRemoteException("Error retrieving network attributes",
+ () -> listener.onNetworkAttributesRetrieved(new Status(Status.ERROR_UNKNOWN),
+ null, null));
}
}
@@ -194,14 +203,13 @@ public abstract class IpMemoryStoreClient {
public void retrieveBlob(@NonNull final String l2Key, @NonNull final String clientId,
@NonNull final String name, @NonNull final OnBlobRetrievedListener listener) {
try {
- try {
- getService().retrieveBlob(l2Key, clientId, name,
- OnBlobRetrievedListener.toAIDL(listener));
- } catch (InterruptedException | ExecutionException m) {
- listener.onBlobRetrieved(new Status(Status.ERROR_UNKNOWN), null, null, null);
- }
- } catch (RemoteException e) {
- Log.e(TAG, "Error retrieving blob", e);
+ runWhenServiceReady(service -> ignoringRemoteException(
+ () -> service.retrieveBlob(l2Key, clientId, name,
+ OnBlobRetrievedListener.toAIDL(listener))));
+ } catch (ExecutionException m) {
+ ignoringRemoteException("Error retrieving blob",
+ () -> listener.onBlobRetrieved(new Status(Status.ERROR_UNKNOWN),
+ null, null, null));
}
}
}
diff --git a/services/net/java/android/net/ip/IpClientManager.java b/services/net/java/android/net/ip/IpClientManager.java
new file mode 100644
index 000000000000..f8d7e845da2c
--- /dev/null
+++ b/services/net/java/android/net/ip/IpClientManager.java
@@ -0,0 +1,273 @@
+/*
+ * Copyright (C) 2019 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package android.net.ip;
+
+import android.annotation.NonNull;
+import android.net.NattKeepalivePacketData;
+import android.net.ProxyInfo;
+import android.net.TcpKeepalivePacketData;
+import android.net.shared.ProvisioningConfiguration;
+import android.os.Binder;
+import android.os.RemoteException;
+import android.util.Log;
+
+/**
+ * A convenience wrapper for IpClient.
+ *
+ * Wraps IIpClient calls, making them a bit more friendly to use. Currently handles:
+ * - Clearing calling identity
+ * - Ignoring RemoteExceptions
+ * - Converting to stable parcelables
+ *
+ * By design, all methods on IIpClient are asynchronous oneway IPCs and are thus void. All the
+ * wrapper methods in this class return a boolean that callers can use to determine whether
+ * RemoteException was thrown.
+ */
+public class IpClientManager {
+ @NonNull private final IIpClient mIpClient;
+ @NonNull private final String mTag;
+
+ public IpClientManager(@NonNull IIpClient ipClient, @NonNull String tag) {
+ mIpClient = ipClient;
+ mTag = tag;
+ }
+
+ public IpClientManager(@NonNull IIpClient ipClient) {
+ this(ipClient, IpClientManager.class.getSimpleName());
+ }
+
+ private void log(String s, Throwable e) {
+ Log.e(mTag, s, e);
+ }
+
+ /**
+ * For clients using {@link ProvisioningConfiguration.Builder#withPreDhcpAction()}, must be
+ * called after {@link IIpClientCallbacks#onPreDhcpAction} to indicate that DHCP is clear to
+ * proceed.
+ */
+ public boolean completedPreDhcpAction() {
+ final long token = Binder.clearCallingIdentity();
+ try {
+ mIpClient.completedPreDhcpAction();
+ return true;
+ } catch (RemoteException e) {
+ log("Error completing PreDhcpAction", e);
+ return false;
+ } finally {
+ Binder.restoreCallingIdentity(token);
+ }
+ }
+
+ /**
+ * Confirm the provisioning configuration.
+ */
+ public boolean confirmConfiguration() {
+ final long token = Binder.clearCallingIdentity();
+ try {
+ mIpClient.confirmConfiguration();
+ return true;
+ } catch (RemoteException e) {
+ log("Error confirming IpClient configuration", e);
+ return false;
+ }
+ }
+
+ /**
+ * Indicate that packet filter read is complete.
+ */
+ public boolean readPacketFilterComplete(byte[] data) {
+ final long token = Binder.clearCallingIdentity();
+ try {
+ mIpClient.readPacketFilterComplete(data);
+ return true;
+ } catch (RemoteException e) {
+ log("Error notifying IpClient of packet filter read", e);
+ return false;
+ } finally {
+ Binder.restoreCallingIdentity(token);
+ }
+ }
+
+ /**
+ * Shut down this IpClient instance altogether.
+ */
+ public boolean shutdown() {
+ final long token = Binder.clearCallingIdentity();
+ try {
+ mIpClient.shutdown();
+ return true;
+ } catch (RemoteException e) {
+ log("Error shutting down IpClient", e);
+ return false;
+ } finally {
+ Binder.restoreCallingIdentity(token);
+ }
+ }
+
+ /**
+ * Start provisioning with the provided parameters.
+ */
+ public boolean startProvisioning(ProvisioningConfiguration prov) {
+ final long token = Binder.clearCallingIdentity();
+ try {
+ mIpClient.startProvisioning(prov.toStableParcelable());
+ return true;
+ } catch (RemoteException e) {
+ log("Error starting IpClient provisioning", e);
+ return false;
+ } finally {
+ Binder.restoreCallingIdentity(token);
+ }
+ }
+
+ /**
+ * Stop this IpClient.
+ *
+ * <p>This does not shut down the StateMachine itself, which is handled by {@link #shutdown()}.
+ */
+ public boolean stop() {
+ final long token = Binder.clearCallingIdentity();
+ try {
+ mIpClient.stop();
+ return true;
+ } catch (RemoteException e) {
+ log("Error stopping IpClient", e);
+ return false;
+ } finally {
+ Binder.restoreCallingIdentity(token);
+ }
+ }
+
+ /**
+ * Set the TCP buffer sizes to use.
+ *
+ * This may be called, repeatedly, at any time before or after a call to
+ * #startProvisioning(). The setting is cleared upon calling #stop().
+ */
+ public boolean setTcpBufferSizes(String tcpBufferSizes) {
+ final long token = Binder.clearCallingIdentity();
+ try {
+ mIpClient.setTcpBufferSizes(tcpBufferSizes);
+ return true;
+ } catch (RemoteException e) {
+ log("Error setting IpClient TCP buffer sizes", e);
+ return false;
+ } finally {
+ Binder.restoreCallingIdentity(token);
+ }
+ }
+
+ /**
+ * Set the HTTP Proxy configuration to use.
+ *
+ * This may be called, repeatedly, at any time before or after a call to
+ * #startProvisioning(). The setting is cleared upon calling #stop().
+ */
+ public boolean setHttpProxy(ProxyInfo proxyInfo) {
+ final long token = Binder.clearCallingIdentity();
+ try {
+ mIpClient.setHttpProxy(proxyInfo);
+ return true;
+ } catch (RemoteException e) {
+ log("Error setting IpClient proxy", e);
+ return false;
+ } finally {
+ Binder.restoreCallingIdentity(token);
+ }
+ }
+
+ /**
+ * Enable or disable the multicast filter. Attempts to use APF to accomplish the filtering,
+ * if not, Callback.setFallbackMulticastFilter() is called.
+ */
+ public boolean setMulticastFilter(boolean enabled) {
+ final long token = Binder.clearCallingIdentity();
+ try {
+ mIpClient.setMulticastFilter(enabled);
+ return true;
+ } catch (RemoteException e) {
+ log("Error setting multicast filter", e);
+ return false;
+ } finally {
+ Binder.restoreCallingIdentity(token);
+ }
+ }
+
+ /**
+ * Add a TCP keepalive packet filter before setting up keepalive offload.
+ */
+ public boolean addKeepalivePacketFilter(int slot, TcpKeepalivePacketData pkt) {
+ final long token = Binder.clearCallingIdentity();
+ try {
+ mIpClient.addKeepalivePacketFilter(slot, pkt.toStableParcelable());
+ return true;
+ } catch (RemoteException e) {
+ log("Error adding Keepalive Packet Filter ", e);
+ return false;
+ } finally {
+ Binder.restoreCallingIdentity(token);
+ }
+ }
+
+ /**
+ * Add a NAT-T keepalive packet filter before setting up keepalive offload.
+ */
+ public boolean addKeepalivePacketFilter(int slot, NattKeepalivePacketData pkt) {
+ final long token = Binder.clearCallingIdentity();
+ try {
+ mIpClient.addNattKeepalivePacketFilter(slot, pkt.toStableParcelable());
+ return true;
+ } catch (RemoteException e) {
+ log("Error adding Keepalive Packet Filter ", e);
+ return false;
+ } finally {
+ Binder.restoreCallingIdentity(token);
+ }
+ }
+
+ /**
+ * Remove a keepalive packet filter after stopping keepalive offload.
+ */
+ public boolean removeKeepalivePacketFilter(int slot) {
+ final long token = Binder.clearCallingIdentity();
+ try {
+ mIpClient.removeKeepalivePacketFilter(slot);
+ return true;
+ } catch (RemoteException e) {
+ log("Error removing Keepalive Packet Filter ", e);
+ return false;
+ } finally {
+ Binder.restoreCallingIdentity(token);
+ }
+ }
+
+ /**
+ * Set the L2 key and group hint for storing info into the memory store.
+ */
+ public boolean setL2KeyAndGroupHint(String l2Key, String groupHint) {
+ final long token = Binder.clearCallingIdentity();
+ try {
+ mIpClient.setL2KeyAndGroupHint(l2Key, groupHint);
+ return true;
+ } catch (RemoteException e) {
+ log("Failed setL2KeyAndGroupHint", e);
+ return false;
+ } finally {
+ Binder.restoreCallingIdentity(token);
+ }
+ }
+}
diff --git a/services/tests/servicestests/src/com/android/server/StorageManagerServiceTest.java b/services/tests/servicestests/src/com/android/server/StorageManagerServiceTest.java
index 68f696b26a26..d192748762fe 100644
--- a/services/tests/servicestests/src/com/android/server/StorageManagerServiceTest.java
+++ b/services/tests/servicestests/src/com/android/server/StorageManagerServiceTest.java
@@ -15,31 +15,21 @@
*/
package com.android.server;
-import static org.junit.Assert.assertEquals;
-import static org.junit.Assert.fail;
-import static org.mockito.ArgumentMatchers.anyInt;
-import static org.mockito.ArgumentMatchers.eq;
import static org.mockito.Mockito.when;
-import android.app.ActivityManagerInternal;
import android.content.Context;
-import android.content.pm.ApplicationInfo;
import android.content.pm.PackageManager;
import android.content.pm.PackageManagerInternal;
-import android.os.UserManagerInternal;
import android.os.storage.StorageManagerInternal;
-import com.android.internal.os.Zygote;
+import androidx.test.filters.SmallTest;
+import androidx.test.runner.AndroidJUnit4;
import org.junit.Before;
-import org.junit.Test;
import org.junit.runner.RunWith;
import org.mockito.Mock;
import org.mockito.MockitoAnnotations;
-import androidx.test.filters.SmallTest;
-import androidx.test.runner.AndroidJUnit4;
-
@SmallTest
@RunWith(AndroidJUnit4.class)
public class StorageManagerServiceTest {
@@ -49,28 +39,6 @@ public class StorageManagerServiceTest {
@Mock private Context mContext;
@Mock private PackageManager mPm;
@Mock private PackageManagerInternal mPmi;
- @Mock private UserManagerInternal mUmi;
- @Mock private ActivityManagerInternal mAmi;
-
- private static final String PKG_GREY = "com.grey";
- private static final String PKG_RED = "com.red";
- private static final String PKG_BLUE = "com.blue";
-
- private static final int UID_GREY = 10000;
- private static final int UID_COLORS = 10001;
-
- private static final int PID_GREY = 1111;
- private static final int PID_RED = 2222;
- private static final int PID_BLUE = 3333;
-
- private static final String NAME_COLORS = "colors";
-
- private static ApplicationInfo buildApplicationInfo(String packageName, int uid) {
- final ApplicationInfo ai = new ApplicationInfo();
- ai.packageName = packageName;
- ai.uid = uid;
- return ai;
- }
@Before
public void setUp() throws Exception {
@@ -80,196 +48,9 @@ public class StorageManagerServiceTest {
LocalServices.removeServiceForTest(PackageManagerInternal.class);
LocalServices.addService(PackageManagerInternal.class, mPmi);
- LocalServices.removeServiceForTest(UserManagerInternal.class);
- LocalServices.addService(UserManagerInternal.class, mUmi);
- LocalServices.removeServiceForTest(ActivityManagerInternal.class);
- LocalServices.addService(ActivityManagerInternal.class, mAmi);
when(mContext.getPackageManager()).thenReturn(mPm);
- when(mUmi.getUserIds()).thenReturn(new int[] { 0 });
-
- when(mPmi.getSharedUserIdForPackage(eq(PKG_GREY))).thenReturn(null);
- when(mPmi.getSharedUserIdForPackage(eq(PKG_RED))).thenReturn(NAME_COLORS);
- when(mPmi.getSharedUserIdForPackage(eq(PKG_BLUE))).thenReturn(NAME_COLORS);
-
- when(mPmi.getPackagesForSharedUserId(eq(NAME_COLORS), anyInt()))
- .thenReturn(new String[] { PKG_RED, PKG_BLUE });
-
- when(mPm.getPackagesForUid(eq(UID_GREY))).thenReturn(new String[] { PKG_GREY });
- when(mPm.getPackagesForUid(eq(UID_COLORS))).thenReturn(new String[] { PKG_RED, PKG_BLUE });
-
- setStorageMountMode(PID_BLUE, UID_COLORS, Zygote.MOUNT_EXTERNAL_WRITE);
- setStorageMountMode(PID_GREY, UID_GREY, Zygote.MOUNT_EXTERNAL_WRITE);
- setStorageMountMode(PID_RED, UID_COLORS, Zygote.MOUNT_EXTERNAL_WRITE);
-
mService = new StorageManagerService(mContext);
}
-
- private void setStorageMountMode(int pid, int uid, int mountMode) {
- when(mAmi.getStorageMountMode(pid, uid)).thenReturn(mountMode);
- }
-
- @Test
- public void testNone() throws Exception {
- assertTranslation(
- "/dev/null",
- "/dev/null", PID_GREY, UID_GREY);
- assertTranslation(
- "/dev/null",
- "/dev/null", PID_RED, UID_COLORS);
- }
-
- @Test
- public void testPrimary() throws Exception {
- assertTranslation(
- "/storage/emulated/0/Android/sandbox/com.grey/foo.jpg",
- "/storage/emulated/0/foo.jpg",
- PID_GREY, UID_GREY);
- assertTranslation(
- "/storage/emulated/0/Android/sandbox/shared-colors/foo.jpg",
- "/storage/emulated/0/foo.jpg",
- PID_RED, UID_COLORS);
- }
-
- @Test
- public void testSecondary() throws Exception {
- assertTranslation(
- "/storage/0000-0000/Android/sandbox/com.grey/foo/bar.jpg",
- "/storage/0000-0000/foo/bar.jpg",
- PID_GREY, UID_GREY);
- assertTranslation(
- "/storage/0000-0000/Android/sandbox/shared-colors/foo/bar.jpg",
- "/storage/0000-0000/foo/bar.jpg",
- PID_RED, UID_COLORS);
- }
-
- @Test
- public void testLegacy() throws Exception {
- // Accessing their own paths goes straight through
- assertTranslation(
- "/storage/emulated/0/Android/data/com.grey/foo.jpg",
- "/storage/emulated/0/Android/data/com.grey/foo.jpg",
- PID_GREY, UID_GREY);
-
- // Accessing other package paths goes into sandbox
- assertTranslation(
- "/storage/emulated/0/Android/sandbox/shared-colors/"
- + "Android/data/com.grey/foo.jpg",
- "/storage/emulated/0/Android/data/com.grey/foo.jpg",
- PID_RED, UID_COLORS);
- }
-
- @Test
- public void testLegacyShared() throws Exception {
- // Accessing their own paths goes straight through
- assertTranslation(
- "/storage/emulated/0/Android/data/com.red/foo.jpg",
- "/storage/emulated/0/Android/data/com.red/foo.jpg",
- PID_RED, UID_COLORS);
- assertTranslation(
- "/storage/emulated/0/Android/data/com.red/foo.jpg",
- "/storage/emulated/0/Android/data/com.red/foo.jpg",
- PID_BLUE, UID_COLORS);
-
- // Accessing other package paths goes into sandbox
- assertTranslation(
- "/storage/emulated/0/Android/sandbox/com.grey/"
- + "Android/data/com.red/foo.jpg",
- "/storage/emulated/0/Android/data/com.red/foo.jpg",
- PID_GREY, UID_GREY);
- }
-
- @Test
- public void testSecurity() throws Exception {
- // Shady paths should throw
- try {
- mService.translateAppToSystem(
- "/storage/emulated/0/../foo.jpg",
- PID_GREY, UID_GREY);
- fail();
- } catch (SecurityException expected) {
- }
-
- // Sandboxes can't see system paths
- try {
- mService.translateSystemToApp(
- "/storage/emulated/0/foo.jpg",
- PID_GREY, UID_GREY);
- fail();
- } catch (SecurityException expected) {
- }
-
- // Sandboxes can't see paths in other sandboxes
- try {
- mService.translateSystemToApp(
- "/storage/emulated/0/Android/sandbox/shared-colors/foo.jpg",
- PID_GREY, UID_GREY);
- fail();
- } catch (SecurityException expected) {
- }
- }
-
- @Test
- public void testPackageNotSandboxed() throws Exception {
- setStorageMountMode(PID_RED, UID_COLORS, Zygote.MOUNT_EXTERNAL_FULL);
-
- // Both app and system have the same view
- assertTranslation(
- "/storage/emulated/0/Android/data/com.red/foo.jpg",
- "/storage/emulated/0/Android/data/com.red/foo.jpg",
- PID_RED, UID_COLORS);
-
- assertTranslation(
- "/storage/emulated/0/Android/sandbox/com.grey/bar.jpg",
- "/storage/emulated/0/Android/sandbox/com.grey/bar.jpg",
- PID_RED, UID_COLORS);
- }
-
- @Test
- public void testPackageInLegacyMode() throws Exception {
- setStorageMountMode(PID_RED, UID_COLORS, Zygote.MOUNT_EXTERNAL_LEGACY);
-
- // Both app and system have the same view
- assertTranslation(
- "/storage/emulated/0/Android/data/com.red/foo.jpg",
- "/storage/emulated/0/Android/data/com.red/foo.jpg",
- PID_RED, UID_COLORS);
-
- assertTranslation(
- "/storage/emulated/0/Android/sandbox/com.grey/bar.jpg",
- "/storage/emulated/0/Android/sandbox/com.grey/bar.jpg",
- PID_RED, UID_COLORS);
- }
-
- @Test
- public void testInstallerPackage() throws Exception {
- setStorageMountMode(PID_GREY, UID_GREY, Zygote.MOUNT_EXTERNAL_INSTALLER);
-
- assertTranslation(
- "/storage/emulated/0/Android/obb/com.grey/foo.jpg",
- "/storage/emulated/0/Android/obb/com.grey/foo.jpg",
- PID_GREY, UID_GREY);
- assertTranslation(
- "/storage/emulated/0/Android/obb/com.blue/bar.jpg",
- "/storage/emulated/0/Android/obb/com.blue/bar.jpg",
- PID_GREY, UID_GREY);
-
- assertTranslation(
- "/storage/emulated/0/Android/data/com.grey/foo.jpg",
- "/storage/emulated/0/Android/data/com.grey/foo.jpg",
- PID_GREY, UID_GREY);
- assertTranslation(
- "/storage/emulated/0/Android/sandbox/com.grey/Android/data/com.blue/bar.jpg",
- "/storage/emulated/0/Android/data/com.blue/bar.jpg",
- PID_GREY, UID_GREY);
- }
-
- private void assertTranslation(String system, String sandbox,
- int pid, int uid) throws Exception {
- assertEquals(system,
- mService.translateAppToSystem(sandbox, pid, uid));
- assertEquals(sandbox,
- mService.translateSystemToApp(system, pid, uid));
- }
}
diff --git a/services/tests/wmtests/src/com/android/server/wm/DisplayContentTests.java b/services/tests/wmtests/src/com/android/server/wm/DisplayContentTests.java
index e60e54c9e44f..f49a57534938 100644
--- a/services/tests/wmtests/src/com/android/server/wm/DisplayContentTests.java
+++ b/services/tests/wmtests/src/com/android/server/wm/DisplayContentTests.java
@@ -19,6 +19,7 @@ package com.android.server.wm;
import static android.content.pm.ActivityInfo.SCREEN_ORIENTATION_LANDSCAPE;
import static android.content.pm.ActivityInfo.SCREEN_ORIENTATION_PORTRAIT;
import static android.content.pm.ActivityInfo.SCREEN_ORIENTATION_UNSPECIFIED;
+import static android.content.pm.ActivityInfo.SCREEN_ORIENTATION_USER;
import static android.os.Build.VERSION_CODES.P;
import static android.os.Build.VERSION_CODES.Q;
import static android.view.Display.DEFAULT_DISPLAY;
@@ -29,6 +30,7 @@ import static android.view.WindowManager.LayoutParams.FLAG_LAYOUT_INSET_DECOR;
import static android.view.WindowManager.LayoutParams.FLAG_LAYOUT_IN_SCREEN;
import static android.view.WindowManager.LayoutParams.TYPE_APPLICATION;
import static android.view.WindowManager.LayoutParams.TYPE_APPLICATION_ATTACHED_DIALOG;
+import static android.view.WindowManager.LayoutParams.TYPE_APPLICATION_OVERLAY;
import static android.view.WindowManager.LayoutParams.TYPE_BASE_APPLICATION;
import static android.view.WindowManager.LayoutParams.TYPE_STATUS_BAR;
import static android.view.WindowManager.LayoutParams.TYPE_VOICE_INTERACTION;
@@ -380,6 +382,14 @@ public class DisplayContentTests extends WindowTestsBase {
assertTrue(window1.isFocused());
assertEquals(perDisplayFocusEnabled && targetSdk >= Q, window2.isFocused());
assertEquals(window1, mWm.mRoot.getTopFocusedDisplayContent().mCurrentFocus);
+
+ // Make sure top focused display not changed if there is a focused app.
+ window1.mAppToken.hiddenRequested = true;
+ window1.getDisplayContent().setFocusedApp(window1.mAppToken);
+ updateFocusedWindow();
+ assertTrue(!window1.isFocused());
+ assertEquals(window1.getDisplayId(),
+ mWm.mRoot.getTopFocusedDisplayContent().getDisplayId());
}
/**
@@ -528,6 +538,43 @@ public class DisplayContentTests extends WindowTestsBase {
}
@Test
+ public void testOrientationForAspectRatio() {
+ final DisplayContent dc = createNewDisplay();
+
+ // When display content is created its configuration is not yet initialized, which could
+ // cause unnecessary configuration propagation, so initialize it here.
+ final Configuration config = new Configuration();
+ dc.computeScreenConfiguration(config);
+ dc.onRequestedOverrideConfigurationChanged(config);
+
+ // Create a window that requests a fixed orientation. It will define device orientation
+ // by default.
+ final WindowState window = createWindow(null /* parent */, TYPE_APPLICATION_OVERLAY, dc,
+ "window");
+ window.mHasSurface = true;
+ window.mAttrs.screenOrientation = SCREEN_ORIENTATION_LANDSCAPE;
+
+ // --------------------------------
+ // Test non-close-to-square display
+ // --------------------------------
+ dc.mBaseDisplayWidth = 1000;
+ dc.mBaseDisplayHeight = (int) (dc.mBaseDisplayWidth * dc.mCloseToSquareMaxAspectRatio * 2f);
+ dc.configureDisplayPolicy();
+
+ assertEquals("Screen orientation must be defined by the window by default.",
+ window.mAttrs.screenOrientation, dc.getOrientation());
+
+ // ----------------------------
+ // Test close-to-square display
+ // ----------------------------
+ dc.mBaseDisplayHeight = dc.mBaseDisplayWidth;
+ dc.configureDisplayPolicy();
+
+ assertEquals("Screen orientation must be SCREEN_ORIENTATION_USER.",
+ SCREEN_ORIENTATION_USER, dc.getOrientation());
+ }
+
+ @Test
public void testDisableDisplayInfoOverrideFromWindowManager() {
final DisplayContent dc = createNewDisplay();
diff --git a/services/tests/wmtests/src/com/android/server/wm/DisplayRotationTests.java b/services/tests/wmtests/src/com/android/server/wm/DisplayRotationTests.java
index 1c10ffb01f8e..49d38c062049 100644
--- a/services/tests/wmtests/src/com/android/server/wm/DisplayRotationTests.java
+++ b/services/tests/wmtests/src/com/android/server/wm/DisplayRotationTests.java
@@ -17,7 +17,6 @@
package com.android.server.wm;
import static android.content.pm.ActivityInfo.SCREEN_ORIENTATION_LANDSCAPE;
-import static android.content.pm.ActivityInfo.SCREEN_ORIENTATION_LOCKED;
import static android.content.pm.ActivityInfo.SCREEN_ORIENTATION_PORTRAIT;
import static android.content.pm.ActivityInfo.SCREEN_ORIENTATION_UNSPECIFIED;
@@ -394,19 +393,6 @@ public class DisplayRotationTests {
verifyOrientationListenerRegistration(0);
}
- @Test
- public void testNotEnablesSensor_ForceDefaultRotation_Squared() throws Exception {
- mBuilder.build();
- configureDisplayRotation(SCREEN_ORIENTATION_LOCKED, false, false);
-
- when(mMockDisplayPolicy.isScreenOnEarly()).thenReturn(true);
- when(mMockDisplayPolicy.isAwake()).thenReturn(true);
- when(mMockDisplayPolicy.isKeyguardDrawComplete()).thenReturn(true);
- when(mMockDisplayPolicy.isWindowManagerDrawComplete()).thenReturn(true);
- mTarget.updateOrientationListener();
- verifyOrientationListenerRegistration(0);
- }
-
private void enableOrientationSensor() {
when(mMockDisplayPolicy.isScreenOnEarly()).thenReturn(true);
when(mMockDisplayPolicy.isAwake()).thenReturn(true);
@@ -533,15 +519,6 @@ public class DisplayRotationTests {
}
@Test
- public void testReturnsUserRotation_ForceDefaultRotation_Squared() throws Exception {
- mBuilder.build();
- configureDisplayRotation(SCREEN_ORIENTATION_LOCKED, false, false);
-
- assertEquals(Surface.ROTATION_0, mTarget.rotationForOrientation(SCREEN_ORIENTATION_PORTRAIT,
- Surface.ROTATION_180));
- }
-
- @Test
public void testReturnsLidOpenRotation_LidOpen() throws Exception {
mBuilder.setLidOpenRotation(Surface.ROTATION_90).build();
configureDisplayRotation(SCREEN_ORIENTATION_LANDSCAPE, false, false);
@@ -643,14 +620,9 @@ public class DisplayRotationTests {
width = 1080;
height = 1920;
break;
- case SCREEN_ORIENTATION_LOCKED:
- // We use locked for squared display.
- width = 1080;
- height = 1080;
- break;
default:
- throw new IllegalArgumentException("displayOrientation needs to be landscape, "
- + "portrait or locked, but we got "
+ throw new IllegalArgumentException("displayOrientation needs to be either landscape"
+ + " or portrait, but we got "
+ ActivityInfo.screenOrientationToString(displayOrientation));
}
@@ -660,10 +632,6 @@ public class DisplayRotationTests {
.thenReturn(isCar);
when(mockPackageManager.hasSystemFeature(PackageManager.FEATURE_LEANBACK))
.thenReturn(isTv);
- when(mMockDisplayPolicy.getNonDecorDisplayWidth(anyInt(), anyInt(), anyInt(), anyInt(),
- any())).thenReturn(width);
- when(mMockDisplayPolicy.getNonDecorDisplayHeight(anyInt(), anyInt(), anyInt(), anyInt(),
- any())).thenReturn(height);
final int shortSizeDp = (isCar || isTv) ? 540 : 720;
final int longSizeDp = 960;
@@ -831,9 +799,6 @@ public class DisplayRotationTests {
.thenReturn(convertRotationToDegrees(mDeskDockRotation));
when(mMockRes.getInteger(com.android.internal.R.integer.config_undockedHdmiRotation))
.thenReturn(convertRotationToDegrees(mUndockedHdmiRotation));
- when(mMockRes.getFloat(
- com.android.internal.R.dimen.config_closeToSquareDisplayMaxAspectRatio))
- .thenReturn(1.33f);
mMockSensorManager = mock(SensorManager.class);
when(mMockContext.getSystemService(Context.SENSOR_SERVICE))
diff --git a/services/tests/wmtests/src/com/android/server/wm/LockTaskControllerTest.java b/services/tests/wmtests/src/com/android/server/wm/LockTaskControllerTest.java
index e24eb75a2750..47c76fc28d15 100644
--- a/services/tests/wmtests/src/com/android/server/wm/LockTaskControllerTest.java
+++ b/services/tests/wmtests/src/com/android/server/wm/LockTaskControllerTest.java
@@ -407,7 +407,7 @@ public class LockTaskControllerTest {
mLockTaskController.startLockTaskMode(tr1, false, TEST_UID);
mLockTaskController.startLockTaskMode(tr2, false, TEST_UID);
- // WHEN calling stopLockTaskMode on the root task
+ // WHEN calling clearLockedTasks on the root task
mLockTaskController.clearLockedTasks("testClearLockedTasks");
// THEN the lock task mode should be inactive
@@ -421,6 +421,80 @@ public class LockTaskControllerTest {
}
@Test
+ public void testClearLockedTasks_noLockSetting_noPassword_deviceIsUnlocked() throws Exception {
+ // GIVEN There is no setting set for LOCK_TO_APP_EXIT_LOCKED
+ Settings.Secure.clearProviderForTest();
+
+ // AND no password is set
+ when(mLockPatternUtils.getKeyguardStoredPasswordQuality(anyInt()))
+ .thenReturn(DevicePolicyManager.PASSWORD_QUALITY_UNSPECIFIED);
+
+ // AND there is a task record
+ TaskRecord tr1 = getTaskRecord(TaskRecord.LOCK_TASK_AUTH_WHITELISTED);
+ mLockTaskController.startLockTaskMode(tr1, true, TEST_UID);
+
+ // WHEN calling clearLockedTasks on the root task
+ mLockTaskController.clearLockedTasks("testClearLockedTasks");
+
+ // THEN the device should not be locked
+ verify(mWindowManager, never()).lockNow(any());
+ }
+
+ @Test
+ public void testClearLockedTasks_noLockSetting_password_deviceIsLocked() throws Exception {
+ // GIVEN There is no setting set for LOCK_TO_APP_EXIT_LOCKED
+ Settings.Secure.clearProviderForTest();
+
+ // AND a password is set
+ when(mLockPatternUtils.isSecure(anyInt()))
+ .thenReturn(true);
+
+ // AND there is a task record
+ TaskRecord tr1 = getTaskRecord(TaskRecord.LOCK_TASK_AUTH_WHITELISTED);
+ mLockTaskController.startLockTaskMode(tr1, true, TEST_UID);
+
+ // WHEN calling clearLockedTasks on the root task
+ mLockTaskController.clearLockedTasks("testClearLockedTasks");
+
+ // THEN the device should be locked
+ verify(mWindowManager, times(1)).lockNow(any());
+ }
+
+ @Test
+ public void testClearLockedTasks_lockSettingTrue_deviceIsLocked() throws Exception {
+ // GIVEN LOCK_TO_APP_EXIT_LOCKED is set to 1
+ Settings.Secure.putIntForUser(mContext.getContentResolver(),
+ Settings.Secure.LOCK_TO_APP_EXIT_LOCKED, 1, mContext.getUserId());
+
+ // AND there is a task record
+ TaskRecord tr1 = getTaskRecord(TaskRecord.LOCK_TASK_AUTH_WHITELISTED);
+ mLockTaskController.startLockTaskMode(tr1, true, TEST_UID);
+
+ // WHEN calling clearLockedTasks on the root task
+ mLockTaskController.clearLockedTasks("testClearLockedTasks");
+
+ // THEN the device should be locked
+ verify(mWindowManager, times(1)).lockNow(any());
+ }
+
+ @Test
+ public void testClearLockedTasks_lockSettingFalse_doesNotRequirePassword() throws Exception {
+ // GIVEN LOCK_TO_APP_EXIT_LOCKED is set to 1
+ Settings.Secure.putIntForUser(mContext.getContentResolver(),
+ Settings.Secure.LOCK_TO_APP_EXIT_LOCKED, 0, mContext.getUserId());
+
+ // AND there is a task record
+ TaskRecord tr1 = getTaskRecord(TaskRecord.LOCK_TASK_AUTH_WHITELISTED);
+ mLockTaskController.startLockTaskMode(tr1, true, TEST_UID);
+
+ // WHEN calling clearLockedTasks on the root task
+ mLockTaskController.clearLockedTasks("testClearLockedTasks");
+
+ // THEN the device should be unlocked
+ verify(mWindowManager, never()).lockNow(any());
+ }
+
+ @Test
public void testUpdateLockTaskPackages() {
String[] whitelist1 = {TEST_PACKAGE_NAME, TEST_PACKAGE_NAME_2};
String[] whitelist2 = {TEST_PACKAGE_NAME};
diff --git a/services/usage/java/com/android/server/usage/UsageStatsDatabase.java b/services/usage/java/com/android/server/usage/UsageStatsDatabase.java
index c55bb3cf0ffe..5197b3bad14b 100644
--- a/services/usage/java/com/android/server/usage/UsageStatsDatabase.java
+++ b/services/usage/java/com/android/server/usage/UsageStatsDatabase.java
@@ -17,7 +17,6 @@
package com.android.server.usage;
import android.app.usage.TimeSparseArray;
-import android.app.usage.UsageEvents;
import android.app.usage.UsageStats;
import android.app.usage.UsageStatsManager;
import android.os.Build;
@@ -94,12 +93,10 @@ public class UsageStatsDatabase {
// Persist versioned backup files.
// Should be false, except when testing new versions
- // STOPSHIP: b/111422946 this should be false on launch
- static final boolean KEEP_BACKUP_DIR = true;
+ static final boolean KEEP_BACKUP_DIR = false;
private static final String TAG = "UsageStatsDatabase";
- // STOPSHIP: b/111422946 this should be boolean DEBUG = UsageStatsService.DEBUG; on launch
- private static final boolean DEBUG = true;
+ private static final boolean DEBUG = UsageStatsService.DEBUG;
private static final String BAK_SUFFIX = ".bak";
private static final String CHECKED_IN_SUFFIX = UsageStatsXml.CHECKED_IN_SUFFIX;
private static final String RETENTION_LEN_KEY = "ro.usagestats.chooser.retention";
@@ -872,111 +869,6 @@ public class UsageStatsDatabase {
Slog.e(TAG, "UsageStatsDatabase", e);
throw e;
}
- // If old version, don't bother sanity checking
- if (version < 4) return;
-
- // STOPSHIP: b/111422946, b/115429334
- // Everything below this comment is sanity check against the new database version.
- // After the new version has soaked for some time the following should removed.
- // The goal of this check is to make sure the the ProtoInputStream is properly reading from
- // the UsageStats files.
- final StringBuilder sb = new StringBuilder();
- final int failureLogLimit = 10;
- int failures = 0;
-
- final int packagesSize = statsOut.packageStats.size();
- for (int i = 0; i < packagesSize; i++) {
- final UsageStats stat = statsOut.packageStats.valueAt(i);
- if (stat == null) {
- // ArrayMap may contain null values, skip them
- continue;
- }
- if (stat.mPackageName.isEmpty()) {
- if (failures++ < failureLogLimit) {
- sb.append("\nUnexpected empty usage stats package name loaded");
- }
- }
- if (stat.mBeginTimeStamp > statsOut.endTime) {
- if (failures++ < failureLogLimit) {
- sb.append("\nUnreasonable usage stats stat begin timestamp ");
- sb.append(stat.mBeginTimeStamp);
- sb.append(" loaded (beginTime : ");
- sb.append(statsOut.beginTime);
- sb.append(", endTime : ");
- sb.append(statsOut.endTime);
- sb.append(")");
- }
- }
- if (stat.mEndTimeStamp > statsOut.endTime) {
- if (failures++ < failureLogLimit) {
- sb.append("\nUnreasonable usage stats stat end timestamp ");
- sb.append(stat.mEndTimeStamp);
- sb.append(" loaded (beginTime : ");
- sb.append(statsOut.beginTime);
- sb.append(", endTime : ");
- sb.append(statsOut.endTime);
- sb.append(")");
- }
- }
- if (stat.mLastTimeUsed > statsOut.endTime) {
- if (failures++ < failureLogLimit) {
- sb.append("\nUnreasonable usage stats stat last used timestamp ");
- sb.append(stat.mLastTimeUsed);
- sb.append(" loaded (beginTime : ");
- sb.append(statsOut.beginTime);
- sb.append(", endTime : ");
- sb.append(statsOut.endTime);
- sb.append(")");
- }
- }
- }
-
- final int eventSize = statsOut.events.size();
- for (int i = 0; i < eventSize; i++) {
- final UsageEvents.Event event = statsOut.events.get(i);
- if (event.mPackage.isEmpty()) {
- if (failures++ < failureLogLimit) {
- sb.append("\nUnexpected empty empty package name loaded");
- }
- }
- if (event.mTimeStamp < statsOut.beginTime || event.mTimeStamp > statsOut.endTime) {
- if (failures++ < failureLogLimit) {
- sb.append("\nUnexpected event timestamp ");
- sb.append(event.mTimeStamp);
- sb.append(" loaded (beginTime : ");
- sb.append(statsOut.beginTime);
- sb.append(", endTime : ");
- sb.append(statsOut.endTime);
- sb.append(")");
- }
- }
- if (event.mEventType < 0 || event.mEventType > UsageEvents.Event.MAX_EVENT_TYPE) {
- if (failures++ < failureLogLimit) {
- sb.append("\nUnexpected event type ");
- sb.append(event.mEventType);
- sb.append(" loaded");
- }
- }
- if ((event.mFlags & ~UsageEvents.Event.VALID_FLAG_BITS) != 0) {
- if (failures++ < failureLogLimit) {
- sb.append("\nUnexpected event flag bit 0b");
- sb.append(Integer.toBinaryString(event.mFlags));
- sb.append(" loaded");
- }
- }
- }
-
- if (failures != 0) {
- if (failures > failureLogLimit) {
- sb.append("\nFailure log limited (");
- sb.append(failures);
- sb.append(" total failures found!)");
- }
- sb.append("\nError found in:\n");
- sb.append(file.getBaseFile().getAbsolutePath());
- sb.append("\nPlease go to b/115429334 to help root cause this issue");
- Slog.wtf(TAG, sb.toString());
- }
}
private void readLocked(InputStream in, IntervalStats statsOut) throws IOException {
@@ -1280,4 +1172,16 @@ public class UsageStatsDatabase {
pw.decreaseIndent();
}
}
+
+ IntervalStats readIntervalStatsForFile(int interval, long fileName) {
+ synchronized (mLock) {
+ final IntervalStats stats = new IntervalStats();
+ try {
+ readLocked(mSortedStatFiles[interval].get(fileName, null), stats);
+ return stats;
+ } catch (Exception e) {
+ return null;
+ }
+ }
+ }
}
diff --git a/services/usage/java/com/android/server/usage/UsageStatsService.java b/services/usage/java/com/android/server/usage/UsageStatsService.java
index 1ec680f10a27..2298aa1dbf83 100644
--- a/services/usage/java/com/android/server/usage/UsageStatsService.java
+++ b/services/usage/java/com/android/server/usage/UsageStatsService.java
@@ -774,6 +774,62 @@ public class UsageStatsService extends SystemService implements
mAppTimeLimit.dump(remainingArgs, pw);
}
return;
+ } else if ("file".equals(arg)) {
+ final IndentingPrintWriter ipw = new IndentingPrintWriter(pw, " ");
+ if (i + 1 >= args.length) {
+ // dump everything for all users
+ final int numUsers = mUserState.size();
+ for (int user = 0; user < numUsers; user++) {
+ ipw.println("user=" + mUserState.keyAt(user));
+ ipw.increaseIndent();
+ mUserState.valueAt(user).dumpFile(ipw, null);
+ ipw.decreaseIndent();
+ }
+ } else {
+ final int user;
+ try {
+ user = Integer.valueOf(args[i + 1]);
+ } catch (NumberFormatException nfe) {
+ ipw.println("invalid user specified.");
+ return;
+ }
+ if (mUserState.indexOfKey(user) < 0) {
+ ipw.println("the specified user does not exist.");
+ return;
+ }
+ final String[] remainingArgs = Arrays.copyOfRange(
+ args, i + 2, args.length);
+ // dump everything for the specified user
+ mUserState.get(user).dumpFile(ipw, remainingArgs);
+ }
+ return;
+ } else if ("database-info".equals(arg)) {
+ final IndentingPrintWriter ipw = new IndentingPrintWriter(pw, " ");
+ if (i + 1 >= args.length) {
+ // dump info for all users
+ final int numUsers = mUserState.size();
+ for (int user = 0; user < numUsers; user++) {
+ ipw.println("user=" + mUserState.keyAt(user));
+ ipw.increaseIndent();
+ mUserState.valueAt(user).dumpDatabaseInfo(ipw);
+ ipw.decreaseIndent();
+ }
+ } else {
+ final int user;
+ try {
+ user = Integer.valueOf(args[i + 1]);
+ } catch (NumberFormatException nfe) {
+ ipw.println("invalid user specified.");
+ return;
+ }
+ if (mUserState.indexOfKey(user) < 0) {
+ ipw.println("the specified user does not exist.");
+ return;
+ }
+ // dump info only for the specified user
+ mUserState.get(user).dumpDatabaseInfo(ipw);
+ }
+ return;
} else if (arg != null && !arg.startsWith("-")) {
// Anything else that doesn't start with '-' is a pkg to filter
pkg = arg;
diff --git a/services/usage/java/com/android/server/usage/UserUsageStatsService.java b/services/usage/java/com/android/server/usage/UserUsageStatsService.java
index 26bfcc944400..bbc7e9b0efb1 100644
--- a/services/usage/java/com/android/server/usage/UserUsageStatsService.java
+++ b/services/usage/java/com/android/server/usage/UserUsageStatsService.java
@@ -28,6 +28,7 @@ import static android.app.usage.UsageStatsManager.INTERVAL_YEARLY;
import android.app.usage.ConfigurationStats;
import android.app.usage.EventList;
import android.app.usage.EventStats;
+import android.app.usage.TimeSparseArray;
import android.app.usage.UsageEvents;
import android.app.usage.UsageEvents.Event;
import android.app.usage.UsageStats;
@@ -38,6 +39,7 @@ import android.os.SystemClock;
import android.text.format.DateUtils;
import android.util.ArrayMap;
import android.util.ArraySet;
+import android.util.AtomicFile;
import android.util.Slog;
import android.util.SparseIntArray;
@@ -665,6 +667,77 @@ class UserUsageStatsService {
mDatabase.dump(pw, compact);
}
+ void dumpDatabaseInfo(IndentingPrintWriter ipw) {
+ mDatabase.dump(ipw, false);
+ }
+
+ void dumpFile(IndentingPrintWriter ipw, String[] args) {
+ if (args == null || args.length == 0) {
+ // dump all files for every interval for specified user
+ final int numIntervals = mDatabase.mSortedStatFiles.length;
+ for (int interval = 0; interval < numIntervals; interval++) {
+ ipw.println("interval=" + intervalToString(interval));
+ ipw.increaseIndent();
+ dumpFileDetailsForInterval(ipw, interval);
+ ipw.decreaseIndent();
+ }
+ } else {
+ final int interval;
+ try {
+ final int intervalValue = stringToInterval(args[0]);
+ if (intervalValue == -1) {
+ interval = Integer.valueOf(args[0]);
+ } else {
+ interval = intervalValue;
+ }
+ } catch (NumberFormatException nfe) {
+ ipw.println("invalid interval specified.");
+ return;
+ }
+ if (interval < 0 || interval >= mDatabase.mSortedStatFiles.length) {
+ ipw.println("the specified interval does not exist.");
+ return;
+ }
+ if (args.length == 1) {
+ // dump all files in the specified interval
+ dumpFileDetailsForInterval(ipw, interval);
+ } else {
+ // dump details only for the specified filename
+ final long filename;
+ try {
+ filename = Long.valueOf(args[1]);
+ } catch (NumberFormatException nfe) {
+ ipw.println("invalid filename specified.");
+ return;
+ }
+ final IntervalStats stats = mDatabase.readIntervalStatsForFile(interval, filename);
+ if (stats == null) {
+ ipw.println("the specified filename does not exist.");
+ return;
+ }
+ dumpFileDetails(ipw, stats, Long.valueOf(args[1]));
+ }
+ }
+ }
+
+ private void dumpFileDetailsForInterval(IndentingPrintWriter ipw, int interval) {
+ final TimeSparseArray<AtomicFile> files = mDatabase.mSortedStatFiles[interval];
+ final int numFiles = files.size();
+ for (int i = 0; i < numFiles; i++) {
+ final long filename = files.keyAt(i);
+ final IntervalStats stats = mDatabase.readIntervalStatsForFile(interval, filename);
+ dumpFileDetails(ipw, stats, filename);
+ ipw.println();
+ }
+ }
+
+ private void dumpFileDetails(IndentingPrintWriter ipw, IntervalStats stats, long filename) {
+ ipw.println("file=" + filename);
+ ipw.increaseIndent();
+ printIntervalStats(ipw, stats, false, false, null);
+ ipw.decreaseIndent();
+ }
+
static String formatDateTime(long dateTime, boolean pretty) {
if (pretty) {
return "\"" + sDateFormat.format(dateTime)+ "\"";
@@ -908,6 +981,21 @@ class UserUsageStatsService {
}
}
+ private static int stringToInterval(String interval) {
+ switch (interval.toLowerCase()) {
+ case "daily":
+ return INTERVAL_DAILY;
+ case "weekly":
+ return INTERVAL_WEEKLY;
+ case "monthly":
+ return INTERVAL_MONTHLY;
+ case "yearly":
+ return INTERVAL_YEARLY;
+ default:
+ return -1;
+ }
+ }
+
private static String eventToString(int eventType) {
switch (eventType) {
case Event.NONE:
diff --git a/services/usb/java/com/android/server/usb/UsbAlsaManager.java b/services/usb/java/com/android/server/usb/UsbAlsaManager.java
index 4874bcef1606..5239d976e66f 100644
--- a/services/usb/java/com/android/server/usb/UsbAlsaManager.java
+++ b/services/usb/java/com/android/server/usb/UsbAlsaManager.java
@@ -35,7 +35,9 @@ import com.android.server.usb.descriptors.UsbDescriptorParser;
import libcore.io.IoUtils;
import java.util.ArrayList;
+import java.util.Arrays;
import java.util.HashMap;
+import java.util.List;
/**
* UsbAlsaManager manages USB audio and MIDI devices.
@@ -61,6 +63,50 @@ public final class UsbAlsaManager {
private final ArrayList<UsbAlsaDevice> mAlsaDevices = new ArrayList<UsbAlsaDevice>();
private UsbAlsaDevice mSelectedDevice;
+ //
+ // Device Blacklist
+ //
+ // This exists due to problems with Sony game controllers which present as an audio device
+ // even if no headset is connected and have no way to set the volume on the unit.
+ // Handle this by simply declining to use them as an audio device.
+ private static final int USB_VENDORID_SONY = 0x054C;
+ private static final int USB_PRODUCTID_PS4CONTROLLER_ZCT1 = 0x05C4;
+ private static final int USB_PRODUCTID_PS4CONTROLLER_ZCT2 = 0x09CC;
+
+ private static final int USB_BLACKLIST_OUTPUT = 0x0001;
+ private static final int USB_BLACKLIST_INPUT = 0x0002;
+
+ private static class BlackListEntry {
+ final int mVendorId;
+ final int mProductId;
+ final int mFlags;
+
+ BlackListEntry(int vendorId, int productId, int flags) {
+ mVendorId = vendorId;
+ mProductId = productId;
+ mFlags = flags;
+ }
+ }
+
+ static final List<BlackListEntry> sDeviceBlacklist = Arrays.asList(
+ new BlackListEntry(USB_VENDORID_SONY,
+ USB_PRODUCTID_PS4CONTROLLER_ZCT1,
+ USB_BLACKLIST_OUTPUT),
+ new BlackListEntry(USB_VENDORID_SONY,
+ USB_PRODUCTID_PS4CONTROLLER_ZCT2,
+ USB_BLACKLIST_OUTPUT));
+
+ private static boolean isDeviceBlacklisted(int vendorId, int productId, int flags) {
+ for (BlackListEntry entry : sDeviceBlacklist) {
+ if (entry.mVendorId == vendorId && entry.mProductId == productId) {
+ // see if the type flag is set
+ return (entry.mFlags & flags) != 0;
+ }
+ }
+
+ return false;
+ }
+
/**
* List of connected MIDI devices
*/
@@ -179,8 +225,12 @@ public final class UsbAlsaManager {
}
// Add it to the devices list
- boolean hasInput = parser.hasInput();
- boolean hasOutput = parser.hasOutput();
+ boolean hasInput = parser.hasInput()
+ && !isDeviceBlacklisted(usbDevice.getVendorId(), usbDevice.getProductId(),
+ USB_BLACKLIST_INPUT);
+ boolean hasOutput = parser.hasOutput()
+ && !isDeviceBlacklisted(usbDevice.getVendorId(), usbDevice.getProductId(),
+ USB_BLACKLIST_OUTPUT);
if (DEBUG) {
Slog.d(TAG, "hasInput: " + hasInput + " hasOutput:" + hasOutput);
}
diff --git a/services/voiceinteraction/java/com/android/server/voiceinteraction/VoiceInteractionSessionConnection.java b/services/voiceinteraction/java/com/android/server/voiceinteraction/VoiceInteractionSessionConnection.java
index 000a347783a3..f16dec6fb670 100644
--- a/services/voiceinteraction/java/com/android/server/voiceinteraction/VoiceInteractionSessionConnection.java
+++ b/services/voiceinteraction/java/com/android/server/voiceinteraction/VoiceInteractionSessionConnection.java
@@ -253,7 +253,7 @@ final class VoiceInteractionSessionConnection implements ServiceConnection,
if (data == null) {
try {
- mSession.handleAssist(-1, null, null, null, null, -1, 0);
+ mSession.handleAssist(-1, null, null, null, null, 0, 0);
} catch (RemoteException e) {
// Ignore
}
diff --git a/telephony/java/android/telephony/CarrierConfigManager.java b/telephony/java/android/telephony/CarrierConfigManager.java
index d2334d4a3125..9adc16f67102 100755
--- a/telephony/java/android/telephony/CarrierConfigManager.java
+++ b/telephony/java/android/telephony/CarrierConfigManager.java
@@ -2964,6 +2964,15 @@ public class CarrierConfigManager {
public static final String KEY_GSM_RSSI_THRESHOLDS_INT_ARRAY =
"gsm_rssi_thresholds_int_array";
+ /**
+ * Determines whether Wireless Priority Service call is supported over IMS.
+ *
+ * See Wireless Priority Service from https://www.fcc.gov/general/wireless-priority-service-wps
+ * @hide
+ */
+ public static final String KEY_SUPPORT_WPS_OVER_IMS_BOOL =
+ "support_wps_over_ims_bool";
+
/** The default value for every variable. */
private final static PersistableBundle sDefaults;
@@ -3381,6 +3390,7 @@ public class CarrierConfigManager {
-97, /* SIGNAL_STRENGTH_GOOD */
-89, /* SIGNAL_STRENGTH_GREAT */
});
+ sDefaults.putBoolean(KEY_SUPPORT_WPS_OVER_IMS_BOOL, true);
}
/**
diff --git a/telephony/java/android/telephony/TelephonyManager.java b/telephony/java/android/telephony/TelephonyManager.java
index aa9883d54a6a..328a0a7a9512 100644
--- a/telephony/java/android/telephony/TelephonyManager.java
+++ b/telephony/java/android/telephony/TelephonyManager.java
@@ -3836,10 +3836,12 @@ public class TelephonyManager {
}
/**
- * Return the set of subscriber IDs that should be considered as "merged
- * together" for data usage purposes. This is commonly {@code null} to
- * indicate no merging is required. Any returned subscribers are sorted in a
- * deterministic order.
+ * Return the set of subscriber IDs that should be considered "merged together" for data usage
+ * purposes. This is commonly {@code null} to indicate no merging is required. Any returned
+ * subscribers are sorted in a deterministic order.
+ * <p>
+ * The returned set of subscriber IDs will include the subscriber ID corresponding to this
+ * TelephonyManager's subId.
*
* @hide
*/
@@ -3848,7 +3850,7 @@ public class TelephonyManager {
try {
ITelephony telephony = getITelephony();
if (telephony != null)
- return telephony.getMergedSubscriberIds(getOpPackageName());
+ return telephony.getMergedSubscriberIds(getSubId(), getOpPackageName());
} catch (RemoteException ex) {
} catch (NullPointerException ex) {
}
diff --git a/telephony/java/android/telephony/ims/ImsSsData.java b/telephony/java/android/telephony/ims/ImsSsData.java
index 464db34d0d65..32b4382829df 100644
--- a/telephony/java/android/telephony/ims/ImsSsData.java
+++ b/telephony/java/android/telephony/ims/ImsSsData.java
@@ -457,7 +457,7 @@ public final class ImsSsData implements Parcelable {
}
public boolean isTypeInterrogation() {
- return (getServiceType() == SS_INTERROGATION);
+ return (getRequestType() == SS_INTERROGATION);
}
/**
diff --git a/telephony/java/com/android/internal/telephony/ITelephony.aidl b/telephony/java/com/android/internal/telephony/ITelephony.aidl
index f226bb1fa588..3991fea66a85 100644
--- a/telephony/java/com/android/internal/telephony/ITelephony.aidl
+++ b/telephony/java/com/android/internal/telephony/ITelephony.aidl
@@ -1051,7 +1051,17 @@ interface ITelephony {
*/
String getLine1AlphaTagForDisplay(int subId, String callingPackage);
- String[] getMergedSubscriberIds(String callingPackage);
+ /**
+ * Return the set of subscriber IDs that should be considered "merged together" for data usage
+ * purposes. This is commonly {@code null} to indicate no merging is required. Any returned
+ * subscribers are sorted in a deterministic order.
+ * <p>
+ * The returned set of subscriber IDs will include the subscriber ID corresponding to this
+ * TelephonyManager's subId.
+ *
+ * @hide
+ */
+ String[] getMergedSubscriberIds(int subId, String callingPackage);
/**
* Override the operator branding for the current ICCID.
diff --git a/tests/net/java/android/net/IpMemoryStoreTest.java b/tests/net/java/android/net/IpMemoryStoreTest.java
index 18c67688940a..8ff2de9777c9 100644
--- a/tests/net/java/android/net/IpMemoryStoreTest.java
+++ b/tests/net/java/android/net/IpMemoryStoreTest.java
@@ -16,10 +16,26 @@
package android.net;
-import static org.mockito.ArgumentMatchers.any;
+import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertFalse;
+import static org.junit.Assert.assertNull;
+import static org.junit.Assert.assertTrue;
+import static org.mockito.Mockito.any;
import static org.mockito.Mockito.doAnswer;
+import static org.mockito.Mockito.doNothing;
+import static org.mockito.Mockito.doThrow;
+import static org.mockito.Mockito.eq;
+import static org.mockito.Mockito.inOrder;
+import static org.mockito.Mockito.times;
+import static org.mockito.Mockito.verify;
import android.content.Context;
+import android.net.ipmemorystore.Blob;
+import android.net.ipmemorystore.IOnStatusListener;
+import android.net.ipmemorystore.NetworkAttributes;
+import android.net.ipmemorystore.NetworkAttributesParcelable;
+import android.net.ipmemorystore.Status;
+import android.os.RemoteException;
import androidx.test.filters.SmallTest;
import androidx.test.runner.AndroidJUnit4;
@@ -27,28 +43,57 @@ import androidx.test.runner.AndroidJUnit4;
import org.junit.Before;
import org.junit.Test;
import org.junit.runner.RunWith;
+import org.mockito.ArgumentCaptor;
+import org.mockito.Captor;
+import org.mockito.InOrder;
import org.mockito.Mock;
import org.mockito.MockitoAnnotations;
+import java.net.UnknownHostException;
+import java.util.Arrays;
+
@RunWith(AndroidJUnit4.class)
@SmallTest
public class IpMemoryStoreTest {
+ private static final String TAG = IpMemoryStoreTest.class.getSimpleName();
+ private static final String TEST_CLIENT_ID = "testClientId";
+ private static final String TEST_DATA_NAME = "testData";
+ private static final String TEST_OTHER_DATA_NAME = TEST_DATA_NAME + "Other";
+ private static final byte[] TEST_BLOB_DATA = new byte[] { -3, 6, 8, -9, 12,
+ -128, 0, 89, 112, 91, -34 };
+ private static final NetworkAttributes TEST_NETWORK_ATTRIBUTES = buildTestNetworkAttributes(
+ "hint", 219);
+
@Mock
Context mMockContext;
@Mock
NetworkStackClient mNetworkStackClient;
@Mock
IIpMemoryStore mMockService;
+ @Mock
+ IOnStatusListener mIOnStatusListener;
IpMemoryStore mStore;
+ @Captor
+ ArgumentCaptor<IIpMemoryStoreCallbacks> mCbCaptor;
+ @Captor
+ ArgumentCaptor<NetworkAttributesParcelable> mNapCaptor;
+
@Before
public void setUp() {
MockitoAnnotations.initMocks(this);
- doAnswer(invocation -> {
- ((IIpMemoryStoreCallbacks) invocation.getArgument(0))
- .onIpMemoryStoreFetched(mMockService);
- return null;
- }).when(mNetworkStackClient).fetchIpMemoryStore(any());
+ }
+
+ private void startIpMemoryStore(boolean supplyService) {
+ if (supplyService) {
+ doAnswer(invocation -> {
+ ((IIpMemoryStoreCallbacks) invocation.getArgument(0))
+ .onIpMemoryStoreFetched(mMockService);
+ return null;
+ }).when(mNetworkStackClient).fetchIpMemoryStore(any());
+ } else {
+ doNothing().when(mNetworkStackClient).fetchIpMemoryStore(mCbCaptor.capture());
+ }
mStore = new IpMemoryStore(mMockContext) {
@Override
protected NetworkStackClient getNetworkStackClient() {
@@ -57,24 +102,228 @@ public class IpMemoryStoreTest {
};
}
+ private static NetworkAttributes buildTestNetworkAttributes(String hint, int mtu) {
+ return new NetworkAttributes.Builder()
+ .setGroupHint(hint)
+ .setMtu(mtu)
+ .build();
+ }
+
+ @Test
+ public void testNetworkAttributes() throws Exception {
+ startIpMemoryStore(true);
+ final String l2Key = "fakeKey";
+
+ mStore.storeNetworkAttributes(l2Key, TEST_NETWORK_ATTRIBUTES,
+ status -> {
+ assertTrue("Store not successful : " + status.resultCode, status.isSuccess());
+ });
+ verify(mMockService, times(1)).storeNetworkAttributes(eq(l2Key),
+ mNapCaptor.capture(), any());
+ assertEquals(TEST_NETWORK_ATTRIBUTES, new NetworkAttributes(mNapCaptor.getValue()));
+
+ mStore.retrieveNetworkAttributes(l2Key,
+ (status, key, attr) -> {
+ assertTrue("Retrieve network attributes not successful : "
+ + status.resultCode, status.isSuccess());
+ assertEquals(l2Key, key);
+ assertEquals(TEST_NETWORK_ATTRIBUTES, attr);
+ });
+
+ verify(mMockService, times(1)).retrieveNetworkAttributes(eq(l2Key), any());
+ }
+
+ @Test
+ public void testPrivateData() throws RemoteException {
+ startIpMemoryStore(true);
+ final Blob b = new Blob();
+ b.data = TEST_BLOB_DATA;
+ final String l2Key = "fakeKey";
+
+ mStore.storeBlob(l2Key, TEST_CLIENT_ID, TEST_DATA_NAME, b,
+ status -> {
+ assertTrue("Store not successful : " + status.resultCode, status.isSuccess());
+ });
+ verify(mMockService, times(1)).storeBlob(eq(l2Key), eq(TEST_CLIENT_ID), eq(TEST_DATA_NAME),
+ eq(b), any());
+
+ mStore.retrieveBlob(l2Key, TEST_CLIENT_ID, TEST_OTHER_DATA_NAME,
+ (status, key, name, data) -> {
+ assertTrue("Retrieve blob status not successful : " + status.resultCode,
+ status.isSuccess());
+ assertEquals(l2Key, key);
+ assertEquals(name, TEST_DATA_NAME);
+ assertTrue(Arrays.equals(b.data, data.data));
+ });
+ verify(mMockService, times(1)).retrieveBlob(eq(l2Key), eq(TEST_CLIENT_ID),
+ eq(TEST_OTHER_DATA_NAME), any());
+ }
+
@Test
- public void testNetworkAttributes() {
- // TODO : implement this
+ public void testFindL2Key()
+ throws UnknownHostException, RemoteException, Exception {
+ startIpMemoryStore(true);
+ final String l2Key = "fakeKey";
+
+ mStore.findL2Key(TEST_NETWORK_ATTRIBUTES,
+ (status, key) -> {
+ assertTrue("Retrieve network sameness not successful : " + status.resultCode,
+ status.isSuccess());
+ assertEquals(l2Key, key);
+ });
+ verify(mMockService, times(1)).findL2Key(mNapCaptor.capture(), any());
+ assertEquals(TEST_NETWORK_ATTRIBUTES, new NetworkAttributes(mNapCaptor.getValue()));
}
@Test
- public void testPrivateData() {
- // TODO : implement this
+ public void testIsSameNetwork() throws UnknownHostException, RemoteException {
+ startIpMemoryStore(true);
+ final String l2Key1 = "fakeKey1";
+ final String l2Key2 = "fakeKey2";
+
+ mStore.isSameNetwork(l2Key1, l2Key2,
+ (status, answer) -> {
+ assertFalse("Retrieve network sameness suspiciously successful : "
+ + status.resultCode, status.isSuccess());
+ assertEquals(Status.ERROR_ILLEGAL_ARGUMENT, status.resultCode);
+ assertNull(answer);
+ });
+ verify(mMockService, times(1)).isSameNetwork(eq(l2Key1), eq(l2Key2), any());
}
@Test
- public void testFindL2Key() {
- // TODO : implement this
+ public void testEnqueuedIpMsRequests() throws Exception {
+ startIpMemoryStore(false);
+
+ final Blob b = new Blob();
+ b.data = TEST_BLOB_DATA;
+ final String l2Key = "fakeKey";
+
+ // enqueue multiple ipms requests
+ mStore.storeNetworkAttributes(l2Key, TEST_NETWORK_ATTRIBUTES,
+ status -> {
+ assertTrue("Store not successful : " + status.resultCode, status.isSuccess());
+ });
+ mStore.retrieveNetworkAttributes(l2Key,
+ (status, key, attr) -> {
+ assertTrue("Retrieve network attributes not successful : "
+ + status.resultCode, status.isSuccess());
+ assertEquals(l2Key, key);
+ assertEquals(TEST_NETWORK_ATTRIBUTES, attr);
+ });
+ mStore.storeBlob(l2Key, TEST_CLIENT_ID, TEST_DATA_NAME, b,
+ status -> {
+ assertTrue("Store not successful : " + status.resultCode, status.isSuccess());
+ });
+ mStore.retrieveBlob(l2Key, TEST_CLIENT_ID, TEST_OTHER_DATA_NAME,
+ (status, key, name, data) -> {
+ assertTrue("Retrieve blob status not successful : " + status.resultCode,
+ status.isSuccess());
+ assertEquals(l2Key, key);
+ assertEquals(name, TEST_DATA_NAME);
+ assertTrue(Arrays.equals(b.data, data.data));
+ });
+
+ // get ipms service ready
+ mCbCaptor.getValue().onIpMemoryStoreFetched(mMockService);
+
+ InOrder inOrder = inOrder(mMockService);
+
+ inOrder.verify(mMockService).storeNetworkAttributes(eq(l2Key), mNapCaptor.capture(), any());
+ inOrder.verify(mMockService).retrieveNetworkAttributes(eq(l2Key), any());
+ inOrder.verify(mMockService).storeBlob(eq(l2Key), eq(TEST_CLIENT_ID), eq(TEST_DATA_NAME),
+ eq(b), any());
+ inOrder.verify(mMockService).retrieveBlob(eq(l2Key), eq(TEST_CLIENT_ID),
+ eq(TEST_OTHER_DATA_NAME), any());
+ assertEquals(TEST_NETWORK_ATTRIBUTES, new NetworkAttributes(mNapCaptor.getValue()));
}
@Test
- public void testIsSameNetwork() {
- // TODO : implement this
+ public void testEnqueuedIpMsRequestsWithException() throws Exception {
+ startIpMemoryStore(true);
+ doThrow(RemoteException.class).when(mMockService).retrieveNetworkAttributes(any(), any());
+
+ final Blob b = new Blob();
+ b.data = TEST_BLOB_DATA;
+ final String l2Key = "fakeKey";
+
+ // enqueue multiple ipms requests
+ mStore.storeNetworkAttributes(l2Key, TEST_NETWORK_ATTRIBUTES,
+ status -> {
+ assertTrue("Store not successful : " + status.resultCode, status.isSuccess());
+ });
+ mStore.retrieveNetworkAttributes(l2Key,
+ (status, key, attr) -> {
+ assertTrue("Retrieve network attributes not successful : "
+ + status.resultCode, status.isSuccess());
+ assertEquals(l2Key, key);
+ assertEquals(TEST_NETWORK_ATTRIBUTES, attr);
+ });
+ mStore.storeBlob(l2Key, TEST_CLIENT_ID, TEST_DATA_NAME, b,
+ status -> {
+ assertTrue("Store not successful : " + status.resultCode, status.isSuccess());
+ });
+ mStore.retrieveBlob(l2Key, TEST_CLIENT_ID, TEST_OTHER_DATA_NAME,
+ (status, key, name, data) -> {
+ assertTrue("Retrieve blob status not successful : " + status.resultCode,
+ status.isSuccess());
+ assertEquals(l2Key, key);
+ assertEquals(name, TEST_DATA_NAME);
+ assertTrue(Arrays.equals(b.data, data.data));
+ });
+
+ // verify the rest of the queue is still processed in order even if the remote exception
+ // occurs when calling one or more requests
+ InOrder inOrder = inOrder(mMockService);
+
+ inOrder.verify(mMockService).storeNetworkAttributes(eq(l2Key), mNapCaptor.capture(), any());
+ inOrder.verify(mMockService).storeBlob(eq(l2Key), eq(TEST_CLIENT_ID), eq(TEST_DATA_NAME),
+ eq(b), any());
+ inOrder.verify(mMockService).retrieveBlob(eq(l2Key), eq(TEST_CLIENT_ID),
+ eq(TEST_OTHER_DATA_NAME), any());
+ assertEquals(TEST_NETWORK_ATTRIBUTES, new NetworkAttributes(mNapCaptor.getValue()));
}
+ @Test
+ public void testEnqueuedIpMsRequestsCallbackFunctionWithException() throws Exception {
+ startIpMemoryStore(true);
+
+ final Blob b = new Blob();
+ b.data = TEST_BLOB_DATA;
+ final String l2Key = "fakeKey";
+
+ // enqueue multiple ipms requests
+ mStore.storeNetworkAttributes(l2Key, TEST_NETWORK_ATTRIBUTES,
+ status -> {
+ assertTrue("Store not successful : " + status.resultCode, status.isSuccess());
+ });
+ mStore.retrieveNetworkAttributes(l2Key,
+ (status, key, attr) -> {
+ throw new RuntimeException("retrieveNetworkAttributes test");
+ });
+ mStore.storeBlob(l2Key, TEST_CLIENT_ID, TEST_DATA_NAME, b,
+ status -> {
+ throw new RuntimeException("storeBlob test");
+ });
+ mStore.retrieveBlob(l2Key, TEST_CLIENT_ID, TEST_OTHER_DATA_NAME,
+ (status, key, name, data) -> {
+ assertTrue("Retrieve blob status not successful : " + status.resultCode,
+ status.isSuccess());
+ assertEquals(l2Key, key);
+ assertEquals(name, TEST_DATA_NAME);
+ assertTrue(Arrays.equals(b.data, data.data));
+ });
+
+ // verify the rest of the queue is still processed in order even if when one or more
+ // callback throw the remote exception
+ InOrder inOrder = inOrder(mMockService);
+
+ inOrder.verify(mMockService).storeNetworkAttributes(eq(l2Key), mNapCaptor.capture(),
+ any());
+ inOrder.verify(mMockService).storeBlob(eq(l2Key), eq(TEST_CLIENT_ID), eq(TEST_DATA_NAME),
+ eq(b), any());
+ inOrder.verify(mMockService).retrieveBlob(eq(l2Key), eq(TEST_CLIENT_ID),
+ eq(TEST_OTHER_DATA_NAME), any());
+ assertEquals(TEST_NETWORK_ATTRIBUTES, new NetworkAttributes(mNapCaptor.getValue()));
+ }
}
diff --git a/tests/net/java/com/android/server/ConnectivityServiceTest.java b/tests/net/java/com/android/server/ConnectivityServiceTest.java
index 363ac9ce1d25..0ef56e553aa9 100644
--- a/tests/net/java/com/android/server/ConnectivityServiceTest.java
+++ b/tests/net/java/com/android/server/ConnectivityServiceTest.java
@@ -3854,6 +3854,9 @@ public class ConnectivityServiceTest {
networkCallback.expectCallback(CallbackState.UNAVAILABLE, null);
testFactory.waitForRequests();
+ // unregister network callback - a no-op, but should not fail
+ mCm.unregisterNetworkCallback(networkCallback);
+
testFactory.unregister();
handlerThread.quit();
}
diff --git a/tests/net/java/com/android/server/IpSecServiceParameterizedTest.java b/tests/net/java/com/android/server/IpSecServiceParameterizedTest.java
index 7c40adfac002..71b72b84de81 100644
--- a/tests/net/java/com/android/server/IpSecServiceParameterizedTest.java
+++ b/tests/net/java/com/android/server/IpSecServiceParameterizedTest.java
@@ -32,6 +32,7 @@ import static org.mockito.Mockito.when;
import android.app.AppOpsManager;
import android.content.Context;
+import android.content.pm.PackageManager;
import android.net.INetd;
import android.net.IpSecAlgorithm;
import android.net.IpSecConfig;
@@ -57,6 +58,7 @@ import org.junit.Test;
import org.junit.runner.RunWith;
import org.junit.runners.Parameterized;
+import java.net.Inet4Address;
import java.net.Socket;
import java.util.Arrays;
import java.util.Collection;
@@ -119,6 +121,11 @@ public class IpSecServiceParameterizedTest {
}
@Override
+ public PackageManager getPackageManager() {
+ return mMockPkgMgr;
+ }
+
+ @Override
public void enforceCallingOrSelfPermission(String permission, String message) {
if (permission == android.Manifest.permission.MANAGE_IPSEC_TUNNELS) {
return;
@@ -128,6 +135,7 @@ public class IpSecServiceParameterizedTest {
};
INetd mMockNetd;
+ PackageManager mMockPkgMgr;
IpSecService.IpSecServiceConfiguration mMockIpSecSrvConfig;
IpSecService mIpSecService;
Network fakeNetwork = new Network(0xAB);
@@ -152,11 +160,16 @@ public class IpSecServiceParameterizedTest {
@Before
public void setUp() throws Exception {
mMockNetd = mock(INetd.class);
+ mMockPkgMgr = mock(PackageManager.class);
mMockIpSecSrvConfig = mock(IpSecService.IpSecServiceConfiguration.class);
mIpSecService = new IpSecService(mMockContext, mMockIpSecSrvConfig);
// Injecting mock netd
when(mMockIpSecSrvConfig.getNetdInstance()).thenReturn(mMockNetd);
+
+ // PackageManager should always return true (feature flag tests in IpSecServiceTest)
+ when(mMockPkgMgr.hasSystemFeature(anyString())).thenReturn(true);
+
// A package granted the AppOp for MANAGE_IPSEC_TUNNELS will be MODE_ALLOWED.
when(mMockAppOps.noteOp(anyInt(), anyInt(), eq("blessedPackage")))
.thenReturn(AppOpsManager.MODE_ALLOWED);
@@ -709,4 +722,18 @@ public class IpSecServiceParameterizedTest {
} catch (SecurityException expected) {
}
}
+
+ @Test
+ public void testFeatureFlagVerification() throws Exception {
+ when(mMockPkgMgr.hasSystemFeature(eq(PackageManager.FEATURE_IPSEC_TUNNELS)))
+ .thenReturn(false);
+
+ try {
+ String addr = Inet4Address.getLoopbackAddress().getHostAddress();
+ mIpSecService.createTunnelInterface(
+ addr, addr, new Network(0), new Binder(), "blessedPackage");
+ fail("Expected UnsupportedOperationException for disabled feature");
+ } catch (UnsupportedOperationException expected) {
+ }
+ }
}
diff --git a/tests/net/java/com/android/server/net/ipmemorystore/NetworkAttributesTest.java b/tests/net/java/com/android/server/net/ipmemorystore/NetworkAttributesTest.java
index a83faf34776d..fb84611cb662 100644
--- a/tests/net/java/com/android/server/net/ipmemorystore/NetworkAttributesTest.java
+++ b/tests/net/java/com/android/server/net/ipmemorystore/NetworkAttributesTest.java
@@ -14,7 +14,7 @@
* limitations under the License.
*/
-package com.android.server.connectivity.ipmemorystore;
+package com.android.server.net.ipmemorystore;
import static org.junit.Assert.assertEquals;
diff --git a/tools/apilint/apilint b/tools/apilint/apilint
new file mode 100755
index 000000000000..e42857f1a190
--- /dev/null
+++ b/tools/apilint/apilint
@@ -0,0 +1,147 @@
+#!/bin/bash
+
+# Copyright (C) 2019 The Android Open Source Project
+#
+# Licensed under the Apache License, Version 2.0 (the 'License');
+# you may not use this file except in compliance with the License.
+# You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing, software
+# distributed under the License is distributed on an 'AS IS' BASIS,
+# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+# See the License for the specific language governing permissions and
+# limitations under the License.
+
+if [ "$1" == "--help" -o "$1" == "-h" ]; then
+echo "Usage: apilint [FILTERS...]"
+echo " Shows lint from currently open files (as diffed from HEAD), i.e. errors"
+echo " you will receive if you upload this CL."
+echo
+echo "Usage: apilint --all [FILTERS...]"
+echo " Shows all lint errors present in the current working directory, regardless"
+echo " of when they were added."
+echo
+echo "Usage: apilint --level API_LEVEL [FILTERS...]"
+echo " Shows lint as it stands in API_LEVEL"
+echo
+echo "Usage: apilint --shal SHA [FILTERS...]"
+echo " Shows lint from locally commited git change SHA."
+echo
+echo "Usage: apilint --unreleased [FILTERS...]"
+echo " Shows all lint errors in the current working directory directory added since"
+echo " the last released SDK version."
+echo
+echo "FILTERS"
+echo " List of class or package names by which to filter the results."
+echo
+exit
+fi
+
+if [ \( -z "$ANDROID_BUILD_TOP" \) \
+ -a \( ! -f frameworks/base/api/current.txt \) \
+ -a \( ! -f frameworks/base/api/system-current.txt \) \
+ ]; then
+ echo "apilint must be run either with ANDROID_BUILD_TOP set or from the" 1>&2
+ echo "root of the android source tree" 1>&2
+ exit 1
+fi
+
+if [ ${ANDROID_BUILD_TOP:0:1} != "/" ]; then
+ echo "ANDROID_BUILD_TOP must be an absolute path, not: $ANDROID_BUILD_TOP" 1>&2
+ exit 1
+fi
+
+if [ -z "$ANDROID_BUILD_TOP" ]; then
+ ANDROID_BUILD_TOP=$(pwd)
+fi
+
+FW_BASE=$ANDROID_BUILD_TOP/frameworks/base
+
+MODE=open
+
+OPTIONS=$(getopt -n apilint -o "" -l "all,sha:,unreleased" -- "$@")
+
+[ $? -eq 0 ] || {
+ exit 1
+}
+
+eval set -- "$OPTIONS"
+while true; do
+ case "$1" in
+ --all)
+ MODE=all
+ ;;
+ --sha)
+ shift; # The arg is next in position args
+ MODE=sha
+ SHA=$1
+ ;;
+ --unreleased)
+ MODE=unreleased
+ ;;
+ --)
+ shift
+ break
+ ;;
+ esac
+ shift
+done
+FILTERS=
+for var in "$@"
+do
+ FILTERS="$FILTERS --filter $var"
+done
+
+if [ $MODE = "all" ]; then
+ python2.7 -B $ANDROID_BUILD_TOP/frameworks/base/tools/apilint/apilint.py \
+ --title "SDK" \
+ $FILTERS \
+ $ANDROID_BUILD_TOP/frameworks/base/api/current.txt
+ python2.7 -B $ANDROID_BUILD_TOP/frameworks/base/tools/apilint/apilint.py \
+ --title "SystemApi" \
+ $FILTERS \
+ --base-current $ANDROID_BUILD_TOP/frameworks/base/api/current.txt \
+ $ANDROID_BUILD_TOP/frameworks/base/api/system-current.txt
+elif [ $MODE = "open" ]; then
+ python2.7 -B $ANDROID_BUILD_TOP/frameworks/base/tools/apilint/apilint.py \
+ --title "SDK" \
+ $FILTERS \
+ $ANDROID_BUILD_TOP/frameworks/base/api/current.txt \
+ <(cd $FW_BASE ; git show HEAD:api/current.txt)
+ python2.7 -B $ANDROID_BUILD_TOP/frameworks/base/tools/apilint/apilint.py \
+ --title "SystemApi" \
+ $FILTERS \
+ --base-current $ANDROID_BUILD_TOP/frameworks/base/api/current.txt \
+ --base-previous <(cd $FW_BASE ; git show HEAD:api/current.txt) \
+ $ANDROID_BUILD_TOP/frameworks/base/api/system-current.txt \
+ <(cd $FW_BASE ; git show HEAD:api/system-current.txt)
+elif [ $MODE = "sha" ]; then
+ python2.7 -B $ANDROID_BUILD_TOP/frameworks/base/tools/apilint/apilint.py \
+ --title "SDK" \
+ $FILTERS \
+ <(cd $FW_BASE ; git show $SHA:api/current.txt) \
+ <(cd $FW_BASE ; git show $SHA^:api/current.txt)
+ python2.7 -B $ANDROID_BUILD_TOP/frameworks/base/tools/apilint/apilint.py \
+ --title "SystemApi" \
+ $FILTERS \
+ --base-current <(cd $FW_BASE ; git show $SHA:api/current.txt) \
+ --base-previous <(cd $FW_BASE ; git show $SHA^:api/current.txt) \
+ <(cd $FW_BASE ; git show $SHA:api/system-current.txt) \
+ <(cd $FW_BASE ; git show $SHA^:api/system-current.txt)
+elif [ $MODE = "unreleased" ]; then
+ LAST_SDK=$(ls $ANDROID_BUILD_TOP/prebuilts/sdk | grep "^[0-9][0-9]*$" | sort -n | tail -n 1)
+ python2.7 -B $ANDROID_BUILD_TOP/frameworks/base/tools/apilint/apilint.py \
+ --title "SDK" \
+ $FILTERS \
+ $ANDROID_BUILD_TOP/frameworks/base/api/current.txt \
+ $ANDROID_BUILD_TOP/prebuilts/sdk/$LAST_SDK/public/api/android.txt
+ python2.7 -B $ANDROID_BUILD_TOP/frameworks/base/tools/apilint/apilint.py \
+ --title "SystemApi" \
+ $FILTERS \
+ --base-current $ANDROID_BUILD_TOP/frameworks/base/api/current.txt \
+ --base-previous $ANDROID_BUILD_TOP/prebuilts/sdk/$LAST_SDK/public/api/android.txt \
+ $ANDROID_BUILD_TOP/frameworks/base/api/system-current.txt \
+ $ANDROID_BUILD_TOP/prebuilts/sdk/$LAST_SDK/system/api/android.txt
+fi
diff --git a/tools/apilint/apilint.py b/tools/apilint/apilint.py
index f41426d84af1..9e42c044e209 100644
--- a/tools/apilint/apilint.py
+++ b/tools/apilint/apilint.py
@@ -707,6 +707,7 @@ def _yield_until_matching_class(classes, needle):
class Failure():
def __init__(self, sig, clazz, detail, error, rule, msg):
+ self.clazz = clazz
self.sig = sig
self.error = error
self.rule = rule
@@ -2126,6 +2127,15 @@ def verify_compat(cur, prev):
return failures
+def match_filter(filters, fullname):
+ for f in filters:
+ if fullname == f:
+ return True
+ if fullname.startswith(f + '.'):
+ return True
+ return False
+
+
def show_deprecations_at_birth(cur, prev):
"""Show API deprecations at birth."""
global failures
@@ -2199,12 +2209,9 @@ def show_stats(cur, prev):
print " ", "".join([ str(stats[k]).ljust(20) for k in sorted(stats.keys()) ])
-if __name__ == "__main__":
+def main():
parser = argparse.ArgumentParser(description="Enforces common Android public API design \
patterns. It ignores lint messages from a previous API level, if provided.")
- parser.add_argument("current.txt", type=argparse.FileType('r'), help="current.txt")
- parser.add_argument("previous.txt", nargs='?', type=argparse.FileType('r'), default=None,
- help="previous.txt")
parser.add_argument("--base-current", nargs='?', type=argparse.FileType('r'), default=None,
help="The base current.txt to use when examining system-current.txt or"
" test-current.txt")
@@ -2213,6 +2220,8 @@ if __name__ == "__main__":
" test-previous.txt")
parser.add_argument("--no-color", action='store_const', const=True,
help="Disable terminal colors")
+ parser.add_argument("--color", action='store_const', const=True,
+ help="Use terminal colors")
parser.add_argument("--allow-google", action='store_const', const=True,
help="Allow references to Google")
parser.add_argument("--show-noticed", action='store_const', const=True,
@@ -2221,10 +2230,21 @@ if __name__ == "__main__":
help="Show API deprecations at birth")
parser.add_argument("--show-stats", action='store_const', const=True,
help="Show API stats")
+ parser.add_argument("--title", action='store', default=None,
+ help="Title to put in for display purposes")
+ parser.add_argument("--filter", action="append",
+ help="If provided, only show lint for the given packages or classes.")
+ parser.add_argument("current.txt", type=argparse.FileType('r'), help="current.txt")
+ parser.add_argument("previous.txt", nargs='?', type=argparse.FileType('r'), default=None,
+ help="previous.txt")
args = vars(parser.parse_args())
if args['no_color']:
USE_COLOR = False
+ elif args['color']:
+ USE_COLOR = True
+ else:
+ USE_COLOR = sys.stdout.isatty()
if args['allow_google']:
ALLOW_GOOGLE = True
@@ -2233,6 +2253,12 @@ if __name__ == "__main__":
base_current_file = args['base_current']
previous_file = args['previous.txt']
base_previous_file = args['base_previous']
+ filters = args['filter']
+ if not filters:
+ filters = []
+ title = args['title']
+ if not title:
+ title = current_file.name
if args['show_deprecations_at_birth']:
with current_file as f:
@@ -2290,6 +2316,11 @@ if __name__ == "__main__":
print
"""
+ # ignore everything but the given filters, if provided
+ if filters:
+ cur_fail = dict([(key, failure) for key, failure in cur_fail.iteritems()
+ if match_filter(filters, failure.clazz.fullname)])
+
if args['show_noticed'] and len(cur_noticed) != 0:
print "%s API changes noticed %s\n" % ((format(fg=WHITE, bg=BLUE, bold=True), format(reset=True)))
for f in sorted(cur_noticed.keys()):
@@ -2297,8 +2328,20 @@ if __name__ == "__main__":
print
if len(cur_fail) != 0:
- print "%s API style issues %s\n" % ((format(fg=WHITE, bg=BLUE, bold=True), format(reset=True)))
+ print "%s API style issues: %s %s" % ((format(fg=WHITE, bg=BLUE, bold=True),
+ title, format(reset=True)))
+ for f in filters:
+ print "%s filter: %s %s" % ((format(fg=WHITE, bg=BLUE, bold=True),
+ f, format(reset=True)))
+ print
for f in sorted(cur_fail):
print cur_fail[f]
print
+ print "%d errors" % len(cur_fail)
sys.exit(77)
+
+if __name__ == "__main__":
+ try:
+ main()
+ except KeyboardInterrupt:
+ sys.exit(1)
diff --git a/tools/apilint/apilint_test.py b/tools/apilint/apilint_test.py
index 5cb43db0b00d..811cb9aa23d5 100644
--- a/tools/apilint/apilint_test.py
+++ b/tools/apilint/apilint_test.py
@@ -392,5 +392,23 @@ class PackageTests(unittest.TestCase):
p = self._package("package @Rt(a.b.L_G_P) @RestrictTo(a.b.C) an.pref.int {")
self.assertEquals('an.pref.int', p.name)
+class FilterTests(unittest.TestCase):
+ def test_filter_match_prefix(self):
+ self.assertTrue(apilint.match_filter(["a"], "a.B"))
+ self.assertTrue(apilint.match_filter(["a.B"], "a.B.C"))
+
+ def test_filter_dont_match_prefix(self):
+ self.assertFalse(apilint.match_filter(["c"], "a.B"))
+ self.assertFalse(apilint.match_filter(["a."], "a.B"))
+ self.assertFalse(apilint.match_filter(["a.B."], "a.B.C"))
+
+ def test_filter_match_exact(self):
+ self.assertTrue(apilint.match_filter(["a.B"], "a.B"))
+
+ def test_filter_dont_match_exact(self):
+ self.assertFalse(apilint.match_filter([""], "a.B"))
+ self.assertFalse(apilint.match_filter(["a.C"], "a.B"))
+ self.assertFalse(apilint.match_filter(["a.C"], "a.B"))
+
if __name__ == "__main__":
unittest.main()