This topic is in reference to the article found here: http://www.cocos2d-iphone.org/archives/1214
The comments section was getting way too busy with questions, so please post anything question related here for now. Thanks.
A fast, easy to use, free, and community supported 2D game engine
This topic is in reference to the article found here: http://www.cocos2d-iphone.org/archives/1214
The comments section was getting way too busy with questions, so please post anything question related here for now. Thanks.
Thanks for the thread.
Okay, as I am diving into the code, I understand most of what I am seeing. My first real head scratcher is the methods for Ninja. I see the +(id) ninjaWithGame twice… with one having a cpShape as a second parameter, and one without. The one without simply calls the one with. Same for the -(id) initWithGame… one with cpShape, and one without, with the one without calling the one with.
So, as I am not a learned man in these areas, left to my own devices, I would eliminate the two methods that do not have shape as a parameter since all they do is call another method. I have no reason, other than they look to be duplicative. I assume there is a reason to keep them both, and I would love to know what it is!
Okay, as I am diving into the code, I understand most of what I am seeing. My first real head scratcher is the methods for Ninja. I see the +(id) ninjaWithGame twice… with one having a cpShape as a second parameter, and one without. The one without simply calls the one with. Same for the -(id) initWithGame… one shape, and one without, with the one without calling the one with.
So, as I am not a learned man in these areas, left to my own devices, I would eliminate the two methods that do not have shape as a parameter. I have no reason, other than they look to be duplicative. I assume there is a reason to keep them both, and I would love to know what it is!
The reason there are 2 "constructors" is mainly for convenience. The first case is that you just want to have a ninja created and you don't care about it's shape, it's nice to have it just created. The second case is the saved game case when it's reading it back in; the SpaceManager serialization code hands you a shape and you create whatever you need to with it. In that case we just pass the shape on to the ninja constructor.
Hi again. This is a bit tangential, but I am having difficulty adapting the code from Ninja.h/.m to use a poly shape. I didn't see anything to replace addCircleAt: for replacing the shape with a poly shape. I did find initWithFile:bodyName:spaceManager that appears to do exactly what I need. Unfortunately while it compiles fine, it crashes quickly. Here is where the crash starts.
Assertion failed: (bd), function -[GCpShapeCache anchorPointForShape:], file /Users/jcmeyer5/Documents/Project/Project/SpaceManager/PhysicsEditorLoaders/GCpShapeCache.m, line 216.
sharedlibrary apply-load-rules all
Current language: auto; currently objective-c
kill
error while killing target (killing anyway): warning: error on line 2184 of "/SourceCache/gdb/gdb-1708/src/gdb/macosx/macosx-nat-inferior.c" in function "void macosx_kill_inferior_safe()": (os/kern) failure (0x5x)
quit
Program ended with exit code: 0
It gives a SIGABRT at the assert(bd) in the implementation of anchorPointForShape:
Not sure what I am doing wrong. From what I have read of this function, it should work.
Thanks!
That's Physics Editor specific code, if you're using that you'll need to follow their rules which include loading a file of shape/body definitions created using Physics Editor.
There actually is an addPolyAt function:
[game.spaceManager addPolyAt:pos mass:10 rotation:0 numPoints:3 points:vert1, vert2, vert3, nil];
http://www.mobile-bros.com/spacemanager/docs/0.1.2/interface_space_manager.html
Okay. That helps. Didn't you write hooks into the PE assets? I thought that was the cpCCSprite+PhysicsEditor.h/.m included with SpaceManager. That is where I found the initWithFile:bodyName:spaceManager.
Thanks for your help. I didn't think addPolyAt took an NSString for a body name. Will have to check on it after my sons Christmas party.
Well I can't take credit for writing it, but yes it's there. The calls talk directly to the GCpShapeCache in order to retrieve a body by name and set it accordingly. You still need to make sure GCpShapeCache loads the file that Physics Editor created when/if you used it to define your shapes/bodies.
Ah. Got it. Thanks!
Another issue. I am setting up SpaceManager in my own project. In (GrenadeGame) Game.h, there is
@interface GameLayer : CCLayer
{
SpaceManagerCocos2d* smgr;
}
@property (readonly) SpaceManager* spaceManager;
+(id) scene;
@end
and in Game.m
@implementation GameLayer
@synthesize spaceManager = smgr;
and later
smgr = [[SpaceManager alloc] init];
smgr.constantDt = 1.0/55.0f;
Now, when i use the same code, I get a compiler warning telling me "Incompatible pointer types assigning to SpaceManagerCocos2d* from SpaceManager*. This is my only warning, and I believe it is causing a SIGABRT. If I were to venture a guess, it appears that I am declaring smgr as both SpaceManager and a SpaceManagerCocos2d objects.
Any ideas?
Nevermind. Pass me the dunce cap. I am an idiot. My alloc should be SpaceManagerCocos2d.
The game is running quite slow (around 20 fps) on an iPhone 4 with iOS 5.1 installed. Physics are displayed like moving in slow motion. Any ideas on that?
What does the profiler say?
The drawing calls on that example aren't very optimized but 20 fps does seem slow.
I digged a little deeper, here's what I found using the OpenGL ES Analyzer:
1) This command was redundant: glPointSize(3.0000000f) at -[cpShapeNode draw]
"OpenGL ES Analyzer detected a GL function call that sets a piece of GL state to its current value. Minimize the number of these redundant state calls, since these calls are performing unnecessary work."
2) Recommend Using VBO at -[cpShapeNode drawPolyShape]
"Your application sourced vertex array data from client memory rather than from a vertex buffer object (VBO). In this situation, every time glDrawArrays or glDrawElements is called the data is retransmitted to the graphics hardware to be rendered. Use VBOs instead to store the per-vertex data. See documentation on glGenBuffers, glBindBuffer, and glBufferData for more information."
3) Recommend using VAO at -[cpShadeNode drawPolyShape]
"Your application used the same vertex array configuration for multiple consecutive calls to glDrawArrays or glDrawElements. Use vertex array objects (VAOs) to encapsulate the vertex array configuration, allowing optimal reuse of that configuration across multiple draw calls. See documentation on glGenVertexArraysOES and glBindVertexArrayOES."
These three hints given by the analyzer had _by far_ the most occurrences in my sample period.
There's also a hint with a higher severity but with way lesser occurrences:
4) Depth Test Enabled Without Depth Buffer at -[CCSprite draw]
"OpenGL ES Analyzer detected rendering with GL_DEPTH_TEST enabled into a framebuffer without an attached depth buffer. To get useful results from depth testing, attach a depth buffer to your FBO."
On an iPhone 4S the game example runs with around 45 FPS which is still way too slow.
Any suggestions on improving performance? Can the SpaceManager version used in this example easily be updated?
Thanks,
Michael
@Michael - Cool, interesting stuff; I guess I've never really run the analyzer before. The VBO suggestion is most likely a good one. There probably should be a batched draw of all cpShapeNodes. I personally don't use that class very much anymore and find myself using cpCCSprite combined with CCSpriteBatchNode.
The newest SpaceManager actually has a debug layer which draws all the shapes and constraints fairly efficiently. Perhaps you could harness that code to draw all the shapes you were interested in.
You must log in to post.