[Author Prev][Author Next][Thread Prev][Thread Next][Author Index][Thread Index]

Re: [pygame] Bug: numpyarray.pixels_alpha array not properly aligned



Marcus von Appen wrote:
On, Tue Jan 08, 2008, Lenard Lindstrom wrote:

[...]
The problem is that the major and minor axis of the array are reversed from those of the surface. Try replacing lines 272-276 with:

   return numpy.ndarray(buffer=surface.get_buffer (),
                        dtype=numpy.uint8,
                        shape=surface.get_size (),
                        offset=start,
                        strides=(4, surface.get_pitch ()))

The offset argument sets the relative position of the alpha byte. The strides argument makes the second argument the major axis and the first argument skip by the pixel size of 4 bytes. It works with the test case I submitted and an application I wrote that relies heavily on arrays. Hope this helps.

You refer to rev. 1072 I guess, not to the fixed version? I cannot see
any misbehaviour anymore.



That was fast. Unfortunately I found more bugs. In surfarray.py lines 241 and 243 should have "array" instead of "surface". Also make_surface ignores all but the blue color plane for a 3d array. I have enclosed a test program make_surface_bug.py.

Finally, I noticed a major performance decrease for array_colorkey on a 24 bit surface with numpy. It runs 80 times slower than with Numeric. The attached array_colorkey.py is the benchmark program I used. 32 bits surfaces are only 5 times slower, so I suppose one can always update ones programs to them instead.

--
Lenard Lindstrom
<len-l@xxxxxxxxx>

# Shows bug with numpyarray.pixels_alpha.
# Displays two green rectangles with a transparent center.
# A surfarray.make_surface test for numpy. This show as an all-white window.

import pygame as pg
import numpy as np
import cPickle

pg.surfarray.use_array('numpy')

pg.init()

window_size = (200, 200)

screen = pg.display.set_mode(window_size)

pixels = np.zeros(window_size + (3,), np.uint8)
pixels[...] = 255  # All white.
s = pg.surfarray.make_surface(pixels)
screen.blit(s, (0, 0))

pg.display.flip()

while 1:
    event = pg.event.wait()
    if event.type in [pg.KEYDOWN, pg.QUIT]:
        break

# A program to compare compare the performance of surfarray.array_colorkey
# when using numpy and Numeric.

import pygame as pg
from time import clock

start = 0.0
numpy_elapse = 0.0
numeric_elapse = 0.0
a = None
s = pg.Surface((1000, 1000), 0, 24)
s.fill((255, 0, 0), (0, 0, 500, 1000))
s.fill((0, 255, 0), (500, 0, 500, 1000))
s.set_colorkey((0, 255, 0))

for i in range(40):
    pg.surfarray.use_array('numeric')
    start = clock()
    a = pg.surfarray.array_colorkey(s)
    numeric_elapse += clock() - start
    a = None

    pg.surfarray.use_array('numpy')
    start = clock()
    a = pg.surfarray.array_colorkey(s)
    numpy_elapse += clock() - start
    a = None

print "--- Results ---"
print "Numeric:", numeric_elapse, "seconds"
print "Numpy:", numpy_elapse, "seconds"