how to destroy a weld joint - cocos2d-iphone

I have searched extensively and haven't been able to find any guidelines or posts on destroying a weldJoint. How do I destroy the weldJoint between bodyA and bodyB? I created my weldJoint in the following way.
weldJointDef.Initialize(bodyA, bodyB, bodyA->GetWorldCenter());
weldJointDef.collideConnected = false;
weldJoint = (b2WeldJoint*) world->CreateJoint(&weldJointDef);

world->DestroyJoint( weldJoint );

Related

How to change the image of a MenuSpriteItem Cocos2d-x C++

I've got a button that I need to be a toggle button for the sound of a game. I'm using the MenuSpriteItem class.
auto menuSoundOn = Sprite::createWithSpriteFrameName("soundOn.png");
auto menuSoundOff = Sprite::createWithSpriteFrameName("soundOff.png");
auto menuSoundBtn = MenuItemSprite::create(menuSoundOn, menuSoundOff, CC_CALLBACK_1(LevelsLayer::shutSound, this));
menuSoundBtn->setTag(0);
_mainMenu = Menu::create(menuSoundBtn, nullptr);
this->addChild(_mainMenu);
//Then in my shutSound method
auto menuSoundBtn = _mainMenu->getChildByTag(0);
if (_ifSound){
_ifSound = false;
//Do some stuff to shut the sound
menuSoundBtn->setSelectedImage("noSound.png");
}
else{
_ifSound = true;
//Do some stuff to bring the sound back
menuSoundBtn->setSelectedImage("sound.png");
}
The problem is that getting the Btn from his parent with getChildByTag(0) method I receive a Node according with the documentation, but setSelectedImage is not part of the Node class and there is an error telling me so, so what is the right way to access MenuSpriteItems from their Parents and then manipulate them as in this case by changing the Normal Image?
Greetings.
I've got the answer and It's really powerful and simple.
auto menuSoundBtn = dynamic_cast<MenuItemSprite*>(_mainMenu->getChildByTag(0));
This is the explanation from the guy:
This code will get the child with tag 0 and turn it into a MenuItemSprite* object if it is a MenuItemSprite* object, or it returns null if the object was not a MenuItemSprite*.
Hope it helps someone. Greetings.

How do I make a custom event with VTK?

I'm making a thread software with VTK, where I need to change the model itself in real time, while I need to change his method of rendering. Everything is working fine, but, the problem start with the interactor->start(); , the model data gets updated just fine, but it's only showed on screen when I move The camera. Also I have selected some methods for generating a 3D data from a imagedata file, for that I need to close the vtk window (interactor window) and then the code will reopen it and send the new data generated to it...
I would need something like these:
int force close_window = false; int refresh_interactor = false;
I managed to make the Window close, but only with vtkcommand::Keypressed command, but idk how do I do with a new command :S, I tried the vtkcommand::UserEvent but I didn't found a good information about how to deal with that data (like some way to call it)
the way I'm dealing with VTK is with two threads, the first one, is just about the vtk iren loop, and the second one would manage the models and check if iren requires to be updated.
In my dream code it should be something like this:
=======================================================
bool VTKWindow()
{
...
vtkSmartPointer ator = vtkSmartPointer::New();
iren = vtkSmartPointer::New();
RenWindow = vtkSmartPointer::New();
render->SetBackground(.1, .2, .3);
RenWindow->AddRenderer(renderer);
iren->SetRenderWindow(RenWindow);
if(data_type == voxel_type)
{
Render->AddViewProp(VoxelData);
}
else
{
actor->SetMapper(PolyData);
Render->AddActor(Actor);
}
RenWindow->Render();
iren->Start();
}
void ManageVTK()
{
while true loop...
if(force close_window == true)
do some command to exit the iren loop
if(refresh_interactor == true)
do some command to refresh iren
}
Sorry for the english, it's not my native language, and also sorry about the question format, it's the first time I'm using stackoverflow
It may sounds stupid, but, I found a kind of solution for the problem.
I saw on related links this guy vtkRenderWindowInteractor event loop and threading and, it's almost the same problem...
class VTKNewEvent : public vtkCommand{
public:
vtkTypeMacro(VTKNewEvent , vtkCommand);
static VTKNewEvent * New(){
return new VTKNewEvent ;
}
void Execute(vtkObject * caller, unsigned long vtkNotUsed(eventId), void * vtkNotUsed(callData)){
vtkRenderWindowInteractor *iren = static_cast<vtkRenderWindowInteractor*>(caller);
if (iren_close == true){
iren->GetRenderWindow()->Finalize // Stop the interactor
iren->TerminateApp();
iren_close = false;
}
if (iren_update== true){
renderJanela->Render();
iren_update= false;
}
}
};
bool VTKWindow(){
vtkSmartPointer<VTKNewEvent > IrenRefresh= vtkSmartPointer<VTKNewEvent>::New();
...
iren->CreateRepeatingTimer(1);//this makes that IrenRefresh will be called at every 1ms
iren->AddObserver(vtkCommand::TimerEvent, IrenRefresh);
iren->Start();
...
}
it's simple, but, maybe not the best, but it did Th job, I hope this link will help people that are starting into the VTK world, since threads + rendering loop wasn't a simple job to understand what was going on

