Kojote Geschrieben 27. August 2019 Melden Share Geschrieben 27. August 2019 Grüße! Mal ne Frage, ich habe mir für mein Speicher und Lademenü überlegt, dass ich eine Grafikanzeige einbaue, an dem Punkt wo gespeichert wird (weißer Leerraum). Dazu wird ein Screenshot von der aktuellen Kameraansicht gemacht, dafür habe ich schon ein Script. Nun brauche ich aber nur ein kleines Bild und nicht die volle Monitorauflösung, zumal PNG ja in solchen größen eh eine zu große Dateigröße hat. Kann man beim Speichern, die Größe des Bildes beeinflussen? Grüße Kojote Link zu diesem Kommentar Auf anderen Seiten teilen More sharing options...
Sascha Geschrieben 27. August 2019 Melden Share Geschrieben 27. August 2019 Da muss man ja wieder raten, wie du deinen Screenshot denn aufnimmst... benutzt du ScreenCapture.CaptureScreenshotAsTexture? Da kannst du dann ja hinterher Texture2D.Resize raufknallen. Link zu diesem Kommentar Auf anderen Seiten teilen More sharing options...
Mr 3d Geschrieben 27. August 2019 Melden Share Geschrieben 27. August 2019 Wenn ich die Beschreibung von Resize richtig verstehe, skaliert die Methode nicht den Inhalt der Textur, sondern setzt einfach die neue Auflösung ohne Farbdaten. https://answers.unity.com/questions/556913/scaling-resizing-an-image-texture2d.html Link zu diesem Kommentar Auf anderen Seiten teilen More sharing options...
Sascha Geschrieben 27. August 2019 Melden Share Geschrieben 27. August 2019 Ah ja, hast natürlich Recht. Danke! Link zu diesem Kommentar Auf anderen Seiten teilen More sharing options...
Kojote Geschrieben 27. August 2019 Autor Melden Share Geschrieben 27. August 2019 Ach sorry, ich erstelle ein Bild mit: ScreenCapture.CaptureScreenshot(path + "/Screenshot_" + time + ".png", 0); Link zu diesem Kommentar Auf anderen Seiten teilen More sharing options...
Sascha Geschrieben 27. August 2019 Melden Share Geschrieben 27. August 2019 Jau, dann nimm mal die "ToTexture"-Version, damit du die Textur runterskalieren kannst (siehe Link von @Mr 3d), und dann kannst du sie selber in eine Datei speichern. Dabei hilft die Klasse ImageConversion. Die spuckt dir bytes aus, die du dann wiederum mit einem FileStream in eine Datei schreiben kannst. Link zu diesem Kommentar Auf anderen Seiten teilen More sharing options...
Kojote Geschrieben 27. August 2019 Autor Melden Share Geschrieben 27. August 2019 OK, schau ich mir dann mal an, danke! Link zu diesem Kommentar Auf anderen Seiten teilen More sharing options...
Kojote Geschrieben 28. August 2019 Autor Melden Share Geschrieben 28. August 2019 OK, also ich bin eine ganze Ecke weiter gekommen, speichern funktioniert soweit: IEnumerator RecordSavegamePicture() { yield return new WaitForEndOfFrame(); texture2D = ScreenCapture.CaptureScreenshotAsTexture(); yield return new WaitForEndOfFrame(); EditPicture(); } private void EditPicture() { texture2D = ScalePictureTexture(texture2D, savegamePictureTargetWidth, savegamePictureTargetHight); SavePicture(); } private Texture2D ScalePictureTexture(Texture2D source, int targetWidth, int targetHight) { Texture2D result = new Texture2D(targetWidth, targetHight, source.format, false); Color[] rpixels = result.GetPixels(0); float incX = (1.0f / (float)targetWidth); float incY = (1.0f / (float)targetHight); for (int px = 0; px < rpixels.Length; px++) { rpixels[px] = source.GetPixelBilinear(incX * ((float)px % targetWidth), incY * ((float)Mathf.Floor(px / targetHight))); } result.SetPixels(rpixels, 0); result.Apply(); return result; } private void SavePicture() { // Textur in JPG und schreibbares Byte-Array Umwandeln byte[] byteTextureArray = texture2D.EncodeToJPG(85); // Dateinamen festlegen file = path + "/SavePicture_" + selectedSavegame + ".jpg"; // Speichern FileStream fileStream = File.Open(file, FileMode.OpenOrCreate); fileStream.Write(byteTextureArray, 0, byteTextureArray.Length); fileStream.Close(); } Nur beim Laden harkts noch, ich kann zwar den Bytestream wieder lesen und in ein Image bringen und dann als Sprite zuweisen, aber dann ... Bekomme nur ein schwarzes Bild. private void LoadPicturesTest() { for (int i = 0; i < savegamePictureSpriteArray.Length; i++) { file = path + "/SavePicture_1.jpg"; if (File.Exists(file)) { // Filestream öffnen und Daten in Byte-Array schreiben FileStream fileStream = File.Open(file, FileMode.Open); byte[] byteTextureArray = new byte[fileStream.Length]; fileStream.Read(byteTextureArray, 0, (int)fileStream.Length); fileStream.Close(); // Textur aus dem Byte-Array erzeugen Texture2D texture2D = new Texture2D(savegamePictureTargetWidth, savegamePictureTargetHight); texture2D.LoadImage(byteTextureArray); texture2D.Apply(); // Aus der Textur das Sprite erzeugen savegamePictureSpriteArray[0] = Sprite.Create(texture2D, new Rect(0, 0, savegamePictureTargetWidth, savegamePictureTargetHight), Vector2.zero); savegamePictureImage.sprite = savegamePictureSpriteArray[0]; Debug.Log("Erledigt!"); } } } EDIT: Sehe gerade, nen Bug meldet er auch: Assertion failed: Invalid AABB inAABB UnityEngine.Canvas:SendWillRenderCanvases() EDIT 2: Super Fehler! Beim testen vergessen Länge und Breite des Bildes anzugeben, Code funktioniert wunderbar: Link zu diesem Kommentar Auf anderen Seiten teilen More sharing options...
Kojote Geschrieben 30. Oktober 2019 Autor Melden Share Geschrieben 30. Oktober 2019 Hat in Unity 2017 sehr gut funktioniert. In Unity 2018 macht er dies nicht mehr. Das kommt nach dem Skalieren heraus, vor dem Skalieren ist das Bild normal: Was macht er denn hier plötzlich? 🤨 Irgendwie gibts ein paar Änderungen bei 2017 zu 2018. Mit JSON hatte ich plötzlich Probleme und mit dem Skalieren nun auch, obwohl ich an beiden Scripten nichts geändert habe. Weiteres Problem ist, ich habe die Coroutine etwas umgebaut, dass das UI nicht mit gerendert wird: IEnumerator RecordSavegamePicture() { yield return new WaitForEndOfFrame(); canvasGroupOverAll.alpha = 0; texture2D = ScreenCapture.CaptureScreenshotAsTexture(); Debug.Log("Screen wird erstellt. Alpha ist: " + canvasGroupOverAll.alpha); canvasGroupOverAll.alpha = 1; yield return new WaitForEndOfFrame(); EditPicture(); } Habe dem Canvas eine CanvasGroup verpasst und setze den Alpha vor dem Screen auf 0. Danach wieder auf 1. Aber er erstellt den Screen immer mit UI, obwohl laut Debug der Alpha 0 ist. Link zu diesem Kommentar Auf anderen Seiten teilen More sharing options...
Thariel Geschrieben 31. Oktober 2019 Melden Share Geschrieben 31. Oktober 2019 Warum skalieren? Weil du ein paar KB sparen willst? 😁 Ich speichere es einfach ab und stelle es verkleinert dar (Image). Dann geht das Speichern auch etwas schneller. Du kannst dir ja mal dieses Asset anschauen. Ist kostenlos und hab ich mir auch gerade geholt zum testen. Scheint nice zu sein. Kannst du auch extrem hochauflösende Screenshots machen (4K, 8K, ...). https://assetstore.unity.com/packages/tools/instant-screenshot-24122 Link zu diesem Kommentar Auf anderen Seiten teilen More sharing options...
Kojote Geschrieben 1. November 2019 Autor Melden Share Geschrieben 1. November 2019 Naja, ein gespeichertes Bild ist knapp über 1 MB groß. Sollte keine Probleme machen. Was jedoch jetzt immer noch nicht geht, ist das Laden der Bilddateien: Problem war hier, dass wenn ich das Bild hiermit einlade: private void LoadPictures() { for (int i = 0; i < savegamePictureSpriteArray.Length; i++) { file = path + "/SavePicture_" + i + ".jpg"; if (File.Exists(file)) { byte[] bytes = File.ReadAllBytes(file); texture2D = new Texture2D(savegamePictureTargetWidth, savegamePictureTargetHeight, TextureFormat.RGB24, false); texture2D.filterMode = FilterMode.Trilinear; texture2D.LoadImage(bytes); savegamePictureSpriteArray[i] = Sprite.Create(texture2D, new Rect(0, 0, savegamePictureTargetWidth, savegamePictureTargetHeight), Vector2.zero); savegamePictureImage.sprite = savegamePictureSpriteArray[i]; } else { savegamePictureImage.sprite = savegamePictureEmpty; } } } Ich zwar sage, dass das Image nur in einer größe von 1000 x 563 angezeigt werden soll, er aber nicht skaliert, sondern das dabei heraus kommt: Er schneidet sich ein Stückchen aus dem Bild raus zur Anzeige. Deswegen die Skalierung. Link zu diesem Kommentar Auf anderen Seiten teilen More sharing options...
Thariel Geschrieben 1. November 2019 Melden Share Geschrieben 1. November 2019 Das ist nicht skalieren was du da machst Du erstellst lediglich ein neues kleineres Bild mit dem Ausschnitt eines grösseren. Schau dir mal Texture2D.Resize an, war aber mit dem Ergebnis nie wirklich zufrieden. Wenn du etwas recherchierst findest du auch viele Snippets die du nutzen kannst. Aber eigentlich brauchst du das Bild ja nicht zu skalieren, du kannst es einfach im Image kleiner darstellen und wenn du ein Aspect Ratio Fitter hinzufügst, hast du alles was du brauchst Link zu diesem Kommentar Auf anderen Seiten teilen More sharing options...
Kojote Geschrieben 2. November 2019 Autor Melden Share Geschrieben 2. November 2019 OK, das verkleinern beim speichern und anzeigen haut nun hin, war nur nen kleiner Fehler. Das mit dem Resize schau ich mir dann mal an, danke! Link zu diesem Kommentar Auf anderen Seiten teilen More sharing options...
Recommended Posts
Archiviert
Dieses Thema ist jetzt archiviert und für weitere Antworten gesperrt.