Ekran Ostatnie, nazywany również ekranem Przegląd, lista ostatnich zadań lub ekran ostatnio używanych aplikacji, to interfejs systemowy z listą ostatnio używanych aktywności i zadań. Użytkownik może poruszać się po liście, wybrać zadanie do wznowienia lub usunąć je z listy, przesuwając je poza ekran.
Ekran Ostatnie korzysta z modelu opartego na dokumentach wprowadzonego w Androidzie 5.0 (poziom interfejsu API 21). W jego przypadku wiele wystąpień tej samej aktywności obejmującej różne dokumenty może być wyświetlanych jako zadania na ekranie Ostatnie. Na przykład na Dysku Google może być zadanie dla każdego z kilku dokumentów Google. Każdy dokument jest wyświetlany jako zadanie na ekranie Ostatnie:
Innym typowym przykładem jest sytuacja, w której użytkownik korzysta z przeglądarki i klika Udostępnij > Gmail. Pojawi się ekran Utwórz w aplikacji Gmail. Kiedy klikniesz wtedy przycisk Ostatnie, Chrome i Gmail będą działać jako osobne zadania:
Zwykle system określa sposób wyświetlania zadań i działań na ekranie Ostatnie. Nie musicie niczego zmieniać. Aplikacja może jednak określić, jak i kiedy aktywność ma się pojawiać na ekranie Ostatnie.
Klasa ActivityManager.AppTask
pozwala zarządzać zadaniami, a flagi aktywności klasy Intent
pozwalają określić, kiedy aktywność ma zostać dodana do ekranu Ostatnie lub z niej usunięta. Poza tym atrybuty <activity>
umożliwiają określenie działania w pliku manifestu.
Dodawanie zadań do ekranu Ostatnie
Użycie flag klasy Intent
do dodawania zadania daje większą kontrolę nad tym, kiedy i jak dokument jest otwierany i ponownie otwierany na ekranie Ostatnie. Gdy używasz atrybutów <activity>
, możesz wybrać, czy zawsze otwierać dokument w nowym zadaniu czy ponownie używać w nim istniejącego zadania.
Dodawanie zadania za pomocą flagi intencji
Gdy tworzysz nowy dokument powiązany z Twoją aktywnością, wywołujesz metodę startActivity()
i przekazujesz do niego intencję, która uruchamia działanie. Aby wstawić przerwę logiczną, dzięki której system będzie traktować Twoją aktywność jako nowe zadanie na ekranie Ostatnie, przekaż flagę FLAG_ACTIVITY_NEW_DOCUMENT
w metodzie addFlags()
elementu Intent
, który uruchamia aktywność.
Jeśli podczas tworzenia nowego dokumentu ustawisz flagę FLAG_ACTIVITY_MULTIPLE_TASK
, system zawsze utworzy nowe zadanie z aktywnością docelową jako główną. To ustawienie umożliwia otwieranie tego samego dokumentu w więcej niż jednym zadaniu. Poniższy kod pokazuje, jak robi to główna aktywność:
Kotlin
fun createNewDocument(view: View) { val newDocumentIntent = newDocumentIntent() if (useMultipleTasks) { newDocumentIntent.addFlags(Intent.FLAG_ACTIVITY_MULTIPLE_TASK) } startActivity(newDocumentIntent) } private fun newDocumentIntent(): Intent = Intent(this, NewDocumentActivity::class.java).apply { addFlags(Intent.FLAG_ACTIVITY_NEW_DOCUMENT or android.content.Intent.FLAG_ACTIVITY_RETAIN_IN_RECENTS) putExtra(KEY_EXTRA_NEW_DOCUMENT_COUNTER, documentCounter++) }
Java
public void createNewDocument(View view) { final Intent newDocumentIntent = newDocumentIntent(); if (useMultipleTasks) { newDocumentIntent.addFlags(Intent.FLAG_ACTIVITY_MULTIPLE_TASK); } startActivity(newDocumentIntent); } private Intent newDocumentIntent() { boolean useMultipleTasks = checkbox.isChecked(); final Intent newDocumentIntent = new Intent(this, NewDocumentActivity.class); newDocumentIntent.addFlags(Intent.FLAG_ACTIVITY_NEW_DOCUMENT); newDocumentIntent.putExtra(KEY_EXTRA_NEW_DOCUMENT_COUNTER, documentCounter++); return newDocumentIntent; } }
Gdy główne działanie uruchamia nowe działanie, system przeszukuje istniejące zadania w poszukiwaniu tego, którego intencja pasuje do nazwy komponentu intencji i danych dotyczących intencji. Jeśli zadanie nie zostanie znalezione lub intencja zawiera flagę FLAG_ACTIVITY_MULTIPLE_TASK
, zostanie utworzone nowe zadanie z aktywnością główną.
Jeśli system znajdzie zadanie, którego intencja jest zgodna z nazwą komponentu intencji i danymi intencji, wyświetli to zadanie na wierzchu i przekaże nową intencję do onNewIntent()
.
Nowa aktywność pobiera intencję i tworzy nowy dokument na ekranie Ostatnie, jak widać w tym przykładzie:
Kotlin
override fun onCreate(savedInstanceState: Bundle?) { super.onCreate(savedInstanceState) setContentView(R.layout.activity_new_document) documentCount = intent .getIntExtra(DocumentCentricActivity.KEY_EXTRA_NEW_DOCUMENT_COUNTER, 0) documentCounterTextView = findViewById(R.id.hello_new_document_text_view) setDocumentCounterText(R.string.hello_new_document_counter) } override fun onNewIntent(newIntent: Intent) { super.onNewIntent(newIntent) /* If FLAG_ACTIVITY_MULTIPLE_TASK has not been used, this Activity will be reused. */ setDocumentCounterText(R.string.reusing_document_counter) }
Java
@Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_new_document); documentCount = getIntent() .getIntExtra(DocumentCentricActivity.KEY_EXTRA_NEW_DOCUMENT_COUNTER, 0); documentCounterTextView = (TextView) findViewById( R.id.hello_new_document_text_view); setDocumentCounterText(R.string.hello_new_document_counter); } @Override protected void onNewIntent(Intent intent) { super.onNewIntent(intent); /* If FLAG_ACTIVITY_MULTIPLE_TASK has not been used, this activity is reused to create a new document. */ setDocumentCounterText(R.string.reusing_document_counter); }
Dodawanie zadania za pomocą atrybutu activity
Aktywność może też określać w swoim pliku manifestu, że zawsze jest uruchamiana jako nowe zadanie. W tym celu użyj atrybutu <activity>
android:documentLaunchMode
.
Ten atrybut ma 4 wartości, które dają następujące efekty, gdy użytkownik otworzy dokument w aplikacji:
intoExisting
- Aktywność spowoduje ponowne wykorzystanie istniejącego zadania w dokumencie. Przypomina to ustawienie flagi
FLAG_ACTIVITY_NEW_DOCUMENT
bez ustawienia flagiFLAG_ACTIVITY_MULTIPLE_TASK
zgodnie z opisem w sekcji Dodawanie zadania za pomocą flagi intencji. always
- Ta aktywność powoduje utworzenie nowego zadania w dokumencie, nawet jeśli dokument jest już otwarty. Użycie tej wartości jest równoznaczne z ustawieniem zarówno flagi
FLAG_ACTIVITY_NEW_DOCUMENT
, jak iFLAG_ACTIVITY_MULTIPLE_TASK
. none
- Aktywność nie utworzy nowego zadania w dokumencie. Ekran Ostatnie traktuje aktywność domyślnie tak, jak ma to miejsce. Wyświetla ono jedno zadanie w aplikacji, które jest wznawiane od aktywności wywołanej przez użytkownika jako ostatnie.
never
- Aktywność nie utworzy nowego zadania w dokumencie. Ustawienie tej wartości zastępuje działanie flag
FLAG_ACTIVITY_NEW_DOCUMENT
iFLAG_ACTIVITY_MULTIPLE_TASK
. Jeśli któreś z nich jest ustawione w intencji, a na ekranie Ostatnie pojawi się jedno zadanie dla aplikacji, zostanie ono wznowione na podstawie aktywności wywołanej ostatnio przez użytkownika.
Usuwanie zadań
Domyślnie zadanie związane z dokumentem jest automatycznie zamykane po zakończeniu jego działania na ekranie Ostatnie. Możesz zastąpić to zachowanie klasą ActivityManager.AppTask
, flagą Intent
lub atrybutem <activity>
.
Zawsze możesz całkowicie wykluczyć zadanie z ekranu Ostatnie, ustawiając atrybut <activity>
android:excludeFromRecents
na wartość true
.
Maksymalną liczbę zadań, które aplikacja może wykonywać na ekranie Ostatnie, możesz ustawić w atrybucie <activity>
android:maxRecents
na wartość całkowitą. Po osiągnięciu maksymalnej liczby zadań najczęściej używane zadanie znika z ekranu Ostatnie. Wartością domyślną jest 16, a maksymalna – 50 (25 w przypadku urządzeń z małą ilością pamięci). Wartości mniejsze niż 1 są nieprawidłowe.
Usuwanie zadań przy użyciu klasy AppTask
W działaniu, które tworzy nowe zadanie na ekranie Ostatnie, możesz określić, kiedy je usunąć i zakończyć wszystkie powiązane z nim działania, wywołując metodę finishAndRemoveTask()
:
Kotlin
fun onRemoveFromOverview(view: View) { // It is good pratice to remove a document from the overview stack if not needed anymore. finishAndRemoveTask() }
Java
public void onRemoveFromRecents(View view) { // The document is no longer needed; remove its task. finishAndRemoveTask(); }
Zachowaj ukończone zadania
Jeśli chcesz zachować zadanie na ekranie Ostatnie, nawet po zakończeniu aktywności tego zadania, przekaż flagę FLAG_ACTIVITY_RETAIN_IN_RECENTS
w metodzie addFlags()
intencji uruchamiającej działanie.
Kotlin
private fun newDocumentIntent() = Intent(this, NewDocumentActivity::class.java).apply { addFlags(Intent.FLAG_ACTIVITY_NEW_DOCUMENT or android.content.Intent.FLAG_ACTIVITY_RETAIN_IN_RECENTS) putExtra(KEY_EXTRA_NEW_DOCUMENT_COUNTER, getAndIncrement()) }
Java
private Intent newDocumentIntent() { final Intent newDocumentIntent = new Intent(this, NewDocumentActivity.class); newDocumentIntent.addFlags(Intent.FLAG_ACTIVITY_NEW_DOCUMENT | android.content.Intent.FLAG_ACTIVITY_RETAIN_IN_RECENTS); newDocumentIntent.putExtra(KEY_EXTRA_NEW_DOCUMENT_COUNTER, getAndIncrement()); return newDocumentIntent; }
Aby uzyskać ten sam efekt, ustaw wartość atrybutu <activity>
android:autoRemoveFromRecents
na false
. Wartość domyślna to true
w przypadku działań związanych z dokumentami i false
dla standardowych działań. Użycie tego atrybutu zastępuje flagę FLAG_ACTIVITY_RETAIN_IN_RECENTS
.
Włączanie udostępniania ostatnich adresów URL (tylko Pixel)
Na urządzeniach Pixel z Androidem 12 lub nowszym użytkownicy mogą udostępniać linki do ostatnio oglądanych treści internetowych bezpośrednio na ekranie Ostatnie. Po otwarciu treści w aplikacji użytkownik może otworzyć ekran Ostatnie i znaleźć aplikację, w której oglądał treści, a następnie kliknąć przycisk linku, aby skopiować lub udostępnić URL.
Każda aplikacja może włączyć dla użytkowników łączenie z ostatnimi usługami przez udostępnienie interfejsu internetowego i zastąpienie wartości onProvideAssistContent()
, jak w tym przykładzie:
Kotlin
class MainActivity : AppCompatActivity() { protected fun onCreate(savedInstanceState: Bundle?) { super.onCreate(savedInstanceState) setContentView(R.layout.activity_main) } fun onProvideAssistContent(outContent: AssistContent) { super.onProvideAssistContent(outContent) outContent.setWebUri(Uri.parse("https://example.com/myCurrentPage")) } }
Java
public class MainActivity extends AppCompatActivity { @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); } @Override public void onProvideAssistContent(AssistContent outContent) { super.onProvideAssistContent(outContent); outContent.setWebUri(Uri.parse("https://example.com/myCurrentPage")); } }