Mit der MediaPipe Image Generator-Aufgabe können Sie Bilder auf Grundlage eines Text-Prompts generieren. Bei dieser Aufgabe wird ein Text-zu-Bild-Modell verwendet, um Bilder mithilfe von Diffusionstechniken zu generieren.
Die Aufgabe akzeptiert einen Text-Prompt als Eingabe sowie ein optionales Bedingungsbild, das das Modell erweitern und als Referenz für die Generierung verwenden kann. Image Generator kann auch Bilder auf Grundlage bestimmter Konzepte generieren, die dem Modell während des Trainings oder des erneuten Trainings zur Verfügung gestellt wurden. Weitere Informationen finden Sie unter Mit LoRA anpassen.
Der in dieser Anleitung beschriebene Beispielcode ist auf GitHub verfügbar. Weitere Informationen zu den Funktionen, Modellen und Konfigurationsoptionen dieser Aufgabe finden Sie in der Übersicht.
Codebeispiel
Der Beispielcode für MediaPipe Tasks ist eine einfache Implementierung einer Image Generator-App für Android. Sie können die App als Ausgangspunkt für Ihre eigene Android App verwenden oder sie als Referenz nutzen, wenn Sie eine vorhandene App ändern. Der Beispiel Code für Image Generator wird auf GitHub gehostet.
Code herunterladen
In der folgenden Anleitung wird beschrieben, wie Sie mit dem Befehlszeilentool „git“ eine lokale Kopie des Beispiel codes erstellen.
So laden Sie den Beispielcode herunter:
- Klonen Sie das Git-Repository mit dem folgenden Befehl:
git clone https://github.com/google-ai-edge/mediapipe-samples
- Optional können Sie Ihre Git-Instanz so konfigurieren, dass sie Sparse Checkout verwendet, damit Sie nur die Dateien für die Image Generator-Beispiel-App haben:
cd mediapipe-samples git sparse-checkout init --cone git sparse-checkout set examples/image_generation/android
Nachdem Sie eine lokale Version des Beispielcodes erstellt haben, können Sie das Projekt in Android Studio importieren und die App ausführen. Eine Anleitung finden Sie im Einrichtungsleitfaden für Android.
Schlüsselkomponenten
Die folgenden Dateien enthalten den entscheidenden Code für diese Beispielanwendung zur Bildgenerierung:
- ImageGenerationHelper.kt: Initialisiert die Aufgabe und verarbeitet die Bildgenerierung.
- DiffusionActivity.kt: Generiert Bilder, wenn Plug‑ins oder LoRA-Gewichtungen nicht aktiviert sind.
- PluginActivity.kt: Implementiert die Plug‑in-Modelle, mit denen Nutzer ein Bedingungs bild als Eingabe bereitstellen können.
- LoRAWeightActivity.kt: Greift auf die LoRA-Gewichtungen zu und verarbeitet sie. Diese werden verwendet, um Basismodelle anzupassen und Bilder bestimmter Konzepte zu generieren.
Einrichtung
In diesem Abschnitt werden die wichtigsten Schritte zum Einrichten Ihrer Entwicklungsumgebung und Ihrer Codeprojekte speziell für die Verwendung von Image Generator beschrieben. Allgemeine Informationen zum Einrichten Ihrer Entwicklungsumgebung für die Verwendung von MediaPipe-Aufgaben, einschließlich der Anforderungen an die Plattformversion, finden Sie im Einrichtungsleitfaden für Android.
Abhängigkeiten
Für die Image Generator-Aufgabe wird die Bibliothek com.google.mediapipe:tasks-vision-image-generator verwendet. Fügen Sie diese Abhängigkeit der Datei build.gradle in Ihrer Android-App hinzu:
dependencies {
implementation 'com.google.mediapipe:tasks-vision-image-generator:latest.release'
}
Fügen Sie für Geräte mit Android 12 (API 31) oder höher die Abhängigkeit der nativen OpenCL-Bibliothek hinzu. Weitere Informationen finden Sie in der Dokumentation zum
uses-native-library
Tag.
Fügen Sie der Datei AndroidManifest.xml die folgenden uses-native-library-Tags hinzu:
<uses-native-library android:name="libOpenCL.so" android:required="false" />
<uses-native-library android:name="libOpenCL-car.so" android:required="false"/>
<uses-native-library android:name="libOpenCL-pixel.so" android:required="false" />
Modell
Für die MediaPipe Image Generator-Aufgabe ist ein trainiertes Basismodell erforderlich, das mit dieser Aufgabe kompatibel ist. Nachdem Sie ein Modell heruntergeladen haben, installieren Sie die erforderlichen Abhängigkeiten und konvertieren Sie das Modell in ein geeignetes Format. Übertragen Sie das konvertierte Modell dann auf das Android-Gerät.
Weitere Informationen zu den verfügbaren trainierten Modellen für Image Generator finden Sie im Abschnitt Modelle in der Aufgaben übersicht.
Basismodell herunterladen
Für Image Generator muss das Basismodell dem
stable-diffusion-v1-5/stable-diffusion-v1-5 EMA-only Modellformat entsprechen, das auf dem folgenden
Modell basiert:
stable-diffusion-v1-5/stable-diffusion-v1-5 EMA-only.
Abhängigkeiten installieren und Modell konvertieren
$ pip install torch typing_extensions numpy Pillow requests pytorch_lightning absl-py
Führen Sie das
convert.py
Skript aus:
$ python3 convert.py --ckpt_path <ckpt_path> --output_path <output_path>
Konvertiertes Modell auf das Gerät übertragen
Übertragen Sie den Inhalt des Ordners <output_path> auf das Android-Gerät.
$ adb shell rm -r /data/local/tmp/image_generator/ # Remove any previously loaded weights
$ adb shell mkdir -p /data/local/tmp/image_generator/
$ adb push <output_path>/. /data/local/tmp/image_generator/bins
Plug‑in-Modelle herunterladen und LoRA-Gewichtungen hinzufügen (optional)
Wenn Sie ein Plug‑in-Modell verwenden möchten, prüfen Sie, ob das Modell heruntergeladen werden muss. Für Plug‑ins, die ein zusätzliches Modell erfordern, müssen die Plug‑in-Modelle entweder im APK gebündelt oder bei Bedarf heruntergeladen werden. Plug‑in-Modelle sind ressourcenarm (~23 MB) und können direkt im APK gebündelt werden. Wir empfehlen jedoch, Plug‑in-Modelle bei Bedarf herunterzuladen.
Wenn Sie ein Modell mit LoRA angepasst haben, laden Sie es bei Bedarf herunter. Weitere Informationen finden Sie unter Plug‑in-Modell für LoRA-Gewichtungen.
Aufgabe erstellen
Für die MediaPipe Image Generator-Aufgabe wird die Funktion createFromOptions() verwendet, um die Aufgabe einzurichten. Die Funktion createFromOptions() akzeptiert Werte für die Konfigurationsoptionen. Weitere Informationen zu den Konfigurationsoptionen finden Sie unter Konfigurations
optionen.
Konfigurationsoptionen
Für diese Aufgabe sind die folgenden Konfigurationsoptionen für Android-Apps verfügbar:
| Option | Beschreibung | Wertebereich |
|---|---|---|
imageGeneratorModelDirectory |
Das Verzeichnis des Image Generator-Modells, in dem die Modellgewichtungen gespeichert sind. | PATH |
loraWeightsFilePath |
Legt den Pfad zur Datei mit den LoRA-Gewichtungen fest. Optional und nur anwendbar, wenn das Modell mit LoRA angepasst wurde. | PATH |
errorListener |
Legt einen optionalen Fehlerlistener fest. | N/A |
Die Aufgabe unterstützt auch Plug‑in-Modelle, mit denen Nutzer Bedingungsbilder in die Aufgabeneingabe einbeziehen können. Das Basismodell kann diese erweitern und als Referenz für die Generierung verwenden. Diese Bedingungsbilder können Gesichts-Landmarks, Kantenumrisse und Tiefenschätzungen sein, die das Modell als zusätzlichen Kontext und Informationen zum Generieren von Bildern verwendet.
Wenn Sie dem Basismodell ein Plug‑in-Modell hinzufügen, konfigurieren Sie auch die Plug‑in-Optionen. Das Plug‑in für Gesichts-Landmarks verwendet faceConditionOptions, das Plug‑in für Canny-Kanten edgeConditionOptions und das Plug‑in für die Tiefe depthConditionOptions.
Optionen für Canny-Kanten
Konfigurieren Sie die folgenden Optionen in edgeConditionOptions.
| Option | Beschreibung | Wertebereich | Standardwert |
|---|---|---|---|
threshold1 |
Erster Schwellenwert für das Hystereseverfahren. | Float |
100 |
threshold2 |
Zweiter Schwellenwert für das Hystereseverfahren. | Float |
200 |
apertureSize |
Blendenöffnung für den Sobel-Operator. Der typische Bereich liegt zwischen 3 und 7. | Integer |
3 |
l2Gradient |
Gibt an, ob die L2-Norm zur Berechnung der Bildgradientengröße anstelle der Standard-L1-Norm verwendet wird. | BOOLEAN |
False |
EdgePluginModelBaseOptions |
Das -Objekt, das den Pfad
für das Plug‑in-Modell festlegt.BaseOptions |
BaseOptions-Objekt |
N/A |
Weitere Informationen zur Funktionsweise dieser Konfigurationsoptionen finden Sie unter Canny-Kantendetektor.
Optionen für Gesichts-Landmarks
Konfigurieren Sie die folgenden Optionen in faceConditionOptions.
| Option | Beschreibung | Wertebereich | Standardwert |
|---|---|---|---|
minFaceDetectionConfidence |
Der Mindestkonfidenzwert für die Gesichtserkennung, damit sie als erfolgreich gilt. | Float [0.0,1.0] |
0.5 |
minFacePresenceConfidence |
Der Mindestkonfidenzwert für die Gesichtserkennung bei der Erkennung von Gesichts-Landmarks. | Float [0.0,1.0] |
0.5 |
faceModelBaseOptions |
Das -Objekt, das den Pfad
für das Modell festlegt, mit dem das Bedingungsbild erstellt wird.BaseOptions |
BaseOptions-Objekt |
N/A |
FacePluginModelBaseOptions |
Das -Objekt, das den Pfad
für das Plug‑in-Modell festlegt.BaseOptions |
BaseOptions-Objekt |
N/A |
Weitere Informationen zur Funktionsweise dieser Konfigurationsoptionen finden Sie unter der Face Landmarker-Aufgabe.
Optionen für die Tiefe
Konfigurieren Sie die folgenden Optionen in depthConditionOptions.
| Option | Beschreibung | Wertebereich | Standardwert |
|---|---|---|---|
depthModelBaseOptions |
Das -Objekt, das den Pfad
für das Modell festlegt, mit dem das Bedingungsbild erstellt wird.BaseOptions |
BaseOptions-Objekt |
N/A |
depthPluginModelBaseOptions |
Das -Objekt, das den Pfad
für das Plug‑in-Modell festlegt.BaseOptions |
BaseOptions-Objekt |
N/A |
Nur mit dem Basismodell erstellen
val options = ImageGeneratorOptions.builder()
.setImageGeneratorModelDirectory(modelPath)
.build()
imageGenerator = ImageGenerator.createFromOptions(context, options)
Mit Plug‑ins erstellen
Wenn Sie ein optionales Plug‑in-Modell anwenden, legen Sie die Basisoptionen für das Plug‑in-Modell mit setPluginModelBaseOptions fest. Wenn für das Plug‑in-Modell ein zusätzliches heruntergeladenes Modell erforderlich ist, um das Bedingungsbild zu erstellen, geben Sie den Pfad in BaseOptions an.
Gesichts-Landmarks
val options = ImageGeneratorOptions.builder()
.setImageGeneratorModelDirectory(modelPath)
.build()
val faceModelBaseOptions = BaseOptions.builder()
.setModelAssetPath("face_landmarker.task")
.build()
val facePluginModelBaseOptions = BaseOptions.builder()
.setModelAssetPath("face_landmark_plugin.tflite")
.build()
val faceConditionOptions = FaceConditionOptions.builder()
.setFaceModelBaseOptions(faceModelBaseOptions)
.setPluginModelBaseOptions(facePluginModelBaseOptions)
.setMinFaceDetectionConfidence(0.3f)
.setMinFacePresenceConfidence(0.3f)
.build()
val conditionOptions = ConditionOptions.builder()
.setFaceConditionOptions(faceConditionOptions)
.build()
imageGenerator =
ImageGenerator.createFromOptions(context, options, conditionOptions)
Canny-Kanten
val options = ImageGeneratorOptions.builder()
.setImageGeneratorModelDirectory(modelPath)
.build()
val edgePluginModelBaseOptions = BaseOptions.builder()
.setModelAssetPath("canny_edge_plugin.tflite")
.build()
val edgeConditionOptions = EdgeConditionOptions.builder()
.setThreshold1(100.0f)
.setThreshold2(100.0f)
.setApertureSize(3)
.setL2Gradient(false)
.setPluginModelBaseOptions(edgePluginModelBaseOptions)
.build()
val conditionOptions = ConditionOptions.builder()
.setEdgeConditionOptions(edgeConditionOptions)
.build()
imageGenerator =
ImageGenerator.createFromOptions(context, options, conditionOptions)
Tiefe
val options = ImageGeneratorOptions.builder()
.setImageGeneratorModelDirectory(modelPath)
.build()
val depthModelBaseOptions = BaseOptions.builder()
.setModelAssetPath("depth_model.tflite")
.build()
val depthPluginModelBaseOptions = BaseOptions.builder()
.setModelAssetPath("depth_plugin.tflite")
.build()
val depthConditionOptions =
ConditionOptions.DepthConditionOptions.builder()
.setDepthModelBaseOptions(depthModelBaseOptions)
.setPluginModelBaseOptions(depthPluginModelBaseOptions)
.build()
val conditionOptions = ConditionOptions.builder()
.setDepthConditionOptions(depthConditionOptions)
.build()
imageGenerator =
ImageGenerator.createFromOptions(context, options, conditionOptions)
Mit LoRA-Gewichtungen erstellen
Wenn Sie LoRA-Gewichtungen einbeziehen, verwenden Sie den Parameter loraWeightsFilePath, um auf den Pfad zu verweisen.
val options = ImageGeneratorOptions.builder()
.setLoraWeightsFilePath(weightsPath)
.setImageGeneratorModelDirectory(modelPath)
.build()
imageGenerator = ImageGenerator.createFromOptions(context, options)
Daten vorbereiten
Image Generator akzeptiert die folgenden Eingaben:
- prompt (erforderlich): Der Text-Prompt, der das zu generierende Bild beschreibt.
- iterations (erforderlich): Die Gesamtzahl der Iterationen zum Generieren des Bildes. Ein guter Ausgangspunkt sind 20.
- seed (erforderlich): Der Zufalls-Seed, der bei der Bildgenerierung verwendet wird.
- condition image (optional): Das Bild, das das Modell als Referenz für die Generierung verwendet. Nur anwendbar, wenn ein Plug‑in-Modell verwendet wird.
- condition type (optional): Der Typ des Plug‑in-Modells, das mit der Aufgabe verwendet wird. Nur anwendbar, wenn ein Plug‑in-Modell verwendet wird.
Eingaben nur mit dem Basismodell
fun setInput(prompt: String, iteration: Int, seed: Int) {
imageGenerator.setInputs(prompt, iteration, seed)
}
Eingaben mit Plug‑ins
Wenn Sie ein optionales Plug‑in-Modell anwenden, verwenden Sie auch den Parameter conditionType, um das Plug‑in-Modell auszuwählen, und den Parameter sourceConditionImage, um das Bedingungsbild zu generieren.
| Option | Beschreibung | Wert |
|---|---|---|
conditionType |
Das Plug‑in-Modell, das auf das Basismodell angewendet wird. | {"FACE", "EDGE", "DEPTH"} |
sourceConditionImage |
Das Quellbild, das zum Erstellen des Bedingungsbildes verwendet wird. | MPImage-Objekt |
Wenn Sie ein Plug‑in-Modell verwenden, erstellen Sie das Bedingungsbild mit createConditionImage:
fun createConditionImage(
inputImage: MPImage,
conditionType: ConditionType
): Bitmap {
val result =
imageGenerator.createConditionImage(inputImage, conditionType)
return BitmapExtractor.extract(result)
}
Nachdem Sie das Bedingungsbild erstellt haben, fügen Sie es zusammen mit dem Prompt, dem Seed und der Anzahl der Iterationen als Eingabe hinzu.
imageGenerator.setInputs(
prompt,
conditionalImage,
conditionType,
iteration,
seed
)
Eingaben mit LoRA-Gewichtungen
Wenn Sie LoRA-Gewichtungen verwenden, muss das Token im Text-Prompt enthalten sein, wenn Sie ein Bild mit dem spezifischen Konzept generieren möchten, das durch die Gewichtungen dargestellt wird.
fun setInput(prompt: String, iteration: Int, seed: Int) {
imageGenerator.setInputs(prompt, iteration, seed)
}
Aufgabe ausführen
Verwenden Sie die Methode generate(), um ein Bild mit den im vorherigen Abschnitt angegebenen Eingaben zu generieren. So wird ein einzelnes generiertes Bild erstellt.
Nur mit dem Basismodell erstellen
fun generate(prompt: String, iteration: Int, seed: Int): Bitmap {
val result = imageGenerator.generate(prompt, iteration, seed)
val bitmap = BitmapExtractor.extract(result?.generatedImage())
return bitmap
}
Mit Plug‑ins erstellen
fun generate(
prompt: String,
inputImage: MPImage,
conditionType: ConditionType,
iteration: Int,
seed: Int
): Bitmap {
val result = imageGenerator.generate(
prompt,
inputImage,
conditionType,
iteration,
seed
)
val bitmap = BitmapExtractor.extract(result?.generatedImage())
return bitmap
}
Mit LoRA-Gewichtungen erstellen
Der Prozess zum Generieren von Bildern mit einem Modell, das mit LoRA-Gewichtungen angepasst wurde, ähnelt dem Prozess mit einem Standard-Basismodell. Achten Sie darauf, dass das Token im Prompt enthalten ist, und führen Sie denselben Code aus.
fun generate(prompt: String, iteration: Int, seed: Int): Bitmap {
val result = imageGenerator.generate(prompt, iteration, seed)
val bitmap = BitmapExtractor.extract(result?.generatedImage())
return bitmap
}
Iterative Generierung
Image Generator kann auch die generierten Zwischenbilder während jeder Iteration ausgeben, wie im Eingabeparameter iterations definiert. Rufen Sie die Methode setInputs auf, um diese Zwischenergebnisse anzuzeigen, und rufen Sie dann execute() auf, um jeden Schritt auszuführen. Setzen Sie den Parameter showResult auf true, um die Zwischenergebnisse anzuzeigen.
fun execute(showResult: Boolean): Bitmap {
val result = imageGenerator.execute(showResult)
val bitmap =
BitmapExtractor.extract(result.generatedImage())
return bitmap
}
Ergebnisse verarbeiten und anzeigen
Image Generator gibt ein ImageGeneratorResult zurück, das das generierte Bild, einen Zeitstempel des Abschlusszeitpunkts und das Bedingungsbild enthält, falls eines als Eingabe bereitgestellt wurde.
val bitmap = BitmapExtractor.extract(result.generatedImage())
Das folgende Bild wurde aus den folgenden Eingaben generiert, wobei nur ein Basismodell verwendet wurde.
Eingaben :
- Prompt: „Ein bunter Cartoon-Waschbär mit einem schlaffen Hut mit breiter Krempe der mit einem Stock durch den Wald geht, animiert, Dreiviertelansicht, Gemälde“
- Seed: 312687592
- Iterations: 20
Generiertes Bild :