1

我是 jME(java Monkey Engine)的新手。我正在做关于智能家居模拟器的主项目。我决定用 jME 来做这个项目。

现在,我的模拟器中有一个 3D 模型,下一步我想做的是控制我的虚拟房子的大门,所以,我按照这个教程,我可以实现我想要的。

http://www.youtube.com/watch?v=MNDiZ9YHIpM

我试着打开和关闭门,我成功了。但问题是物理,当门打开时你可以看到门是如何打开的,但是当我试图穿过门时我不能,我知道我可以在对象中做一个物理层但是当我尝试这样做控制消失。

我有一个控制我的大门的班级,我想在那个班级中插入一个刚体作为我的门,但我不能,所以我想知道是否有人知道如何做到这一点。

谢谢你!!!

PD:对不起我的英语!!!

这是我正在使用的代码:

主班

public class Main extends SimpleApplication
        implements ActionListener{

private GhostControl ghostControl;
  private Node staticScene,dynamicScene;
  private BulletAppState bulletAppState;
  private RigidBodyControl landscape;
  private OpenDoor rigidDoor;
  private CharacterControl player;
  private Vector3f walkDirection = new Vector3f();
  private boolean left = false, right = false, up = false, down = false;

  Spatial mainDoor;
  OpenDoor control;

  HUD hud = new HUD();
  BitmapText hudText;

  public static void main(String[] args) {
    Main app = new Main();
     //some presets
    AppSettings settings = new AppSettings(true);
    settings.setResolution(1280,720);
    settings.setFrameRate(60);
    //settings.setFullscreen(true);
    app.setSettings(settings);
    //app.setShowSettings(false);
    app.setPauseOnLostFocus(true);
    app.start();
  }

  public void simpleInitApp() {   
    //don't show stats
    setDisplayFps(false);
    setDisplayStatView(false);

    //PIC
    Picture pic = new Picture("HUD Picture");
    pic.setImage(assetManager, "Textures/hudFrame.png", true);
    pic.setWidth(settings.getWidth());
    pic.setHeight(settings.getHeight()/8);
    pic.setPosition(0,settings.getHeight()-settings.getHeight()/8);
    guiNode.attachChild(pic);
    //Show HUD


    hudText = new BitmapText(guiFont, false);   
    hudText.setSize(guiFont.getCharSet().getRenderedSize());      // font size
    hudText.setSize(settings.getHeight()/45);
    hudText.setColor(ColorRGBA.Green);                             // font color
    hudText.setLocalTranslation(settings.getWidth()/45,settings.getHeight()-settings.getHeight()/45, 0); // 
    guiNode.attachChild(hudText);

    hud = new HUD();

    /** Set up Physics */
    bulletAppState = new BulletAppState();
    bulletAppState.setThreadingType(BulletAppState.ThreadingType.PARALLEL);//for bullets
    stateManager.attach(bulletAppState);
    //bulletAppState.getPhysicsSpace().enableDebug(assetManager);
    // We re-use the flyby camera for rotation, while positioning is handled by physics
    viewPort.setBackgroundColor(new ColorRGBA(0.7f, 0.8f, 1f, 1f));
    flyCam.setMoveSpeed(100);
    setUpKeys();
    setUpLight();

    //Preload Levels

    staticScene = (Node) assetManager.loadModel("Scenes/newScene.j3o");
    staticScene.setLocalScale(5f);

    //Intentamos hacer lo mismo pero a partir de un nodo del modelo
    mainDoor = (Spatial)staticScene.getChild("MainDoor-ogremesh");    




    //Set up physics and add level/player to scenegraph

    setDoor(mainDoor);
    setLevel(staticScene);    

  }

  private void setLevel(Spatial level) {
     // We set up collision detection for the scene by creating a
    // compound collision shape and a static RigidBodyControl with mass zero.
    CollisionShape sceneShape =
            CollisionShapeFactory.createMeshShape((Node) level);

    landscape = new RigidBodyControl(sceneShape, 0);  
    level.addControl(landscape);

    // We set up collision detection for the player by creating
    // a capsule collision shape and a CharacterControl.
    // The CharacterControl offers extra settings for
    // size, stepheight, jumping, falling, and gravity.
    // We also put the player in its starting position.
    CapsuleCollisionShape capsuleShape = new CapsuleCollisionShape(1.5f, 6f, 1);
    player = new CharacterControl(capsuleShape, 0.05f);
    player.setJumpSpeed(20);
    player.setFallSpeed(30);
    player.setGravity(30);
    player.setPhysicsLocation(new Vector3f(20,10,-10));
    // We attach the scene and the player to the rootnode and the physics space,
    // to make them appear in the game world.
    rootNode.attachChild(level);
    bulletAppState.getPhysicsSpace().add(landscape);
    bulletAppState.getPhysicsSpace().add(player); 


  }

  public void setDoor(Spatial door){

    CollisionShape sceneDoor =
            CollisionShapeFactory.createMeshShape((Node)door);

    rigidDoor = new OpenDoor(sceneDoor, 0);
    rigidDoor.setKinematic(true);

    door.addControl(rigidDoor);
    bulletAppState.getPhysicsSpace().add(door); 

  }

  private PhysicsSpace getPhysicsSpace() {
        return bulletAppState.getPhysicsSpace();
  }

  private void setUpLight() {
    // We add light so we see the scene
    AmbientLight al = new AmbientLight();
    al.setColor(ColorRGBA.White.mult(0.1f));
    rootNode.addLight(al);

    DirectionalLight dl = new DirectionalLight();
    dl.setColor(ColorRGBA.White);
    dl.setDirection(new Vector3f(1.5f, -2, 2).normalizeLocal());
    rootNode.addLight(dl);
  }

  /** We over-write some navigational key mappings here, so we can
   * add physics-controlled walking and jumping: */
  private void setUpKeys() {
    inputManager.deleteMapping(INPUT_MAPPING_EXIT);
    inputManager.addMapping("Left", new KeyTrigger(KeyInput.KEY_A));
    inputManager.addMapping("Right", new KeyTrigger(KeyInput.KEY_D));
    inputManager.addMapping("Up", new KeyTrigger(KeyInput.KEY_W));
    inputManager.addMapping("Down", new KeyTrigger(KeyInput.KEY_S));
    inputManager.addMapping("Jump", new KeyTrigger(KeyInput.KEY_SPACE));
    inputManager.addMapping("Action", new KeyTrigger(KeyInput.KEY_E));
    inputManager.addMapping("Quit", new KeyTrigger(KeyInput.KEY_ESCAPE));
    inputManager.addListener(this, "Left");
    inputManager.addListener(this, "Right");
    inputManager.addListener(this, "Up");
    inputManager.addListener(this, "Down");
    inputManager.addListener(this, "Jump");
    inputManager.addListener(actionListener,"Action");
    inputManager.addListener(this, "Quit"); // listen for ESC key to close game
  }

  public void onAction(String binding, boolean value, float tpf) {

    hud.setToken(binding);

    if (binding.equals("Left")) {
      if (value) { left = true; } else { left = false; }
    } else if (binding.equals("Right")) {
      if (value) { right = true; } else { right = false; }
    } else if (binding.equals("Up")) {
      if (value) { up = true; } else { up = false; }
    } else if (binding.equals("Down")) {
      if (value) { down = true; } else { down = false; }
    } else if (binding.equals("Jump")) {
      player.jump();
    } else if (binding.equals("Quit")) {
      stop(); // simple way to close game
    } 
  }

  private ActionListener actionListener = new ActionListener() {
    public void onAction(String name, boolean keyPressed, float tpf) {
      if (name.equals("Action") && !keyPressed) {
         rigidDoor.actionDoor();

      }
    }
  };


  @Override
  public void simpleUpdate(float tpf) {

        Vector3f camDir = cam.getDirection().clone().multLocal(0.6f);
        Vector3f camLeft = cam.getLeft().clone().multLocal(0.4f);
        walkDirection.set(0, 0, 0);
        if (left)  { walkDirection.addLocal(camLeft); }
        if (right) { walkDirection.addLocal(camLeft.negate()); }
        if (up)    { walkDirection.addLocal(camDir); }
        if (down)  { walkDirection.addLocal(camDir.negate()); }
        player.setWalkDirection(walkDirection);
        cam.setLocation(player.getPhysicsLocation());  
  }


}

