Way to optimize my image slicing cffi based function

33 views Asked by At

I'm using cffi and raylib to create a small game engine, i've just created a function that can slice an image, despite some improvements that have to be done, it's working well, therefore, my function is really slow.

def slice(path, size):
    slices = []
    base_image = ffi.new("Image*", LoadImage(path.encode("ascii")))
    for y in range(0, base_image.height, size[1]):
        for x in range(0, base_image.width, size[0]):
            image = ffi.new("Image*", LoadImage(path.encode("ascii"))) #The problem is here
            ImageCrop(image, (x, y, x+size[0], y+size[1]))
            slices.append(image[0])
    return slices

When i tried to do this :

def slice(path, size):
    slices = []
    base_image = ffi.new("Image*", LoadImage(path.encode("ascii")))
    for y in range(0, base_image.height, size[1]):
        for x in range(0, base_image.width, size[0]):
            image = base_image 
            ImageCrop(image, (x, y, x+size[0], y+size[1]))
            slices.append(image[0])
    return slices

or

import copy
def slice(path, size):
    slices = []
    base_image = ffi.new("Image*", LoadImage(path.encode("ascii")))
    for y in range(0, base_image.height, size[1]):
        for x in range(0, base_image.width, size[0]):
            image = copy.copy(base_image) 
            ImageCrop(image, (x, y, x+size[0], y+size[1]))
            slices.append(image[0])
    return slices

it did'nt work.

1

There are 1 answers

0
Armin Rigo On

How would you do that in C? I'm not sure, but reading your piece of code, I would guess that maybe Image is the return type of the LoadImage() function (not Image* or anything else), whereas ImageCrop() takes a Image* p_image first argument. It uses *p_image as input, crops it, and outputs the cropped image by writing the new Image inside *p_image. I'm not sure, but this might be one of the many ways to do it in C.

In other words, and again this is a guess, in C you'd write code like this:

Image base_image = LoadImage(path);
for (...every slice...) {
    Image image_part = base_image;   // makes a copy of the Image data structure in C
    ImageCrop(&image_part, ...);
    // now 'image_part' contains the cropped image
}

If that is actually correct, then the CFFI version would be:

base_image = LoadImage(path.encode("ascii"))   # returns an Image
for ...:
    image_part = ffi.new("Image *", base_image)
    # ^^ makes a new 'Image' initialized with a copy of the data structure
    #    from base_image, and returns a pointer to that new Image
    ImageCrop(image_part, (...))
    images.append(image_part[0])