Pygame,, na co se nehodí,, ? – Python – Fórum – Programujte.com
 x   TIP: Přetáhni ikonu na hlavní panel pro připnutí webu

Pygame,, na co se nehodí,, ? – Python – Fórum – Programujte.comPygame,, na co se nehodí,, ? – Python – Fórum – Programujte.com

 

PiKey
~ Anonymní uživatel
27 příspěvků
28. 10. 2012   #1
-
0
-

PROLOG:

tak jsem před pár začal dloubat do pythonu

jako někdejší mladiství pascalíř / assemblerař, jsem hledal něco, v čem se programy píšou (ne malujou jako např. v delfnovi, tam jsem se neodvážil ani na hello world)

tak se mi ten python i začal líbit, když jsem po pouhých třech večerech dokončil hru "Tajdrlák na poli" (je na ulož.to, kdyby někdo,,)

TEĎ O CO KRÁČÍ:

rozhodl jsem se, že nejlépe si python osvojím tak, že do něj přepíšu nějaké své staré hračky z pascalu a narazil jsem nemile na fakt, že pygame (a dokonce i pygame.surfarray) je neskutečně neschopný pracovat s pixely,,,,,

takže plamen i při 320*200 jel rychlostí frame za deset sekund

tak jsem se na plamen vyplác a dal se do hvězdiček,,,

200 hvězd 45 fps (!!) a to ty hvězdy maluju přes draw.rect, přes pixely to bylo cca 2fps

a teď bych strašně rád nemazal staré hvězdy po updatu, ale nechal je rozmazat (dělával jsem to tak, že jsem projel obrazovku, všechny body světlejší než dejme tomu 10 jsem ztmavil o 10 a naopak všechny body pod 10 nastavil na nulu) takže hvězdičky měly krásné ocásky,,

