开发者

Setting Pixels Quickly

I have searched and searched for a good answer and I am about to cry from frustration. I am a hobbyist programmer, I don开发者_C百科't do things because they make sense, or they are the right way to do them; I do them to learn how, and right now I am stumped.

I want to set individual pixels on the screen. This may sound easy, but it's my other conditions that makes it hard. I need to do this quickly, CPU only, 20 fps or better (with other program elements running of course), on a 400 by 300 screen or better (full screen?).

I have been rendering some cool images using programs I wrote in Python that uses Pygame, but it takes 50 milliseconds to fill a 100px by 100px screen with just random pixels (that's my 20 fps right there, and other program bits slow it down more). Ideally I would LOVE to make my own (crappy) 3D game that just uses the CPU only, setting pixels on the screen (perhaps a voxel octree sort of graphics).

Is there any way (with any language, but preferably Python) I could like, make a 2D array of pixel values (more like 3D array with RGB) (is this called a bitmap?) in the RAM and dump it on to the display or something? Wouldn't that be fast??? How DO you interface directly with the pixels on a window. Argh! I am so clueless. I am / am not a programming noob. Give me whatever you can throw at me, I can digest it. I just need some pointers (haha) in the right direction.


If you want to make your own "for each pixel" math (as opposed to just moving circles and bitmaps around), you will have to do it in C (or C++) to get anywhere close to machine speed.

On the other hand, if you want to make a full game, it will not be fun to write it all in a low-level language like C. You will need to combine fast C code with some some high-level scripting language. With Python you can bridge to a C extension module via numpy, or you can embed a language like Lua into C code, or you can try (oh horror) to learn high-level coding in C++. Either way things will get complex.

If you just want to play around with fast pixel rendering, I reccommend to use SDL (that's what pygame uses internally) but with C or C++ only. Follow a tutorial like this one and have some fun.

If you want to stay within the comfort of Python, I suggest you try a 2D game first (loading and moving around bitmaps) or experiment with cairo (render geometric shapes).


I'm able to get over 20 fps at a resolution of (1920,1080) with pygame.

As Mallett pointed out, you should be using the pygame.surfarray.blit_array() function to copy the pixel data to pygame, and then update the screen with a call to pygame.display.flip().

>>> import timeit
>>> timeit.timeit('pygame.surfarray.blit_array(screen, pixels);pygame.display.flip()', setup='import pygame;import numpy as np;size=(1920,1080);screen=pygame.display.set_mode(size);pixels=np.random.randint(np.iinfo(np.uint32).max,size=size).astype(np.uint32)', number=20)
0.6346819400787354
>>> timeit.timeit("""
... pygame.surfarray.blit_array(screen, pixels)
... pygame.display.flip()
... """,setup="""
... import pygame
... import numpy as np
... size=(1920,1080)
... screen=pygame.display.set_mode(size)
... pixels=np.random.randint(np.iinfo(np.uint32).max,size=size).astype(np.uint32)
... """, number=20)
0.4848361015319824


What you really want to do for PyGame is use pygame.surfarray or pygame.pixelarray. After you set the values in the array, then you copy them all at once. If you read the documentation about surface.set_at(...), which sets pixels individually, you'll see that it's not recommended for all but the smallest tasks.

pygame.surfarray and pygame.pixelarray are typically based on NumPy or Numeric (use NumPy). Googling produces http://pygame.org/docs/tut/surfarray/SurfarrayIntro.html, which will give you a basic overview of some of the great things you can do.


You must look into bitblit , Though I have not done bit-blit in python, googling for it gave promising results. Here is a related discussion from Graphics gems p.134, where they discuss similar problem.


Blockquote Is there any way (with any language, but preferably Python) I could like, make a 2D array of pixel values (more like 3D array with RGB) (is this called a bitmap?) in the RAM and dump it on to the display or something?

Yes, this is called a Frame Buffer. You draw the bitmap in memory and then swap that memory into display memory.

0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