Wie erstelle ich ein Hilfe-Overlay, wie Sie es in einigen Android-Apps und ICS sehen?

93

Ich möchte Hilfe-Overlays erstellen, wie sie beim ersten Laden von ICS oder in Apps wie ES File Explorer oder Apex Launcher angezeigt werden (es gibt noch mehr, aber ich kann mir diese derzeit nicht vorstellen). Ist dies nur ein relatives Layout, bei dem eine Ansicht über der anderen sitzt? Ich konnte keinen Beispielcode dafür finden. Weiß jemand, wie das gemacht wird oder hat er irgendwelche Ideen?

ES File Explorer ES File Explorer

ssuperz28
quelle

Antworten:

84

Nehmen wir an, Sie würden normalerweise anrufen setContentView(R.layout.main), aber beim ersten Start möchten Sie diese Überlagerung haben.

Schritt 1: Erstellen Sie einen FrameLayoutJava-Code und übergeben Sie diesen an setContentView().

Schritt 2: LayoutInflaterZum Aufblasen R.layout.mainin die FrameLayout.

Schritt 3: LayoutInflaterZum Aufblasen des Overlays in das FrameLayout.

Schritt 4: Wenn der Benutzer auf die Schaltfläche (oder was auch immer) tippt, um das Overlay zu schließen, rufen Sie removeView()an, um das Overlay aus dem zu entfernen FrameLayout.

Da das Overlay ein späteres Kind von ist FrameLayout, wird es über den Inhalt von schweben R.layout.main.

CommonsWare
quelle
6
@ ssuperz28: Ja, bis auf die handgezeichneten Pfeilspitzen und die Blase. Dafür bist du allein. :-)
CommonsWare
Ich weiß nicht, ob Sie es geschafft haben, das zu tun, was Sie wollten, aber hier ist eine andere Alternative. stackoverflow.com/questions/8841240/… Wenn Sie die von CommonsWare angegebene Lösung beibehalten, ist das einzige, was mir beim Festlegen der Pfeile einfällt, das FrameLayout von Anweisungen mit einem resourceImage oder backgroundImage zu definieren, das bereits das Bild mit den Pfeilen enthält (und Transparenz).
Edison Santos
1
Gibt es eine Möglichkeit, dies zu tun, aber dies in Bezug auf die Position der Kinder, die sich unterhalb des FrameLayout befinden?
4gus71n
@ CommonsWare - Sir, das würde funktionieren, unabhängig davon, um welches Gerät es sich handelt.
Rat-a-tat-a-tat Ratatouille
2
@ user3364963: Passen Sie die Positionen der Dinge dynamisch an. Meine Antwort war etwas vereinfacht. Ich gehe davon aus, dass sie die Position der hervorzuhebenden Elemente bestimmen und die Koordinaten der "Trainermarken" anpassen. Ein Brauch ViewGroupfür die Ebene "Coach Marks" könnte damit umgehen, und es gibt Bibliotheken (z. B. ShowcaseView), die vordefinierte Implementierungen dieses Musters anbieten.
CommonsWare
80

"Coach Mark" ist "Help Overlay" in UX Talk :-)

coach_mark.xml ist Ihr Coach- Markenlayout

coach_mark_master_view ist die ID der obersten Ansicht (root) in coach_mark.xml

public void onCoachMark(){

    final Dialog dialog = new Dialog(this);
    dialog.requestWindowFeature(Window.FEATURE_NO_TITLE);
    dialog.getWindow().setBackgroundDrawable(new ColorDrawable(android.graphics.Color.TRANSPARENT));
    dialog.setContentView(R.layout.coach_mark);
    dialog.setCanceledOnTouchOutside(true);
    //for dismissing anywhere you touch
    View masterView = dialog.findViewById(R.id.coach_mark_master_view);
    masterView.setOnClickListener(new View.OnClickListener() {
        @Override
        public void onClick(View view) {
            dialog.dismiss();
        }
    });
    dialog.show();
}

Hinzufügen eines Beispiels von coach_mark.xml (zu dieser hervorragenden Lösung von Oded Breiner), damit ppl es einfach kopieren und einfügen kann, um schnell ein funktionierendes Beispiel zu sehen.

Beispiel für coach_mark.xml hier, ändern Sie die -> drawable / coach_marks in Ihr Bild:

coach_mark.xml

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical"
    android:id="@+id/coach_mark_master_view">
    <RelativeLayout
        android:layout_width="match_parent"
        android:layout_height="match_parent" >
         <ImageView
             android:id="@+id/coach_marks_image"
             android:layout_width="match_parent"
             android:layout_height="match_parent"
             android:layout_centerInParent="true"
             android:layout_gravity="center_horizontal"
             android:src="@drawable/coach_marks" />
    </RelativeLayout>