How can I get other layer in the same scene in cocos2d-x?

I have several layers in the scene, like TLayer,HLayer,TouchLayer. How can I get HLayer in HLayer? The solution I take is that I pass Layer to other Layer. However I met some problems recently. I push the Scene and pop Scene while TouchLayer still exists. So my problem is that is it right to pass HLayer to TouchLayer. Or is there a better way to do it in Cocos2d-x?
In the init() function in Scene:
this->setbackgroundLayer(BackgroundLayer::create());
CC_BREAK_IF(!backgroundLayer);
this->addChild(backgroundLayer);
this->setTLayer(TcharacterLayer::create(backgroundLayer->tianzige));
CC_BREAK_IF(!TLayer);
this->addChild(TLayer);
this->setHLayer(HcharacterLayer::create(testCharacter,backgroundLayer->tianzige_draw));
CC_BREAK_IF(!HLayer);
this->addChild(HLayer);
this->settouchLayer(TouchLayer::create(TLayer,HLayer));
CC_BREAK_IF(!touchLayer);
this->addChild(touchLayer);
I made my own create function:
TouchLayer* TouchLayer::create(TcharacterLayer* t,HcharacterLayer* h){
TouchLayer* pRet = new TouchLayer();
if (pRet && pRet->init(t,h))
{
pRet->autorelease();
return pRet;
}else
{
delete pRet;
pRet = NULL;
return NULL;
}
}
Here's how we've done this in the past. Define a set of tags for our layers.
typedef enum {
kBgLayerTag,
kHLayerTag,
kTLayerTag,
kTouchLayerTag
} MyLayerTags
Then while creating the layers set layer specific tags:
this->setTLayer(TcharacterLayer::create(backgroundLayer->tianzige));
CC_BREAK_IF(!TLayer);
TLayer->setTag(kTLayerTag);
this->addChild(TLayer);
And in TouchLayer access the TLayer and others like:
TcharacterLayer* myTLayer = this->getParent()->getChildByTag(kTLayerTag);
Sure, there is nothing wrong in adding a layer as a child. I would do that this way :
BackgroundLayer has all the necessary layers as children (remember to add TouchLayer as the last one and then pass Touch to others) and then you only add BackgroundLayer to your scene. There is even more simple way (probably better): to make BackgroundLayer inherit all the previous ones - but that depends on how much scenes you are going to make.
Edit:
1)
BackgroundLayer * bglayer = BackgroundLayer::create();
TcharacterLayer * tcharlayer = TcharacterLayer::create();
HcharacterLayer * hcharlayer = HcharacterLayer::create();
TouchLayer * tlayer = TouchLayer::create();
bglayer->addChild(tcharlayer);
bglayer->addChild(hcharlayer);
bglayer->addChild(tlayer);
this->addChild(bglayer);
(assuming this as a CCScene)
2)
class BackgroundLayer : public TcharacterLayer, HcharacterLayer, TouchLayer
{
...
}
In the first case you can give each layer a specific tag and then get the layer by getChildByTag(int tag) or just create fields in the BackgroundLayer class for each layer.

