Seite 1 von 1
Pygame Surface durch Strings erstellen?
Verfasst: Mittwoch 30. Dezember 2020, 14:22
von liil92
Hallo, ich bin derzeit auf am programmieren eines kleinen roboters. Dieser soll wie der cozmo nur augen zur anschaulichung haben.
Bis jetzt hab ich die Augen mittels einzelner Bilder und Frames dargestellt, dies wird aber bei rund 10 verschiedenen Formen etc nicht mehr lohnenswert. ( Da zu viele Bilder beigefügt werden müssen um Animationen flüssig darzustllen)
Deswegen habe ich mir überlegt, statt die Bilder einzeln anzeigen zu lassen, mir strings zu erstellen, welche als surface dargestellt werden.
Somit könnte ich die Strings in dem Programm verändern und abrufen, aussehen würden diese dann etwa so hatte ich mir überlegt, wobei wie beim cozmo nur die Augen eine Farbe hätten, also die '0' :
Code: Alles auswählen
" ",
" OOOOOO ",
" OOOOOO OOOOOO ",
" OOOOOO OOOOOO ",
" OOOOOO OOOOOO ",
" ",
" ",
Leider finde ich im Internet nichts unter dieser Suche 'Strings als Surface ausgeben - pygame'
Nun ist die Frage, ob dies überhaupt geht? Kann man Strings als Surface darstellen lassen? und wenn ja, wie? Welche Funktion etc?
Mfg
liil92
Re: Pygame Surface durch Strings erstellen?
Verfasst: Mittwoch 30. Dezember 2020, 15:49
von __blackjack__
@liil92: Ich verstehe nicht so ganz welches Problem dieser Umweg über Zeichenketten lösen soll. Das geht natürlich. Du müsstest dafür halt Code schreiben der die Zeichen irgendwie in Grafik umsetzt. Zum Beispiel für jedes "O" an der entsprechenden Stelle ein Quadrat oder einen Kreis zeichnet.
Re: Pygame Surface durch Strings erstellen?
Verfasst: Mittwoch 30. Dezember 2020, 16:59
von liil92
__blackjack__ hat geschrieben: Mittwoch 30. Dezember 2020, 15:49
@liil92: Ich verstehe nicht so ganz welches Problem dieser Umweg über Zeichenketten lösen soll. Das geht natürlich. Du müsstest dafür halt Code schreiben der die Zeichen irgendwie in Grafik umsetzt. Zum Beispiel für jedes "O" an der entsprechenden Stelle ein Quadrat oder einen Kreis zeichnet.
Hey Blackjack,
damit umgehe ich das Problem andauernd Bilder beizufügen. Außerdem spare ich Speicherplatz ein. Bisher habe ich beispielsweise: Augen bewegen sich von der mitte nach rechts. Dafür brauche ich schon 8 Bilder um dies darzustellen. Abfragen tu ich diese nacheinander in einem Array. Auch das beifügen der Bilder dauert Zeit (Import(), etc).
Mit dem string array würde ich bezwecken wollen, dass man erstens Animationen schneller beifügen kann, da man lediglich ein neues string array erstellt. zweitens würde ich dadurch auch Speicherplatz sparen.
So zusagen würde ich gerne über die Pixel arbeiten und beispielsweiße bei jedem O das Pixel Blau Färben.
Genau da stellt sich mir die Frage, ob es hierfür eine Funktion gibt welche mein String Array einließt und daraus ein Surface erstellt, oder ich aber wie du schon geschrieben hast, selbst Code schreiben muss.
Ps: Ich bin relativ neu bei Python vorallem bei pygame..
Re: Pygame Surface durch Strings erstellen?
Verfasst: Mittwoch 30. Dezember 2020, 17:01
von __deets__
Es gibt dafür keine Funktion. Du kannst sie dir aber schreiben. In dem du durch deinen String wanderst & an den entsprechenden Stellen die Pixel setzt.
Re: Pygame Surface durch Strings erstellen?
Verfasst: Freitag 1. Januar 2021, 10:22
von ThomasL
Hi, kannst du so umsetzen:
Code: Alles auswählen
import numpy as np
import pygame
eyes = [" ",
" OOOOOO ",
" OOOOOO OOOOOO ",
" OOOOOO OOOOOO ",
" OOOOOO OOOOOO ",
" ",
" "]
eyes_converted = np.array([[int(char.translate({ord('O'):'255', ord(' '):'0'})) for char in line] for line in eyes])
print(eyes_converted)
surf = pygame.surfarray.make_surface(eyes_converted)
Re: Pygame Surface durch Strings erstellen?
Verfasst: Freitag 1. Januar 2021, 11:08
von ThomasL
@Admin Warum kann ich meinen Beitrag nicht mehr ändern?
(OK, gerade gesehen, dass das wohl nur innerhalb eines Zeitfensters nach einstellen geht. Ist auch gut so. )
@OP pygame.surfarray.make_surface() nimmt auch ein 2D Array mit (R,G,B) Werten. So kannst du über das Dictionary die komplette RGB Palette verwenden.
Code: Alles auswählen
import numpy as np
import pygame
eyes = [" ",
" OOOOOO ",
" OOOOOO OOOOOO ",
" OOOOOO OOOOOO ",
" OOOOOO OOOOOO ",
" ",
" "]
CONVERT = {'O': (0, 0, 0), ' ': (255, 255, 255)}
eyes_converted = np.array([[CONVERT[char] for char in line] for line in eyes])
surf = pygame.surfarray.make_surface(eyes_converted)
Re: Pygame Surface durch Strings erstellen?
Verfasst: Freitag 1. Januar 2021, 16:03
von __blackjack__
Wobei ich da immer noch nicht den Vorteil gegenüber einem Bild sehe.