</LinearLayout>

Verwenden Sie dieses Thema optional, um Polster zu entfernen:

<style name="WalkthroughTheme" parent="Theme.AppCompat">
    <item name="android:windowIsTranslucent">true</item>
    <item name="android:windowBackground">@android:color/transparent</item>
    <item name="android:windowContentOverlay">@null</item>
    <item name="android:windowNoTitle">true</item>
    <item name="android:backgroundDimEnabled">false</item>
</style>
Oded Breiner
quelle
Hallo, wie können Sie diesen Dialog so erweitern, dass er zum Bildschirm passt? Aus der Dokumentation , A dialog is a small window that prompts [...]. A dialog does not fill the screen and is normally used for modal events [...].. Wenn ich diesen Code verwende, wird meine Hauptansicht in einem kleinen Teil des Bildschirms komprimiert. Wenn ich setze android:layout_width="640dp" android:layout_height="480dp"(dh die tatsächlichen Werte des Bildschirms, mit dem ich teste), funktioniert es korrekt. (Natürlich ist dies keine praktikable Lösung)
Ocramot
@ocramot: das obige Beispiel sollte wegen match_parent und Window im Vollbildmodus sein. FEATURE_NO_TITLE
Oded Breiner
Dann muss es ein anderes Problem geben, weil ich es anders
sehe
1
Ich weiß, dass dies mindestens ein paar Monate alt ist, aber wurde diese Vollbildfrage jemals herausgefunden?
cbhedd
3
Für diejenigen, die nicht wissen, wie man das Thema des Dialogs new Dialog(getContext(), R.style.WalkthroughTheme);
festlegt
4

Sie können das ziemlich schnell tun. Sie fügen beispielsweise ein LinearLayout hinzu, in dem Sie ein Bild mit Alpha einfügen, das Ihren Hilfeinformationen entspricht und das Sie wie eine Überlagerung zeichnen möchten. In Ihrer XML-Datei Ihrer Aktivität platzieren Sie dieses Layout in einem RelativeLayout nach dem Layout Ihrer Aktivität mit der Gone-Sichtbarkeit. Wenn Sie die Hilfeinformationen zeichnen möchten, müssen Sie diese Sichtbarkeit nur auf sichtbar setzen.

Ich hoffe, ich bin klar, wenn Sie Fragen haben, bin ich bitte, sie zu beantworten.

FUBUs
quelle
Danke für deinen Beitrag. So habe ich mir das vorgestellt. Ich muss die Antwort unten jedoch würdigen, da ich sie so bauen werde. Es scheint überschaubarer zu sein und ich muss mein Hauptaktivitätslayout nicht ändern.
ssuperz28
1

Sehen Sie sich meine andere Antwort an, wie programmgesteuert ein Overlay-Layout über der aktuellen Aktivität angezeigt wird. Die layout.xml von Activity muss nichts über die Overlay-Skin wissen. Sie können eine halbtransparente Überlagerung einfügen, nur einen Teil des Bildschirms abdecken, eine oder mehrere Textansichten und Schaltflächen darauf ... Wie kann eine Schaltfläche programmgesteuert überlagert werden?

  • Erstellen Sie die RelativeLayout-Vorlage res / layout / paused.xml oder verwenden Sie eine beliebige Layout-Toplevel
  • Erstellen Sie eine Funktion zum Anzeigen der Überlagerungshaut
  • Der Schlüssel ist, das Handle auf layout.xml zu übertragen, die LayoutInflater-Klasse zu verwenden, um xml zu analysieren, um Objekte anzuzeigen, und der aktuellen Layoutstruktur eine Overlay-Ansicht hinzuzufügen
  • In meinem Beispiel wird ein Timer verwendet, um das Overlay-Objekt zu zerstören, indem es vollständig aus der Ansichtsstruktur entfernt wird. Dies ist wahrscheinlich auch das, was Sie wollen, um es spurlos loszuwerden.

Mein Ziel war es, dass die Hauptaktivitäten keine Overlay-Skins kennen, Overlays kommen und gehen, viele verschiedene Overlays, weiterhin Overlay1.xml-Textdateien als Vorlage verwenden können und der Inhalt programmgesteuert aktualisiert werden sollte. Ich mache so ziemlich das, was CommonsWare uns gesagt hat. Mein Beitrag zeigt den tatsächlichen Programmcode, um loszulegen.

Haftungsausschluss: OPs "Vielen Dank für Ihre Eingabe. So habe ich mir das vorgestellt. Ich muss die Antwort unten würdigen." Kommentar bedeutet nicht meine Antwort, sondern CommonsWare-Antwort. Stackoverflow hat Nachbestellungen geändert.

Wen
quelle