Yes, it is possible. I’ve done random level generation through Python, so a puzzle game would also be possible.
EDIT: When you add objects, their children are also added (except for lights, right now; that feature’s broken, but was fixed in Kupoman’s Cucumber Google Summer of Code project builds).
Hey! thanks for replying, im really new to bge, i solve most of problems i found reading the bpy references and by trial and error, so i always end up with messy scripts and not so elegant solutions…
could you give me some guidelines on how to make it (some functions names, maybe an example to study from, etc.), i dont want you to solve this for me, just a little guide.
Thanks a lot !
SolarLune, ive found your RLG module earlier today, and took a look at the codes, then i realized i didnt even know about the bge module!!! so i was doing everything via bpy.data, bpy.ops, etc.
Now im trying to redo everything in the rigth way.
Satoru, i think i will stick to scripting for now. i just whant to learn.
I`ve noted that bge module is only avaible when BGE is running, and that is the reason i didn’t know about it.
is there a way to acces to it whitout runnig the BGE?
it would be nice to test the functions using the blender python console first!
Unfortunately, no, there’s no way to access the bge Python module without running the BGE.
EDIT: Maybe Monster or someone made something to have a Python console available in the BGE? I’m not sure…
It shows the most basic possibilities in the Game Engine, like how to adress an object, how to add an object in a scene, change it’s properties, etc. It also gives a small example at the bottom when you click on a method.
Using this you can use python to let it generate a random level and ‘materialise’ it via using scene.addObject(…).
Note thought that it is using python for 2.49, so some methods are depricated. You can use ‘print ( dir(object) )’ in your script, to let it print all the current possibilities/properties to the python console of that object within BGE. (Eg. ‘.setOrientation’ and ‘.getOrientation’ has now become ‘.orientation’ for both reading and writing this value).
The site has been a lot of help to me!
Hello again!
I will be checking that site Rotory, thanks. Also i have been using “print(dir(object))” to find out about available things already.
with the addObject function i get all puzzle pieces as a copy of some predefined objects i put in layer2 of the same scene, that way i get copys with all the logics and properties i defined for the original piece, it`s working great, but… a new problem arises…
i need to acces this “instanced” (dont know if thats the english word for it) objects, but all copies of, lets say, piece1, have the same name, so using “logic.getCurrentScene().objects[‘piece1’].name” gives me access to first instance of piece1 but not to the other instances!! and since it is a read only propertie i cant rename them as i make the instances…
You can use a counter and a dictionary to keep track of individual objects. .addObject returns the created object. Example python:
from bge import logic
scene = logic.getCurrentScene()
if 'counter' not in logic.globalDict.keys():
logic.globalDict['counter'] = 0
obj = scene.addObject(Piece01,TargetCube,0)
logic.globalDict['counter'] += 1
logic.globalDict[str(logic.globalDict['counter'])] = obj
Of course I don’t know what method you use to generate the objects you want to implement, but I think this shows the principle. Now any object can be called via the ID using the dictionary (it is a ‘permanent’ dictionary, that is, it will stay for as long as the game-engine runs). If you want you can add a lot more information about this object into this dictionary, under the ID of the object. Or you can subcategorize them…
Calling object with the ID ‘3’ (simple string in the example, but you can use any) would use the following:
targobj = logic.globalDict[‘3’]
targobj.position = [1,2,3] #add whatever you want to do to it
You do not even need to use such “virtual” ids. Each Python object is unique already see id(object).
logic.getCurrentScene().objects[‘piece1’]
is really bad when it comes to added or instantiated objects.
is dangerous in a python file, as you can’t be sure someone renames or removes the object later. Dependencies on Object names should be avoided as much as possible.
You always get the unique reference to the object with scene.objects etc.
It depends on what you want to do, if it is worth to place them in a separate container (e.g. a dict).
With puzzles you might want to use 2 dimensional lists or a dict with the coordinates as key.
@Rotory, it’ s a good idea, but it wont work in my case, since the identifier you get with obj = scene.addObject(Piece01,TargetCube,0) is the same for all instances of the original object, so it’s not possible to reference a certain instance later that way.thanks anyway!
@Monster, checking with dir(obj) i had found the getPhysicsId() function, which is an identifier for objects that “uses physics” i think. But yours ( id(obj) ) will do better.
im not having much time this week for this little project, but i will be testing this option in my free time.
thanks everyone!
@Monster
Problem with using real object ID’s is that after rebuilding the scene all the ID’s will be different I think. Of course you can rename your dictionary references, but then you can just as well use custom ID’s. Also, adding a unique dictionary entry based on the object’s ID can cause duplicates after reloading, resulting in overwriting an existing entry.
Thx for the unique id(object) though Monster Didn’t know of that one… Is there also a way to find the object with a certain id, without iterating through all the objects by python?
I’m not sure if I understood you correct then, but it returns the object being added. Of course the name is the same, since it is a copy of the original. Try manipulating its position/orientation, and you will see it really refers the object just added. At least for me it works…
The identifier you get has the same name, but it isn’t the same across all instances. For example,
a = sce.AddObject('Cube', obj)
b = sce.AddObject('Cube', obj)
c = sce.AddObject('Cube', obj)
In this code, a, b, and c all have different identifiers to different objects, all cloned from the original that may or may not be in existence in the game. Also, a is an identiifer for a unique object, so you can have the object a check to see if it is equal to the identifier, and it will return true. In other words, each object can distinguish itself as an individual, despite the fact that it may not be the only one.
I do not know a method to get objects via their Id. Maybe there is something usefull in the Python docs.
The usageof the pure Id is really limited.
As already mentioned if you need fast access via a key (e.g position) you can store the object’s reference in a list or dict. Usually you want to get the reference rather than a cryptic number for another lookup ;).
Rebuilding a scene is a complete different topic (it mainly belongs to SaveLoad and/or data transfer/multiplayer). The difference is you try to match one object (one scene) with a different object (other scene/other game).
Wow! im learning a lot of details…
I think i get the idea SolarLune and Rotory are pointing here:
The identifier you get has the same name, but it isn’t the same across all instances.
the name of the reference would be the dame, but not the reference itself for 2 diferent instances. Too bad i cant test rigth now, but i will later!
About the Id, i would have to check every object and check for matching IDs, im testing with a small number of instances now, around 50, but the puzzle size will be greater. Just need to check how expensive would this check be.
I would reiterate (no pun intended :D) Rotory’s point. id(object) is not the same upon a game restart, or when the game is opened again, so it is not useful for saveLoaders. It does remain consistent in game, which is why i use it in multiplayer.
Also, SolarLune, are you aware of dict.items() and dict.values()
(i believe values() works, i can’t be sure)
Additionally Rotory, i don’t believe that you can find an object by its id() because, id is an attribute of the object orientated python, and it is not a separate feature