což je v pygamu nemožné :-(

tak jsem to vyřešil tak, že každá hvězdička nechává 5 stop, a postupně jsou vykreslovány tmavšími barvami až (0,0,0)

framerate kolem 33,, při 500 hvězdičkách už to de na 15..

takže,,,,, je nějaké řešení jak tohleto dělat lépe (jinej modul než pyžamo?)

jo a ještě jedna věc,, nejdou malovat rect o velikosti (1,1), minimálně (2,2),, to je schválně, nebo bug, nebo fičura?


import os, sys
import pygame
from random import *
from pygame.locals import *

  


class star (pygame.sprite.Sprite):
    def __init__(self):
        pygame.sprite.Sprite.__init__(self)
        self.x = 3200
        self.y=2400
        self.reset()
        self.rect2=self.rect
        self.rect3=self.rect
        self.rect4=self.rect
        self.rect5=self.rect
        self.color2 = (0, 0, 0)
        self.color3 = (0, 0, 0)
        self.color4 = (0, 0, 0)
        self.color5 = (0, 0, 0)
    def reset(self):
        self.speed = randint (10, 20)
        u=1
        self.x = randint (200, 6200) 
        self.y = randint (200, 4600)
        while u:
            if (self.x in range (3100,3301))and(self.y in range (2300,2501)) :
                self.x = randint (200, 6200) 
                self.y = randint (200, 4600)
            else: u=0
        self.size=randint(2,3)
        self.rect = (self.x/10, self.y/10, self.size, self.size)
        self.r = randint (10, 20)
        self.g = randint (20, 25)
        self.b = randint (25, 30)
        self.color = (0, 0, 0)
    def update (self):
        a = (int(((self.rect[0]-320)**2 + (self.rect[1]-240)**2)**0.5)+280)/8
        self.color= (self.r*a/10, self.g*a/10, self.b*a/10)
        self.color2= (self.r*a/12, self.g*a/12, self.b*a/12)
        self.color3= (self.r*a/14, self.g*a/14, self.b*a/14)
        self.color4= (self.r*a/16, self.g*a/16, self.b*a/16)
   
        if self.x >= 3200:
            self.x += ((self.x-3200)*self.speed)/700
        else:
            self.x -= ((3200-self.x)*self.speed)/700
        if self.y >= 2400:
            self.y += ((self.y-2400)*self.speed)/700
        else:
            self.y -= ((2400-self.y)*self.speed)/700
         
            
        self.rect5 = self.rect4
        self.rect4 = self.rect3
        self.rect3 = self.rect2
        self.rect2 = self.rect
        self.rect = (self.x/10, self.y/10, self.size, self.size)
        if not (self.rect[0] in range (0, 640)) :
            self.reset()
        if not (self.rect[1] in range (0, 480)) :
            self.reset()
        

def toggle_fullscreen():
    obrazovka = pygame.display.get_surface()
    tmp = obrazovka.convert()
    caption = pygame.display.get_caption()
    cursor = pygame.mouse.get_cursor()  # Duoas 16-04-2007 
    
    w,h = obrazovka.get_width(),obrazovka.get_height()
    flags = obrazovka.get_flags()
    bits = obrazovka.get_bitsize()
    
    pygame.display.quit()
    pygame.display.init()
    
    obrazovka = pygame.display.set_mode((w,h),flags^FULLSCREEN,bits)
    obrazovka.blit(tmp,(0,0))
    pygame.display.set_caption(*caption)
 
    pygame.key.set_mods(0) #HACK: work-a-round for a SDL bug??
 
    pygame.mouse.set_cursor( *cursor )  # Duoas 16-04-2007
    
    return obrazovka
        



pygame.init()
obrazovka = pygame.display.set_mode((640, 480))
pozadi = pygame.Surface(obrazovka.get_size()).convert()
obrazovka.blit(pozadi, (0, 0))
pozadi.fill((0,0,0))
pygame.display.flip()
hvezd=200
hvezdicka = star(),
for n in range (1, hvezd) : hvezdicka+=star(),
stars=pygame.sprite.RenderPlain((hvezdicka))

pocitadlo=0

#toggle_fullscreen()
obrazovka=pygame.display.get_surface()

konec=0
while not konec :
    if pocitadlo==0 : a = pygame.time.get_ticks()
    pocitadlo= (pocitadlo+1) % 100
    for udalost in pygame.event.get(): 
        if (udalost.type == QUIT) or (udalost.type==KEYDOWN and udalost.key == K_ESCAPE):
            konec=1
 
    stars.update()
    
    for n in range (0, hvezd) :
        pygame.draw.rect(obrazovka, (hvezdicka[n].color5), (hvezdicka[n].rect5))
        pygame.draw.rect(obrazovka, (hvezdicka[n].color4), (hvezdicka[n].rect4))
        pygame.draw.rect(obrazovka, (hvezdicka[n].color3), (hvezdicka[n].rect3))
        pygame.draw.rect(obrazovka, (hvezdicka[n].color2), (hvezdicka[n].rect2))
        pygame.draw.rect(obrazovka, (hvezdicka[n].color), (hvezdicka[n].rect))

    pygame.display.flip()
    if pocitadlo==99 :
        b=pygame.time.get_ticks()
        print ( 1000/((b-a)/100)), " FPS"




pygame.quit()
Nahlásit jako SPAM
IP: 88.102.202.–
kocourOggy0
Newbie
29. 10. 2012   #2
-
0
-

#1 PiKey

Vykreslování bys mohl urychlit například tím, že nebudeš obnovovat celé okno, ale jen ty obdélníkové části, které se změnily.

pygame.display.update (seznam obdelníků nebo obdélník)

Jestli chceš dělat pouze 1 pixelové čtverečky použij třeba PixelArray. PixelArray však zamyká plochu, takže kdybys  chtěl použít např. blit(), Python ti vyhodí chybovou hlášku. Pro odemknutí plochy stačí smazat samotný objekt PixelArray.

windowSurface = pygame.display.set_mode()

BLACK = (0, 0, 0)

pixArray = pygame.PixelArray(windowSurface)

pixArray[480][380] = BLACK

del pixArray

Na otázku "na co se Pygame nehodí?"  ti nejspíš neodpovim. Pokud vim, nehodí se na 3D - ale to nejspíš neni odpověď, kterou hledáš    Předpokládám, že znáš stránky http://www.pygame.org/news.html, když používáš tento modul.  Když se podívám na některé hry právě na těchto stránkách, jsem překvapen, co dokáže programátor pomocí Pythonu a Pygamu vyčarovat. (viz http://www.pygame.org/project-SubTerrex-2389-4222.html ) Tvůj kód je docela zajímavý testovač výkonu (200 hvězd - 45 fps, 500 hvězd - 15 fps). Řekni mi však, co to chceš dělat za hru/program, kde ti bude neustále lítat 500 hvězdiček?

Se svými znalostmi a úrovní programování rozhodně nejsem vhodná osoba, která by zde měla rozdávat moudra ,obzvlášť pokud tato osoba neumí OOP a tvůj kód jí není zcela jasný 

Na tvoji otázku bude nejlepší odpovědět odkazem:

http://www.geon.wz.cz/pygame/tut/intro/intro.html

(po přečtení bys sis měl udělat jasnější obrázek o Pygamu)

a tady nalezneš několik tipů pro urychlení programů, které využívají Pygame (např. již zminěné vykreslovaní menší části plochy):

http://www.geon.wz.cz/pygame/tut/newbieguide.html

Nahlásit jako SPAM
IP: 89.24.14.–
Věčný začátečník nejen v Pythonu.
PiKey
~ Anonymní uživatel
27 příspěvků
30. 10. 2012   #3
-
0
-

no v podstatě jsi mi odpověděl (a odpověděly mi na to i nějaké pokusy provedené)

pygame (a zjevně python obecně sám o sobě) se nehodí tam, kde chci provádět více než dejme tomu 10**5 početních operací v sekundě

je fakt že těžko vymyslím hru, která to bude dělat

takže si budu muset najít jinou cestu jak si osvojit python a pygame 
(a je to škoda, měl jsem v pascaloassembleru mooc hezký animace na podobných principech, jako průlet červí dírou, 3D objek celý z xyz bodů (a to si teď už v pythonu nedokážu představit zpětný přepočet xyz na xy/color) který rotoval, hořel a ještě se morfoval do několika podob, dokonce jsem i statečně ty objekty texturoval, a to všechno přes jakýsi pixelarray)

abych teda odpověděl kompletně,,,

dal jsem si do svého kódu na stěžejní místa časoměřiče a vypisoval jsem si časy jednotlivých operací..

výpočty hvězdiček cca 2/3 času
vykreslení rectú cca 1/3 času
display.flip nebo display.update cca 2-3ms

zkoušel jsem i přepsat kód do pixelarray - zpomalení při 200 hvězdičkách na 6fps

a čemu přesně nerozumíš na tom kódu?? já s OOP taky nikdy nebyl kamarád, ale nic jiného mi nezbejvá, jestli se chci vrátit po letech na pole ťukání programů

na začátku si definuju třídu jménem star, což je přízrak, mající nějaké ty svoje parametři, a má tři vložené funkce,, (__init__) té se nevyhneme, (reset) která nastaví hvězdičku někam náhodně do výchozí pozice a (update) která ji posouvá a v případě potřeby volá (reset)

pak jsem si udělal proměnnou typu tuple, do které nasázím těch 200 star, takže hned na začátku se mi pro 200 proměnných udělá jak (__init__) tak (reset) a mám 200 hvězdiček, které už jen čekají, až je namaluju

zbytek je hloupej cyklus, kterej dvěstakrát volá star.update(), pak to namaluje a jede znova

Nahlásit jako SPAM
IP: 88.102.202.–
kocourOggy0
Newbie
31. 10. 2012   #4
-
0
-

#3 PiKey

Mohl bys ještě zkusit knihovnu Psyco. Psyco v Pythonu zrychluje některé operace. Mohlo by to výrazně napomoci ke zrychlení tvého kódu. Knihovnu jsem osobně nezkoušel, ale mělo by stačit přidat do tvého programu pouze 2 řádky navíc.

import psyco
psyco.full()

Funguje však jenom s verzí Pythonu 2.x

Tady je toho o Psycu trochu víc, týká se to i výkonu samotného Pythonu:

 http://python.wraith.cz/uvod-vykon.php

Nahlásit jako SPAM
IP: 89.24.17.–
Věčný začátečník nejen v Pythonu.
PiKey
~ Anonymní uživatel
27 příspěvků
1. 11. 2012   #5
-
0
-

#4 kocourOggy
nepodařilo se mi rozchodit ani psyco (ten projekt už je zastavenej x let) ani pypy   

Nahlásit jako SPAM
IP: 88.102.202.–
sputnikone+1
Věrný člen
1. 11. 2012   #6
-
0
-

#5 PiKey
psyco je opravdu mrtvé, je doporučeno používat PyPy. A tos nerozchodil samotné PyPy nebo pygame pod ním (který ještě PyPy přímo nepodporuje, existuje ale "kompatibilní" fork https://bitbucket.org/stefanor/pygame-pypy)

Nahlásit jako SPAM
IP: 89.102.207.–
PiKey0
Newbie
1. 11. 2012   #7
-
0
-

#6 sputnikone
vůůbec se mi ho nepodařilo nainstalovat, asi je pythonovská angličtina mocnější soupeř než ostatní angličtina    jako by to nemohlo mít instalační balíček,,,,

zkusim kouknout na to pygame pypypy 

Nahlásit jako SPAM
IP: 88.102.202.–
říkal jsem si,, že už na světě nemůže být hůř,, pak mě napadlo začít pracovat v pythonu
zlz
~ Anonymní uživatel
634 příspěvků
2. 11. 2012   #8
-
0
-

Pro zjištění rozsahu hodnoty zbytečně vytváříš list, který prohledáváš

if not (self.rect[0] in range (0, 640)) :

Toto je rychlejší

if not (0 <= self.rect[0] <= 640) :

Když místo

for n in range (0, hvezd) :
    pygame.draw.rect(obrazovka, hvezdicka[n].color5, hvezdicka[n].rect5)

požiješ

for h in hvezdicka:
    pygame.draw.rect(obrazovka, h.color5, h.rect5)

tak taky dostaneš pár FPS navíc. (Jednak zase nevytváříš list pro range a druhak opakovaně neindexuješ list hvězdiček)

Co se týče čistě pygame, tak u mě je rychlejší jednou smazat celou obrazovku, než pořád vykreslovat ten pátý rect (který zřejmě má za úkol jen mazat stopu). A na samotné kreslení těch čtverců je rychlejší obrazovka.fill, tím dostaneš nejvíc. Pro 500 hvězdiček jsem měl původně 34 FPS, po úpravách 125.

obrazovka.fill((0,0,0))

for h in hvezdicka:
    obrazovka.fill(h.color4, h.rect4)
    ...
Nahlásit jako SPAM
IP: 80.188.216.–
zlz
~ Anonymní uživatel
634 příspěvků
2. 11. 2012   #9
-
0
-

Ty první dvě poznámky se týkají py2, který pravděpodobně používáš. V py3 s tím není problém.

Nahlásit jako SPAM
IP: 80.188.216.–
PiKey0
Newbie
2. 11. 2012   #10
-
0
-

#9 zlz
hooodně dobrý!

budu si teda pamatovat: nepoužvat range, kde to není nevyhnutelný

FPS se mi zrychlilo téměř 2× (starej semptron 2600 nebo kolik)

Nahlásit jako SPAM
IP: 88.102.202.–
říkal jsem si,, že už na světě nemůže být hůř,, pak mě napadlo začít pracovat v pythonu
Wrunx
~ Anonymní uživatel
35 příspěvků
2. 11. 2012   #11
-
0
-

Také drobnost: místo

 self.color= (self.r*a/10, self.g*a/10, self.b*a/10)
 self.color2= (self.r*a/12, self.g*a/12, self.b*a/12)
 self.color3= (self.r*a/14, self.g*a/14, self.b*a/14)
 self.color4= (self.r*a/16, self.g*a/16, self.b*a/16)

se dá použít "předzpracovaný" součin:

ra=self.r*a; ga=self.g*a; ba=self.b*a
self.color= (ra/10, ga/10, ba/10)
self.color2= (ra/12, ga/12, ba/12)
self.color3= (ra/14, ga/14, ba/14)
self.color4= (ra/16, ga/16, ba/16)

ušetříš sice jen 9 násobení na objekt, ale i to se počítá ;-)

Nahlásit jako SPAM
IP: 188.120.195.–
PiKey0
Newbie
2. 11. 2012   #12
-
0
-

#11 Wrunx
nojo,,,,,,,, teď se stydim, je vidět že jsem sedl k ťukání programů po dlouhý době,,

no možná by pomohlo i místo toho dělení provádět >> (v asm to bylo shr, >> jsem objevil až teď)

Nahlásit jako SPAM
IP: 88.102.202.–
říkal jsem si,, že už na světě nemůže být hůř,, pak mě napadlo začít pracovat v pythonu
PiKey0
Newbie
4. 11. 2012   #13
-
0
-

#11 Wrunx
tk přednásobení přidalo cca 3-4fps při těch 500 hvězdiček (akt. jsem na 26-28)

Nahlásit jako SPAM
IP: 88.102.202.–
říkal jsem si,, že už na světě nemůže být hůř,, pak mě napadlo začít pracovat v pythonu
Wrunx
~ Anonymní uživatel
35 příspěvků
4. 11. 2012   #14
-
0
-

Já jsem to tedy různými kosmetickými úpravami zvedl z původních průměrných 24 na průměrných 44 při 500 hvězdičkách, ale samotný problém rychlosti grafiky to imho samosebou neřeší, to všechno jsou jen sekundární optimalizace, protože nic lepšího neumím :-D

Nahlásit jako SPAM
IP: 188.120.195.–
PiKey0
Newbie
4. 11. 2012   #15
-
0
-

j#14 Wrunx

já jsem tak prolejzal pyžamo.org a narazil jsem na prográmek jménem "numpy gumbo 0.5" který demonstruje nějaký hezký grafický vychytávky (plazma, oheň, bumpmapping atd..) a kupodivu to pracuje celkem rychle,, tak až najdu odvahu, mohl bych si ty kódy projít a dojít na to, kde je fígl (je to postavený na pyžamo a na numpy)

Nahlásit jako SPAM
IP: 88.102.202.–
říkal jsem si,, že už na světě nemůže být hůř,, pak mě napadlo začít pracovat v pythonu
Zjistit počet nových příspěvků

Přidej příspěvek

Toto téma je starší jak čtvrt roku – přidej svůj příspěvek jen tehdy, máš-li k tématu opravdu co říct!

Ano, opravdu chci reagovat → zobrazí formulář pro přidání příspěvku

×Vložení zdrojáku

×Vložení obrázku

Vložit URL obrázku Vybrat obrázek na disku
Vlož URL adresu obrázku:
Klikni a vyber obrázek z počítače:

×Vložení videa

Aktuálně jsou podporována videa ze serverů YouTube, Vimeo a Dailymotion.
×
 
Podporujeme Gravatara.
Zadej URL adresu Avatara (40 x 40 px) nebo emailovou adresu pro použití Gravatara.
Email nikam neukládáme, po získání Gravatara je zahozen.
-
Pravidla pro psaní příspěvků, používej diakritiku. ENTER pro nový odstavec, SHIFT + ENTER pro nový řádek.
Sledovat nové příspěvky (pouze pro přihlášené)
Sleduj vlákno a v případě přidání nového příspěvku o tom budeš vědět mezi prvními.
Reaguješ na příspěvek:

Uživatelé prohlížející si toto vlákno

Uživatelé on-line: 0 registrovaných, 2 hosté

Podobná vlákna

Pygame na python 2.5 — založil Polarski

Pygame instalace — založil Akimi Keita

Pygame Linux — založil Anonymní uživatel

Pygame a ikona — založil Polarski

 

Hostujeme u Českého hostingu       ISSN 1801-1586       ⇡ Nahoru Webtea.cz logo © 20032024 Programujte.com
Zasadilo a pěstuje Webtea.cz, šéfredaktor Lukáš Churý