门控类

    public class OpenDoor extends RigidBodyControl{

    static final float PI = 3.14159265359f;    
    private float speed = 5;
    private float inipos = 0f;
    private boolean action = false; //true=opening, false=closing
    RigidBodyControl myRigidBody;

    public OpenDoor() {

    }

    public OpenDoor(CollisionShape sceneDoor, int i) {
        super(sceneDoor,i);

    }

    @Override
    public void update(float tpf) {
        super.update(tpf);
        Quaternion q = new Quaternion();
        q.fromAngles(0, -tpf, 0);

        spatial.rotate(q); 



        /*float angle;
        float angleRads;
        angle = speed;
        angleRads = (angle * PI)/180;
        if(action==true){
            //counter = counter + angleRads;
            if(Math.abs(spatial.getLocalRotation().getY()*2.2-inipos)<PI/2){
                spatial.rotate(0, -angleRads,0); 

            }

        }else{

            if(spatial.getLocalRotation().getY()*2.2-inipos<0){
            spatial.rotate(0, angleRads,0);
            }            

        }          

*/
    }

    /**
     * @return the speed
     */
    public float getSpeed() {
        return speed;
    }

    /**
     * @param speed the speed to set
     */
    public void setSpeed(float speed) {
        this.speed = speed;
    }

    /**
     * @return the action
     */
    public boolean isAction() {
        return action;
    }

    /**
     * @param action the action to set
     */
    public void setAction(boolean action) {
        this.action = action;
    }

    public boolean getAction() {
        return action;
    }

    public void actionDoor(){

       setAction(!action);

    }

    public Object getRigidDoor() {
        return myRigidBody;
    }



}
4

0 回答 0