Re: Pygame Surface durch Strings erstellen?
Verfasst: Dienstag 5. Januar 2021, 17:33
von liil92
Guten Abend,
erstmal danke für die vielen antworten:)
Ich habe mich nach den Feiertagen, heute selbst nochmal daran versucht..
Ich denke ich bin auf dem richtigen Weg, jedoch stimmt irgendwas nicht wirklich.
Ich versuche über die Funktion 'set_at()' die Pixel an den bestimmten Stellen zu färben.
Anschließend will ich das Ergebnis vergrößern.
Herauskommt jedoch lediglich ein einfarbiges viereck.
Hier mein Code, ich bitte um Entschuldigung wenn dieser etwas wirr ist.
Code: Alles auswählen
import pygame
import sys
import time
import numpy
import cv2
meinArray=[
" OOOOOO OOOOOO ",
" OOOOOO OOOOOO ",
" OOOOOO OOOOOO ",
" OOOOOO OOOOOO ",
]
#Parameter
white = (255,255,255)
height, width = 400, 300
size = height, width
a = b = 0
# Initialisierung pygame
pygame.init()
clock= pygame.time.Clock()
#initialisierung der Bildschirme
screen = pygame.display.set_mode([800,600])
leeres_Bild = pygame.Surface((len(meinArray[0]), len(meinArray)))
#pygame.Surface.fill(leeres_Bild, white)
#Ausgaben test
print('Hello World')
#print(rect)
print(len(meinArray[0]), len(meinArray))
print(pygame.Surface.get_size(screen))
#Separierung und Untersuchung der Zeilen und Spalten, mit anschließender Aktion
x = y = 0
for row in meinArray:
for col in row:
if col == "O":
leeres_Bild.set_at((x, y), pygame.Color(255,0,0))
x += 1
y += 1
x = 0
leeres_Bild = pygame.transform.scale(leeres_Bild, (40*len(meinArray[0]), 40*len(meinArray)))
rect = leeres_Bild.get_rect()
while True:
for event in pygame.event.get():
if event.type == pygame.QUIT: sys.exit()
screen.fill((30,30,30))
screen.blit(leeres_Bild, rect)
pygame.display.update()
clock.tick(60)
MFG