UPBGE - using split() to disconnect individual batched objects

Hi,

I’ve just recently gotten into UPBGE, and am using it to mesh-batch a voxel-based terrain. Upon selection of one of the batched cubes, I’d like to be able to split it from the rest of the batch.

Supposedly there’s a split() function that allows for this; but I have yet to find the proper syntax…
I’ve literally read every documentation available online on the subject (There’s not much) , and have found nothing of use.
Here’s my code so far:

import bge
import math
import random
import mathutils
from mathutils import noise
cont = bge.logic.getCurrentController()
obj = bge.logic.getCurrentScene().objects
own = cont.owner
add = cont.actuators['add']
def roundup(x):
    return int(math.ceil(x / 1)) * 1
def roundupxy(x):
    return int(math.ceil(x / 20)) * 20

coords = []

for x in range(20):
    for y in range(20):
        position = [(own.worldPosition[0] + x) - 25, own.worldPosition[1] + y, 0]
        H =0.5
        lacunarity = 0.1
        octaves = 5
        Z = mathutils.noise.fractal(position, H, lacunarity, octaves, noise.types.STDPERLIN)
        print (Z)
        for z in range(roundup(abs(Z))):
            add.instantAddObject()
            addedobj = add.objectLastCreated
            print ('added')
            addedobj.worldPosition = (x*2, y*2, (z)*2)
            coords.append(addedobj)
batchGroup = bge.types.KX_BatchGroup(coords)

I have no trouble merging the objects; it’s just the de-merging that’s presenting the problem. In another piece of code (run from a different object), I attempt to remove specific objects from the batch group created:

import bge
cont = bge.logic.getCurrentController()
own = cont.owner
obj = bge.logic.getCurrentScene().objects

near = cont.sensors['Collision']

for i in near.hitObjectList:
    bge.types.KX_BatchGroup.split(i)  #This line is what I'm having trouble with

Could someone kindly give me the proper syntax of split() in this context?
Thanks!

array/dict type?

bge.types.KX_BatchGroup.split(i) will split the array into multiple arrays.

array.remove(i) will remove it from the array
array.append(i) will append it into the array

so this wil work(i think, i’m not working with batchgroups yet)

    removed_list = []
    
    for i in near.hitObjectList:
        bge.types.KX_BatchGroup.remove(i) 
        removed_list.append(i)

I’m getting an error:

AttributeError: type object 'KX_BatchGroup' has no attribute 'remove'

I looked on the API documentation again, and the only functions listed were destruct(), split(), and merge(). They don’t have examples of any of them though; so I’m not sure how to go about this.

bit strange indeed, i have looked a bit into it and batchgroup is kinda tricky to use in combination with a near sensor.

near sensor works by detecting actors.
batchgroup can’t work with objects that uses that actor checkbox, actors already getting batched by the game engine itself, therefore they can’t be batched in the group you want to make.

tried to create a new batchgroup for you but due to the actors it won’t work, it does create a new list/batch but the near sensor wont filter object that are in range(due to actor box is not checked).

if you don’t want to make a batchgroup out of the new list, then checking actors for the objects works as intended for the new_list. but you get an error if you want to batch that list.

here is my test: (maybe it can help you a bit)


from bge import logic, types

def test(cont):
    
    own = cont.owner
    plane = own.scene.objects['Plane']
    sphere = own.scene.objects['Sphere']
    
    near = own.sensors['Near']
    
    to_be_removed = []
    new_list = []
    
    coords = [ own, plane, sphere] 
    batchGroup = types.KX_BatchGroup(coords)
    
    #print(batchGroup.objects) # prints all objects in batch
    #print(batchGroup.objects.filter(own.name)) #filter batch to get the obj you need
    #batchGroup.destruct() # clears the batch
    #print(batchGroup.objects[own.name]) #prints the batched object
    
    for i in near.hitObjectList:
        to_be_removed.append(i)
    
    for obj in batchGroup.objects: 
        if obj not in to_be_removed:     
            new_list.append(obj)

    batchGroup.destruct()
    
    batchGroup = types.KX_BatchGroup(new_list)           
    print('new batch: ' + str(batchGroup.objects))            

# NOTE: objects with actor checked in physics panel can't be batched, results in an error: 
#
#    Error: object "Cube" already used in a batch group
#    Error: object "Plane" already used in a batch group
#    Error: object "Sphere" already used in a batch group
#    Error: Python(Cube), Python script error
#    Traceback (most recent call last):
#      File "C:\Users\Cotaks\Desktop\batchtest.blend\script.py", line 14, in test
#    SystemError: KX_BatchGroup(objects): none objects were merged. 

# NOTE 2:
#    
#    batchgroups need to be destructed before you can make a new one

batchtest.blend (556.6 KB)

so, i can’t help you any further with this.