OpenGL ES 2.0 several scenes

How to implement transition between several scenes that use opengl?
I have 2 different scenes. each create its frame and render buffers and bind it. But then I try to switch between these scenes - nothing happens... I tried to delete all buffers when swithing but it's doesn't work. The First scene is still visible..
Well, in my experience you may need to dispose of the textures for the first scene's visuals.
A quick idea is using psm studio's approach to OpenGLES.
public TitleScene ()
{
this.Camera.SetViewFromViewport();
_texture = new Texture2D("Application/images/title.png",false);
_ti = new TextureInfo(_texture);
SpriteUV titleScreen = new SpriteUV(_ti);
titleScreen.Scale = _ti.TextureSizef;
titleScreen.Pivot = new Vector2(0.5f,0.5f);
titleScreen.Position = new Vector2(Director.Instance.GL.Context.GetViewport().Width/2,
Director.Instance.GL.Context.GetViewport().Height/2);
this.AddChild(titleScreen);
public override void Update (float dt)
{
base.Update (dt);
var touches = Touch.GetData(0).ToArray();
if((touches.Length >0 && touches[0].Status == TouchStatus.Down) || Input2.GamePad0.Cross.Press)
{
Director.Instance.ReplaceScene(new MenuScene());
}
}
~TitleScene()
{
_texture.Dispose();
_ti.Dispose ();
}
}
I hope this will give you some help on what you are missing.

Cocos2d: CCCallFuncO with target as parent

I can't seem to get CCCallFuncO working with actionWithTarget set to (JoinedMapsLayer*)self.parent
JoinedMapsLayer is the parent node that a sprite class gets added to.
Inside the sprite class I have a method:
-(void) playAction:(NSString*)name withMessagePart:(NSString *)messagePart {
id displayMessageBox = [CCCallFuncO actionWithTarget:(JoinedMapsLayer*)self.parent
selector:#selector(displayMessageBox:)
object:[NSString stringWithFormat:messagePart]];
if([name isEqualToString:#"shiver"]){
id a1 = [CCMoveTo actionWithDuration:.05 position:ccp(self.sprite.position.x+2, self.sprite.position.y)];
id a2 = [CCMoveTo actionWithDuration:.05 position:ccp(self.sprite.position.x-4, self.sprite.position.y)];
id a3 = [CCMoveTo actionWithDuration:.05 position:ccp(self.sprite.position.x+4, self.sprite.position.y)];
id a4 = [CCMoveTo actionWithDuration:.05 position:ccp(self.sprite.position.x-2, self.sprite.position.y)];
[self.sprite runAction:[CCSequence actions:a1,a2,a3,a2,a3,a2,a3,a2,a3,a2,a3,a2,a3,a2,a3,a2,a3,a2,a3,a2,a3,a2,a3,a4,displayMessageBox, nil]];
}
else if([name isEqualToString:#"spin"]){
id a1 = [CCRotateBy actionWithDuration:.5 angle:360];
[self.sprite runAction:[CCSequence actions:a1,displayMessageBox, nil]];
}
}
It runs the actions just fine on the sprite, but I'm trying to get it to call a method in the parent node. I have a NSLog in there to check, and nothing happens. Any obvious reasons why?
In my parent node's init the class is added to a mutable array
HummingClass *hummingChar = [[HummingClass alloc] init];
[characterArr addObject:hummingChar]
And I access the class later on like:
HummingClass *hummingChar = [characterArr objectAtIndex:interactionIndex];
Interesting thing is that it doesn't crash with self.parent, so I'm thinking I'm not pointing to the parent node correctly. In the objects header I have
#import "JoinedMapsLayer.h"
#class JoinedMapsLayer
edit: even if I do a regular method call like this, it won't work:
[(JoinedMapsLayer*)self.parent displayMessageBox:#"whatever"];
I figured it out with the help of something awful forums. If a sprite is added to an array, you have to assign the parent property manually.
In init in JoinedMapsLayer, I make a temporary pointer to an array index:
tempHummingChar.parent = self;